diff --git a/lib/capybara/node/finders.rb b/lib/capybara/node/finders.rb index 4566d5e8..a5886cb2 100644 --- a/lib/capybara/node/finders.rb +++ b/lib/capybara/node/finders.rb @@ -25,7 +25,7 @@ module Capybara def find(*args) synchronize do query = Capybara::Query.new(*args) - if query.match == :smart + if query.match == :smart or query.match == :prefer_exact result = resolve_query(query, true) result = resolve_query(query, false) if result.size == 0 and not query.exact else diff --git a/lib/capybara/spec/session/find_spec.rb b/lib/capybara/spec/session/find_spec.rb index 99c63d20..22cc8a01 100644 --- a/lib/capybara/spec/session/find_spec.rb +++ b/lib/capybara/spec/session/find_spec.rb @@ -189,6 +189,11 @@ Capybara::SpecHelper.spec '#find' do result = @session.find(:xpath, XPath.descendant[XPath.attr(:class).is("almost_singular but")], :match => :smart, :exact => false) result.text.should == "almost singular but not quite" end + it "raises an error if there is no match" do + expect do + @session.find(:css, ".does-not-exist", :match => :smart, :exact => false) + end.to raise_error(Capybara::ElementNotFound) + end end context "with `exact` set to `true`" do @@ -211,6 +216,63 @@ Capybara::SpecHelper.spec '#find' do result = @session.find(:xpath, XPath.descendant[XPath.attr(:class).is("almost_singular but")], :match => :smart, :exact => true) end.to raise_error(Capybara::ElementNotFound) end + it "raises an error if there is no match" do + expect do + @session.find(:css, ".does-not-exist", :match => :smart, :exact => true) + end.to raise_error(Capybara::ElementNotFound) + end + end + end + + context "when set to `prefer_exact`" do + context "and `exact` set to `false`" do + it "picks the first one when there are multiple exact matches" do + result = @session.find(:xpath, XPath.descendant[XPath.attr(:class).is("multiple")], :match => :prefer_exact, :exact => false) + result.text.should == "multiple one" + end + it "finds a single exact match when there also are inexact matches" do + result = @session.find(:xpath, XPath.descendant[XPath.attr(:class).is("almost_singular")], :match => :prefer_exact, :exact => false) + result.text.should == "almost singular" + end + it "picks the first one when there are multiple inexact matches" do + result = @session.find(:xpath, XPath.descendant[XPath.attr(:class).is("almost_singul")], :match => :prefer_exact, :exact => false) + result.text.should == "almost singular but not quite" + end + it "finds a single inexact match" do + result = @session.find(:xpath, XPath.descendant[XPath.attr(:class).is("almost_singular but")], :match => :prefer_exact, :exact => false) + result.text.should == "almost singular but not quite" + end + it "raises an error if there is no match" do + expect do + @session.find(:css, ".does-not-exist", :match => :prefer_exact, :exact => false) + end.to raise_error(Capybara::ElementNotFound) + end + end + + context "with `exact` set to `true`" do + it "picks the first one when there are multiple exact matches" do + result = @session.find(:xpath, XPath.descendant[XPath.attr(:class).is("multiple")], :match => :prefer_exact, :exact => true) + result.text.should == "multiple one" + end + it "finds a single exact match when there also are inexact matches" do + result = @session.find(:xpath, XPath.descendant[XPath.attr(:class).is("almost_singular")], :match => :prefer_exact, :exact => true) + result.text.should == "almost singular" + end + it "raises an error if there are multiple inexact matches" do + expect do + @session.find(:xpath, XPath.descendant[XPath.attr(:class).is("almost_singul")], :match => :prefer_exact, :exact => true) + end.to raise_error(Capybara::ElementNotFound) + end + it "raises an error if there is a single inexact match" do + expect do + @session.find(:xpath, XPath.descendant[XPath.attr(:class).is("almost_singular but")], :match => :prefer_exact, :exact => true) + end.to raise_error(Capybara::ElementNotFound) + end + it "raises an error if there is no match" do + expect do + @session.find(:css, ".does-not-exist", :match => :prefer_exact, :exact => true) + end.to raise_error(Capybara::ElementNotFound) + end end end