teamcapybara/capybara · error · Capybara::ExpectationNotMet
Item does not match the provided selector
Error message
Item does not match the provided selector
What it means
assert_matches_selector verifies that the receiver element itself is among the nodes matching the given selector plus filters; _verify_match_result resolves the MatchQuery and raises ExpectationNotMet 'Item does not match the provided selector' when self is not in the result set. Unlike assert_selector it checks identity of this specific node, not just that some node matches.
Source
Thrown at lib/capybara/node/matchers.rb:590
##
#
# Asserts that the current node matches a given selector.
#
# node.assert_matches_selector('p#foo')
# node.assert_matches_selector(:xpath, '//p[@id="foo"]')
# node.assert_matches_selector(:foo)
#
# It also accepts all options that {Capybara::Node::Finders#all} accepts,
# such as `:text` and `:visible`.
#
# node.assert_matches_selector('li', text: 'Horse', visible: true)
#
# @param (see Capybara::Node::Finders#all)
# @raise [Capybara::ExpectationNotMet] If the selector does not match
#
def assert_matches_selector(*args, &optional_filter_block)
_verify_match_result(args, optional_filter_block) do |result|
raise Capybara::ExpectationNotMet, 'Item does not match the provided selector' unless result.include? self
end
end
##
#
# Asserts that the current node does not match a given selector.
# Usage is identical to {#assert_matches_selector}.
#
# @param (see #assert_matches_selector)
# @raise [Capybara::ExpectationNotMet] If the selector matches
#
def assert_not_matches_selector(*args, &optional_filter_block)
_verify_match_result(args, optional_filter_block) do |result|
raise Capybara::ExpectationNotMet, 'Item matched the provided selector' if result.include? self
end
end
##View on GitHub (pinned to 15b5fdb76e)
Solutions
- Inspect the element (el.text, el[:class], el[:type]) and align the selector/filters with its real state
- For dynamic states add wait: el.assert_matches_selector('input', checked: true, wait: 5)
- Use the right selector type (:field/:link/:css) whose built-in filters match what you assert
- If you only care that the page contains such nodes, use assert_selector instead of the element-matching form
Example fix
# before
el.assert_matches_selector('li', text: 'Horse') # el.text == 'Horse '
# after
el.assert_matches_selector('li', text: /Horse/)
# or normalize whitespace
el.assert_matches_selector('li', text: 'Horse', normalize_ws: true) Defensive patterns
Strategy: validation
Validate before calling
return unless el.matches_selector?('li', text: /Horse/)
el.assert_matches_selector('li', text: /Horse/) Type guard
def node_matches?(node, *args, **opts, &block) node.matches_selector?(*args, **opts, &block) end
Try / catch
begin
el.assert_matches_selector('input', checked: true, wait: 3)
rescue Capybara::ExpectationNotMet => e
raise unless el.matches_selector?('input') # node exists; state differs — re-drive UI
raise
end Prevention
- Use matches_selector? when you need a boolean branch instead of an exception
- Assert dynamic states (checked/disabled/class) with wait: >= app update time
- Re-find elements after actions that re-render their subtree
When it happens
Trigger: el.assert_matches_selector('li', text: 'Horse') when el is a li but its text is 'Cow'; el.assert_matches_selector('input[type=checkbox]', checked: true) when the box is unchecked; el.assert_matches_selector(:field, 'Email') on an element labelled differently; matching on tag/class that the node does not have.
Common situations: Verifying a located element still satisfies a contract after page updates (element went stale or attributes changed between find and assert), wrong filter values (text with different whitespace), asserting on attributes that toggle dynamically (checked/disabled/active class) before the state settles.
Related errors
- Item matched the provided selector
- result.failure_message
- res.join(' or ')
- result.negative_failure_message
- Ambiguous match, found #{result.size} elements matching #{qu
AI-assisted analysis of teamcapybara/capybara@15b5fdb76e (2026-08-21).
Data as JSON: /api/errors/2e9459b34f7c4c77.
Report an issue: GitHub.