capybara 2.0.3 → 2.1.0.beta1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (81) hide show
  1. data.tar.gz.sig +0 -0
  2. data/History.md +73 -0
  3. data/README.md +52 -5
  4. data/lib/capybara.rb +44 -62
  5. data/lib/capybara/cucumber.rb +4 -1
  6. data/lib/capybara/driver/base.rb +13 -9
  7. data/lib/capybara/driver/node.rb +18 -6
  8. data/lib/capybara/helpers.rb +111 -22
  9. data/lib/capybara/node/actions.rb +24 -19
  10. data/lib/capybara/node/base.rb +25 -32
  11. data/lib/capybara/node/document.rb +6 -2
  12. data/lib/capybara/node/element.rb +45 -7
  13. data/lib/capybara/node/finders.rb +48 -21
  14. data/lib/capybara/node/matchers.rb +38 -21
  15. data/lib/capybara/node/simple.rb +29 -7
  16. data/lib/capybara/query.rb +72 -26
  17. data/lib/capybara/rack_test/browser.rb +11 -3
  18. data/lib/capybara/rack_test/css_handlers.rb +8 -0
  19. data/lib/capybara/rack_test/driver.rb +11 -3
  20. data/lib/capybara/rack_test/form.rb +8 -1
  21. data/lib/capybara/rack_test/node.rb +92 -36
  22. data/lib/capybara/rails.rb +1 -2
  23. data/lib/capybara/result.rb +21 -37
  24. data/lib/capybara/rspec/matchers.rb +60 -31
  25. data/lib/capybara/selector.rb +46 -13
  26. data/lib/capybara/selenium/driver.rb +42 -6
  27. data/lib/capybara/selenium/node.rb +23 -5
  28. data/lib/capybara/session.rb +46 -11
  29. data/lib/capybara/spec/public/test.js +12 -0
  30. data/lib/capybara/spec/session/all_spec.rb +9 -8
  31. data/lib/capybara/spec/session/attach_file_spec.rb +14 -0
  32. data/lib/capybara/spec/session/check_spec.rb +14 -0
  33. data/lib/capybara/spec/session/choose_spec.rb +14 -0
  34. data/lib/capybara/spec/session/click_button_spec.rb +77 -1
  35. data/lib/capybara/spec/session/click_link_or_button_spec.rb +65 -0
  36. data/lib/capybara/spec/session/click_link_spec.rb +24 -0
  37. data/lib/capybara/spec/session/current_scope_spec.rb +29 -0
  38. data/lib/capybara/spec/session/fill_in_spec.rb +14 -0
  39. data/lib/capybara/spec/session/find_button_spec.rb +12 -0
  40. data/lib/capybara/spec/session/find_by_id_spec.rb +12 -1
  41. data/lib/capybara/spec/session/find_field_spec.rb +30 -0
  42. data/lib/capybara/spec/session/find_link_spec.rb +12 -0
  43. data/lib/capybara/spec/session/find_spec.rb +258 -16
  44. data/lib/capybara/spec/session/first_spec.rb +25 -8
  45. data/lib/capybara/spec/session/has_css_spec.rb +2 -2
  46. data/lib/capybara/spec/session/has_field_spec.rb +10 -2
  47. data/lib/capybara/spec/session/has_selector_spec.rb +9 -0
  48. data/lib/capybara/spec/session/has_text_spec.rb +96 -0
  49. data/lib/capybara/spec/session/has_title_spec.rb +47 -0
  50. data/lib/capybara/spec/session/node_spec.rb +43 -0
  51. data/lib/capybara/spec/session/reset_session_spec.rb +10 -2
  52. data/lib/capybara/spec/session/save_page_spec.rb +30 -0
  53. data/lib/capybara/spec/session/select_spec.rb +65 -0
  54. data/lib/capybara/spec/session/text_spec.rb +31 -0
  55. data/lib/capybara/spec/session/title_spec.rb +16 -0
  56. data/lib/capybara/spec/session/uncheck_spec.rb +14 -0
  57. data/lib/capybara/spec/session/unselect_spec.rb +42 -0
  58. data/lib/capybara/spec/session/visit_spec.rb +3 -3
  59. data/lib/capybara/spec/session/within_frame_spec.rb +14 -0
  60. data/lib/capybara/spec/session/within_spec.rb +3 -3
  61. data/lib/capybara/spec/spec_helper.rb +6 -1
  62. data/lib/capybara/spec/views/form.erb +39 -2
  63. data/lib/capybara/spec/views/frame_child.erb +9 -0
  64. data/lib/capybara/spec/views/frame_parent.erb +8 -0
  65. data/lib/capybara/spec/views/with_base_tag.erb +10 -0
  66. data/lib/capybara/spec/views/with_count.erb +7 -0
  67. data/lib/capybara/spec/views/with_hover.erb +17 -0
  68. data/lib/capybara/spec/views/with_html.erb +21 -2
  69. data/lib/capybara/spec/views/with_js.erb +5 -0
  70. data/lib/capybara/spec/views/with_scope.erb +6 -1
  71. data/lib/capybara/spec/views/with_title.erb +1 -0
  72. data/lib/capybara/spec/views/within_frames.erb +1 -0
  73. data/lib/capybara/version.rb +1 -1
  74. data/spec/basic_node_spec.rb +75 -24
  75. data/spec/dsl_spec.rb +2 -1
  76. data/spec/rack_test_spec.rb +4 -3
  77. data/spec/rspec/matchers_spec.rb +105 -17
  78. data/spec/server_spec.rb +8 -8
  79. data/spec/spec_helper.rb +2 -1
  80. metadata +83 -23
  81. metadata.gz.sig +0 -0
@@ -4,6 +4,37 @@ Capybara::SpecHelper.spec '#text' do
4
4
  @session.text.should == 'Bar'
5
5
  end
6
6
 
7
+ it "ignores invisible text by default" do
8
+ @session.visit('/with_html')
9
+ @session.find(:id, "hidden-text").text.should == 'Some of this text is'
10
+ end
11
+
12
+ it "shows invisible text if `:all` given" do
13
+ @session.visit('/with_html')
14
+ @session.find(:id, "hidden-text").text(:all).should == 'Some of this text is hidden!'
15
+ end
16
+
17
+ it "ignores invisible text if `:visible` given" do
18
+ Capybara.ignore_hidden_elements = false
19
+ @session.visit('/with_html')
20
+ @session.find(:id, "hidden-text").text(:visible).should == 'Some of this text is'
21
+ end
22
+
23
+ it "ignores invisible text if `Capybara.ignore_hidden_elements = true`" do
24
+ @session.visit('/with_html')
25
+ @session.find(:id, "hidden-text").text.should == 'Some of this text is'
26
+ Capybara.ignore_hidden_elements = false
27
+ @session.find(:id, "hidden-text").text.should == 'Some of this text is hidden!'
28
+ end
29
+
30
+ it "ignores invisible text if `Capybara.visible_text_only = true`" do
31
+ @session.visit('/with_html')
32
+ Capybara.visible_text_only = true
33
+ @session.find(:id, "hidden-text").text.should == 'Some of this text is'
34
+ Capybara.ignore_hidden_elements = false
35
+ @session.find(:id, "hidden-text").text.should == 'Some of this text is'
36
+ end
37
+
7
38
  context "with css as default selector" do
8
39
  before { Capybara.default_selector = :css }
9
40
  it "should print the text of the page" do
@@ -0,0 +1,16 @@
1
+ Capybara::SpecHelper.spec '#title' do
2
+
3
+ it "should print the title of the page" do
4
+ @session.visit('/with_title')
5
+ @session.title.should == 'Test Title'
6
+ end
7
+
8
+ context "with css as default selector" do
9
+ before { Capybara.default_selector = :css }
10
+ it "should print the title of the page" do
11
+ @session.visit('/with_title')
12
+ @session.title.should == 'Test Title'
13
+ end
14
+ after { Capybara.default_selector = :xpath }
15
+ end
16
+ end
@@ -23,4 +23,18 @@ Capybara::SpecHelper.spec "#uncheck" do
23
23
  extract_results(@session)['pets'].should include('dog')
24
24
  extract_results(@session)['pets'].should_not include('hamster')
25
25
  end
26
+
27
+ context "with :exact option" do
28
+ it "should accept partial matches when false" do
29
+ @session.uncheck('Ham', :exact => false)
30
+ @session.click_button('awesome')
31
+ extract_results(@session)['pets'].should_not include('hamster')
32
+ end
33
+
34
+ it "should not accept partial matches when true" do
35
+ expect do
36
+ @session.uncheck('Ham', :exact => true)
37
+ end.to raise_error(Capybara::ElementNotFound)
38
+ end
39
+ end
26
40
  end
@@ -69,4 +69,46 @@ Capybara::SpecHelper.spec "#unselect" do
69
69
  end.to raise_error(Capybara::ElementNotFound, msg)
70
70
  end
71
71
  end
72
+
73
+ context "with :exact option" do
74
+ context "when `false`" do
75
+ it "can match select box approximately" do
76
+ @session.unselect("Boxerbriefs", :from => "Under", :exact => false)
77
+ @session.click_button("awesome")
78
+ extract_results(@session)["underwear"].should_not include("Boxerbriefs")
79
+ end
80
+
81
+ it "can match option approximately" do
82
+ @session.unselect("Boxerbr", :from => "Underwear", :exact => false)
83
+ @session.click_button("awesome")
84
+ extract_results(@session)["underwear"].should_not include("Boxerbriefs")
85
+ end
86
+
87
+ it "can match option approximately when :from not given" do
88
+ @session.unselect("Boxerbr", :exact => false)
89
+ @session.click_button("awesome")
90
+ extract_results(@session)["underwear"].should_not include("Boxerbriefs")
91
+ end
92
+ end
93
+
94
+ context "when `true`" do
95
+ it "can match select box approximately" do
96
+ expect do
97
+ @session.unselect("Boxerbriefs", :from => "Under", :exact => true)
98
+ end.to raise_error(Capybara::ElementNotFound)
99
+ end
100
+
101
+ it "can match option approximately" do
102
+ expect do
103
+ @session.unselect("Boxerbr", :from => "Underwear", :exact => true)
104
+ end.to raise_error(Capybara::ElementNotFound)
105
+ end
106
+
107
+ it "can match option approximately when :from not given" do
108
+ expect do
109
+ @session.unselect("Boxerbr", :exact => true)
110
+ end.to raise_error(Capybara::ElementNotFound)
111
+ end
112
+ end
113
+ end
72
114
  end
@@ -72,18 +72,18 @@ Capybara::SpecHelper.spec '#visit' do
72
72
  it "should send a referer when following a link" do
73
73
  @session.visit '/referer_base'
74
74
  @session.find('//a[@href="/get_referer"]').click
75
- @session.body.should match %r{http://.*/referer_base}
75
+ @session.should have_content %r{http://.*/referer_base}
76
76
  end
77
77
 
78
78
  it "should preserve the original referer URL when following a redirect" do
79
79
  @session.visit('/referer_base')
80
80
  @session.find('//a[@href="/redirect_to_get_referer"]').click
81
- @session.body.should match %r{http://.*/referer_base}
81
+ @session.should have_content %r{http://.*/referer_base}
82
82
  end
83
83
 
84
84
  it "should send a referer when submitting a form" do
85
85
  @session.visit '/referer_base'
86
86
  @session.find('//input').click
87
- @session.body.should match %r{http://.*/referer_base}
87
+ @session.should have_content %r{http://.*/referer_base}
88
88
  end
89
89
  end
@@ -28,4 +28,18 @@ Capybara::SpecHelper.spec '#within_frame', :requires => [:frames] do
28
28
  it "should return the result of executing the block" do
29
29
  @session.within_frame("frameOne") { "return value" }.should eql "return value"
30
30
  end
31
+ it "should find the div given Element" do
32
+ element = @session.find(:id, 'frameOne')
33
+ @session.within_frame element do
34
+ @session.find("//*[@id='divInFrameOne']").text.should eql 'This is the text of divInFrameOne'
35
+ end
36
+ end
37
+ it "should find multiple nested frames" do
38
+ @session.within_frame 'parentFrame' do
39
+ @session.within_frame 'childFrame' do
40
+ @session.within_frame 'grandchildFrame1' do end
41
+ @session.within_frame 'grandchildFrame2' do end
42
+ end
43
+ end
44
+ end
31
45
  end
@@ -5,7 +5,7 @@ Capybara::SpecHelper.spec '#within' do
5
5
 
6
6
  context "with CSS selector" do
7
7
  it "should click links in the given scope" do
8
- @session.within(:css, "#for_bar li[contains('With Simple HTML')]") do
8
+ @session.within(:css, "#for_bar li", text: 'With Simple HTML') do
9
9
  @session.click_link('Go')
10
10
  end
11
11
  @session.should have_content('Bar')
@@ -46,7 +46,7 @@ Capybara::SpecHelper.spec '#within' do
46
46
 
47
47
  context "with Node rather than selector" do
48
48
  it "should click links in the given scope" do
49
- node_of_interest = @session.find(:css, "#for_bar li[contains('With Simple HTML')]")
49
+ node_of_interest = @session.find(:css, "#for_bar li", text: 'With Simple HTML')
50
50
 
51
51
  @session.within(node_of_interest) do
52
52
  @session.click_link('Go')
@@ -58,7 +58,7 @@ Capybara::SpecHelper.spec '#within' do
58
58
  context "with the default selector set to CSS" do
59
59
  before { Capybara.default_selector = :css }
60
60
  it "should use CSS" do
61
- @session.within("#for_bar li[contains('With Simple HTML')]") do
61
+ @session.within("#for_bar li", text: 'With Simple HTML') do
62
62
  @session.click_link('Go')
63
63
  end
64
64
  @session.should have_content('Bar')
@@ -2,7 +2,6 @@ require "rspec"
2
2
  require "capybara"
3
3
  require "capybara/rspec" # Required here instead of in rspec_spec to avoid RSpec deprecation warning
4
4
  require "capybara/spec/test_app"
5
- require "capybara/spec/spec_helper"
6
5
  require "nokogiri"
7
6
 
8
7
  module Capybara
@@ -19,6 +18,12 @@ module Capybara
19
18
  Capybara.app_host = nil
20
19
  Capybara.default_selector = :xpath
21
20
  Capybara.default_wait_time = 1
21
+ Capybara.ignore_hidden_elements = true
22
+ Capybara.exact = false
23
+ Capybara.exact_options = false
24
+ Capybara.raise_server_errors = true
25
+ Capybara.visible_text_only = false
26
+ Capybara.match = :smart
22
27
  end
23
28
 
24
29
  def filter(requires, metadata)
@@ -8,9 +8,21 @@
8
8
  <option>Mrs</option>
9
9
  <option>Mr</option>
10
10
  <option>Miss</option>
11
+ <option disabled="disabled">Other</option>
11
12
  </select>
13
+ </p>
14
+
15
+ <p>
16
+ <label for="customer_name">Customer Name
17
+ <input type="text" name="form[customer_name]" value="Blah" id="customer_name" disabled="disabled"/>
18
+ </label>
12
19
  </p>
13
20
 
21
+ <p>
22
+ <label for="customer_email">Customer Email
23
+ <input type="text" name="form[customer_email]" value="ben@ben.com" id="customer_email"/>
24
+ </label>
25
+ </p>
14
26
 
15
27
  <p>
16
28
  <label for="form_other_title">Other title</label>
@@ -253,10 +265,35 @@
253
265
  <button type="submit" id="click_me_123" title="Click Title button" value="click_me">Click me!</button>
254
266
  <button type="submit" name="form[no_value]">No Value!</button>
255
267
  <button id="no_type">No Type!</button>
256
- <input type="button" disabled value="Disabled button"/>
268
+ <input type="button" disabled="disabled" value="Disabled button"/>
257
269
  </p>
258
270
  </form>
259
271
 
272
+ <input type="text" name="form[outside_input]" value="outside_input" form="form1"/>
273
+
274
+ <form id="form1" action="/form" method="post">
275
+ <input type="text" name="form[which_form]" value="form1" id="form_which_form"/>
276
+ <input type="text" name="form[for_form2]" value="for_form2" form="form2"/>
277
+ <input type="submit" name="form[submit_form1]" value="submit_form1" id="submit_form1"/>
278
+ </form>
279
+
280
+ <form id="form2" action="/form" method="post">
281
+ <input type="text" name="form[which_form]" value="form2" id="form_which_form"/>
282
+ <input type="submit" name="form[unused]" value="unused"/>
283
+ <button type="submit" name="form[other_form_button]" value="other_form_button" form="form1">Form1</button>
284
+ </form>
285
+
286
+ <textarea name="form[outside_textarea]" form="form1">Some text here</textarea>
287
+ <select name="form[outside_select]" form="form1">
288
+ <option>Lisp</option>
289
+ <option selected="selected">Ruby</option>
290
+ <option>Php</option>
291
+ </select>
292
+
293
+ <input type="submit" name="form[outside_submit]" value="outside_submit" form="form1"/>
294
+ <button type="submit" name="form[outside_button]" value="outside_button" form="form2">Outside!</button>
295
+
296
+
260
297
  <form id="get-form" action="/form/get?foo=bar" method="get">
261
298
  <p>
262
299
  <label for="form_middle_name">Middle Name</label>
@@ -304,7 +341,7 @@
304
341
 
305
342
  <p>
306
343
  <label for="form_multiple_documents">Multiple Documents</label>
307
- <input type="file" name="form[multiple_documents][]" id="form_multiple_documents" multiple />
344
+ <input type="file" name="form[multiple_documents][]" id="form_multiple_documents" multiple="multiple" />
308
345
  </p>
309
346
 
310
347
  <p>
@@ -0,0 +1,9 @@
1
+ <html>
2
+ <head>
3
+ <title>This is the child frame title</title>
4
+ </head>
5
+ <body>
6
+ <iframe src="/frame_one" id="grandchildFrame1"></iframe>
7
+ <iframe src="/frame_two" id="grandchildFrame2"></iframe>
8
+ </body>
9
+ </html>
@@ -0,0 +1,8 @@
1
+ <html>
2
+ <head>
3
+ <title>This is the parent frame title</title>
4
+ </head>
5
+ <body>
6
+ <iframe src='/frame_child' id='childFrame'></iframe>
7
+ </body>
8
+ </html>
@@ -0,0 +1,10 @@
1
+ <html xmlns="http://www.w3.org/1999/xhtml" lang="en">
2
+ <head>
3
+ <meta http-equiv="Content-type" content="text/html; charset=utf-8"/>
4
+ <base href="http://example2.com" />
5
+ <title>with_external_source</title>
6
+ </head>
7
+ <body id="with_js">
8
+ <h1>FooBar</h1>
9
+ </body>
10
+ </html
@@ -0,0 +1,7 @@
1
+ <h1>This page is used for testing number options of has_text?</h1>
2
+
3
+ <p>count1</p>
4
+ <div>
5
+ <p>2 count</p>
6
+ <p>Count</p>
7
+ </div>
@@ -0,0 +1,17 @@
1
+ <html xmlns="http://www.w3.org/1999/xhtml" lang="en">
2
+ <head>
3
+ <meta http-equiv="Content-type" content="text/html; charset=utf-8"/>
4
+ <title>with_hover</title>
5
+ </head>
6
+
7
+ <body id="with_hover">
8
+ <style type="text/css">
9
+ .hidden_until_hover {display: none;}
10
+ .wrapper:hover .hidden_until_hover { display: block }
11
+ </style>
12
+ <div class="wrapper">
13
+ Some text here so the wrapper has size
14
+ <div class="hidden_until_hover">Here I am</div>
15
+ </div>
16
+ </body>
17
+ </html>
@@ -28,11 +28,13 @@
28
28
 
29
29
  <p>
30
30
  <input type="text" id="test_field" value="monkey"/>
31
+ <input type="text" readonly="readonly" value="should not change" />
31
32
  <textarea id="normal">
32
33
  banana</textarea>
33
34
  <textarea id="additional_newline">
34
35
 
35
36
  banana</textarea>
37
+ <textarea readonly="readonly">textarea should not change</textarea>
36
38
  <a href="/redirect_back">BackToMyself</a>
37
39
  <a title="twas a fine link" href="/redirect">A link came first</a>
38
40
  <a title="a fine link" href="/with_simple_html">A link</a>
@@ -49,6 +51,7 @@ banana</textarea>
49
51
  <input type="text" checked="checked" id="checked_field">
50
52
  <a href="/redirect"><img width="20" height="20" alt="very fine image" /></a>
51
53
  <a href="/with_simple_html"><img width="20" height="20" alt="fine image" /></a>
54
+ <a href="/with_simple_html" disabled="disabled">Disabled link</a>
52
55
 
53
56
  <a href="?query_string=true">Naked Query String</a>
54
57
  <% if params[:query_string] %>
@@ -61,6 +64,10 @@ banana</textarea>
61
64
  <a href="/with_simple_html" title="hidden link" class="simple">hidden link</a>
62
65
  </div>
63
66
 
67
+ <div id="hidden-text">
68
+ Some of this text is <em style="display:none">hidden!</em>
69
+ </div>
70
+
64
71
  <div style="display: none;">
65
72
  <a id="first_invisble" class="hidden">first hidden link</a>
66
73
  </div>
@@ -78,6 +85,18 @@ banana</textarea>
78
85
  </div>
79
86
 
80
87
  <ul>
81
- <li id="john_monkey">Monkey John</li>
82
- <li id="paul_monkey">Monkey Paul</li>
88
+ <li class="beatle guitarist" id="john">John</li>
89
+ <li class="beatle bassist drummer" id="paul">Paul</li>
90
+ <li class="beatle guitarist" id="george">George</li>
91
+ <li class="beatle drummer" id="ringo">Ringo</li>
83
92
  </ul>
93
+
94
+ <div>
95
+ <div class="singular">singular</div>
96
+ <div class="multiple">multiple one</div>
97
+ <div class="multiple">multiple two</div>
98
+ <div class="almost_singular but_not_quite">almost singular but not quite</div>
99
+ <div class="almost_singular">almost singular</div>
100
+ </div>
101
+
102
+ <input type="text" disabled="disabled" name="disabled_text" value="This is disabled"/>
@@ -19,6 +19,7 @@
19
19
  </div>
20
20
 
21
21
  <p><a href="#" id="clickable">Click me</a></p>
22
+ <p><a href="#" id="slow-click">Slowly</a></p>
22
23
 
23
24
  <p>
24
25
  <select id="waiter">
@@ -57,6 +58,10 @@
57
58
  </ul>
58
59
  </p>
59
60
 
61
+ <p>
62
+ <a href="#" id="change-title">Change title</a>
63
+ </p>
64
+
60
65
  <script type="text/javascript">
61
66
  // a javascript comment
62
67
  var aVar = 123;
@@ -4,6 +4,7 @@
4
4
  Lorem ipsum dolor sit amet, consectetur adipisicing elit, sed do eiusmod tempor
5
5
  incididunt ut labore et dolore magna aliqua. Ut enim ad minim venia.
6
6
  <a href="/redirect">Go</a>
7
+ <input name="disabled" disabled="disabled"/>
7
8
  </p>
8
9
 
9
10
  <div id="for_bar">
@@ -23,6 +24,10 @@
23
24
  <label for="bar_first_name">First Name</label>
24
25
  <input type="text" name="form[first_name]" value="Peter" id="bar_first_name"/>
25
26
  </p>
27
+ <p>
28
+ <label for="bar_other_name">Other Name</label>
29
+ <input type="text" name="form[other_name]" value="James" id="bar_other_name" disabled="disabled"/>
30
+ </p>
26
31
  <p><input type="submit" value="Go"/></p>
27
32
  </form>
28
33
  </li>
@@ -33,4 +38,4 @@
33
38
  <ul>
34
39
  <li>With Simple HTML: <a href="/">Go</a>
35
40
  </ul>
36
- </div>
41
+ </div>
@@ -0,0 +1 @@
1
+ <title>Test Title</title>
@@ -6,5 +6,6 @@
6
6
  <div id="divInMainWindow">This is the text for divInMainWindow</div>
7
7
  <iframe src="/frame_one" id="frameOne"></iframe>
8
8
  <iframe src="/frame_two" id="frameTwo"></iframe>
9
+ <iframe src="/frame_parent" id="parentFrame"></iframe>
9
10
  </body>
10
11
  </html>