capybara 3.21.0 → 3.22.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (35) hide show
  1. checksums.yaml +4 -4
  2. data/.yardopts +1 -0
  3. data/History.md +14 -0
  4. data/README.md +13 -8
  5. data/lib/capybara.rb +38 -32
  6. data/lib/capybara/driver/node.rb +2 -2
  7. data/lib/capybara/minitest.rb +14 -1
  8. data/lib/capybara/minitest/spec.rb +20 -7
  9. data/lib/capybara/node/finders.rb +41 -47
  10. data/lib/capybara/node/matchers.rb +161 -72
  11. data/lib/capybara/queries/ancestor_query.rb +9 -7
  12. data/lib/capybara/queries/sibling_query.rb +11 -4
  13. data/lib/capybara/result.rb +2 -0
  14. data/lib/capybara/rspec/matchers.rb +16 -1
  15. data/lib/capybara/rspec/matchers/have_ancestor.rb +30 -0
  16. data/lib/capybara/rspec/matchers/have_sibling.rb +30 -0
  17. data/lib/capybara/selector.rb +153 -171
  18. data/lib/capybara/selector/definition/checkbox.rb +8 -5
  19. data/lib/capybara/selector/definition/radio_button.rb +8 -5
  20. data/lib/capybara/selector/filter_set.rb +4 -2
  21. data/lib/capybara/selenium/driver_specializations/chrome_driver.rb +35 -1
  22. data/lib/capybara/session.rb +74 -71
  23. data/lib/capybara/session/config.rb +1 -1
  24. data/lib/capybara/spec/session/check_spec.rb +6 -0
  25. data/lib/capybara/spec/session/choose_spec.rb +6 -0
  26. data/lib/capybara/spec/session/has_ancestor_spec.rb +44 -0
  27. data/lib/capybara/spec/session/has_sibling_spec.rb +50 -0
  28. data/lib/capybara/spec/session/select_spec.rb +5 -5
  29. data/lib/capybara/spec/views/form.erb +1 -1
  30. data/lib/capybara/version.rb +1 -1
  31. data/lib/capybara/window.rb +10 -10
  32. data/spec/minitest_spec.rb +11 -1
  33. data/spec/minitest_spec_spec.rb +11 -1
  34. data/spec/regexp_dissassembler_spec.rb +1 -1
  35. metadata +7 -2
@@ -96,7 +96,7 @@ module Capybara
96
96
  # This attribute will be checked by builtin selector types whenever id would normally be checked.
97
97
  # If `nil` then it will be ignored.
98
98
  #
99
- # @params [String, Symbol, nil] id Name of the attribute to use as the test id
99
+ # @param [String, Symbol, nil] id Name of the attribute to use as the test id
100
100
  #
101
101
  def test_id=(id)
102
102
  @test_id = id&.to_sym
@@ -120,6 +120,12 @@ Capybara::SpecHelper.spec '#check' do
120
120
  expect(extract_results(@session)['pets']).to include('cat')
121
121
  end
122
122
 
123
+ it 'should alias `with`' do
124
+ @session.check('form[pets][]', with: 'cat')
125
+ @session.click_button('awesome')
126
+ expect(extract_results(@session)['pets']).to include('cat')
127
+ end
128
+
123
129
  it 'should raise an error if option not found' do
124
130
  expect do
125
131
  @session.check('form[pets][]', option: 'elephant')
@@ -74,6 +74,12 @@ Capybara::SpecHelper.spec '#choose' do
74
74
  expect(extract_results(@session)['gender']).to eq('male')
75
75
  end
76
76
 
77
+ it 'should alias `:with` option' do
78
+ @session.choose('form[gender]', with: 'male')
79
+ @session.click_button('awesome')
80
+ expect(extract_results(@session)['gender']).to eq('male')
81
+ end
82
+
77
83
  it 'should raise an error if option not found' do
78
84
  expect do
79
85
  @session.choose('form[gender]', option: 'hermaphrodite')
@@ -0,0 +1,44 @@
1
+ # frozen_string_literal: true
2
+
3
+ Capybara::SpecHelper.spec '#have_ancestor' do
4
+ before do
5
+ @session.visit('/with_html')
6
+ end
7
+
8
+ it 'should assert an ancestor using the given locator' do
9
+ el = @session.find(:css, '#ancestor1')
10
+ expect(el).to have_ancestor(:css, '#ancestor2')
11
+ end
12
+
13
+ it 'should assert an ancestor even if not parent' do
14
+ el = @session.find(:css, '#child')
15
+ expect(el).to have_ancestor(:css, '#ancestor3')
16
+ end
17
+
18
+ it 'should not raise an error if there are multiple matches' do
19
+ el = @session.find(:css, '#child')
20
+ expect(el).to have_ancestor(:css, 'div')
21
+ end
22
+
23
+ it 'should allow counts to be specified' do
24
+ el = @session.find(:css, '#child')
25
+
26
+ expect do
27
+ expect(el).to have_ancestor(:css, 'div').once
28
+ end.to raise_error(RSpec::Expectations::ExpectationNotMetError)
29
+
30
+ expect(el).to have_ancestor(:css, 'div').exactly(3).times
31
+ end
32
+ end
33
+
34
+ Capybara::SpecHelper.spec '#have_no_ancestor' do
35
+ before do
36
+ @session.visit('/with_html')
37
+ end
38
+
39
+ it 'should assert no matching ancestor' do
40
+ el = @session.find(:css, '#ancestor1')
41
+ expect(el).to have_no_ancestor(:css, '#child')
42
+ expect(el).not_to have_ancestor(:css, '#child')
43
+ end
44
+ end
@@ -0,0 +1,50 @@
1
+ # frozen_string_literal: true
2
+
3
+ Capybara::SpecHelper.spec '#have_sibling' do
4
+ before do
5
+ @session.visit('/with_html')
6
+ end
7
+
8
+ it 'should assert a prior sibling element using the given locator' do
9
+ el = @session.find(:css, '#mid_sibling')
10
+ expect(el).to have_sibling(:css, '#pre_sibling')
11
+ end
12
+
13
+ it 'should assert a following sibling element using the given locator' do
14
+ el = @session.find(:css, '#mid_sibling')
15
+ expect(el).to have_sibling(:css, '#post_sibling')
16
+ end
17
+
18
+ it 'should not raise an error if there are multiple matches' do
19
+ el = @session.find(:css, '#mid_sibling')
20
+ expect(el).to have_sibling(:css, 'div')
21
+ end
22
+
23
+ it 'should allow counts to be specified' do
24
+ el = @session.find(:css, '#mid_sibling')
25
+
26
+ expect(el).to have_sibling(:css, 'div').exactly(2).times
27
+ expect do
28
+ expect(el).to have_sibling(:css, 'div').once
29
+ end.to raise_error(RSpec::Expectations::ExpectationNotMetError)
30
+ end
31
+ end
32
+
33
+ Capybara::SpecHelper.spec '#have_no_sibling' do
34
+ before do
35
+ @session.visit('/with_html')
36
+ end
37
+
38
+ it 'should assert no matching sibling' do
39
+ el = @session.find(:css, '#mid_sibling')
40
+ expect(el).to have_no_sibling(:css, '#not_a_sibling')
41
+ expect(el).not_to have_sibling(:css, '#not_a_sibling')
42
+ end
43
+
44
+ it 'should raise if there are matching siblings' do
45
+ el = @session.find(:css, '#mid_sibling')
46
+ expect do
47
+ expect(el).to have_no_sibling(:css, '#pre_sibling')
48
+ end.to raise_error(RSpec::Expectations::ExpectationNotMetError)
49
+ end
50
+ end
@@ -42,13 +42,13 @@ Capybara::SpecHelper.spec '#select' do
42
42
  end
43
43
 
44
44
  it 'should select an option from a select box by id' do
45
- @session.select('Finish', from: 'form_locale')
45
+ @session.select('Finnish', from: 'form_locale')
46
46
  @session.click_button('awesome')
47
47
  expect(extract_results(@session)['locale']).to eq('fi')
48
48
  end
49
49
 
50
50
  it 'should select an option from a select box by label' do
51
- @session.select('Finish', from: 'Locale')
51
+ @session.select('Finnish', from: 'Locale')
52
52
  @session.click_button('awesome')
53
53
  expect(extract_results(@session)['locale']).to eq('fi')
54
54
  end
@@ -183,7 +183,7 @@ Capybara::SpecHelper.spec '#select' do
183
183
  context 'with :exact option' do
184
184
  context 'when `false`' do
185
185
  it 'can match select box approximately' do
186
- @session.select('Finish', from: 'Loc', exact: false)
186
+ @session.select('Finnish', from: 'Loc', exact: false)
187
187
  @session.click_button('awesome')
188
188
  expect(extract_results(@session)['locale']).to eq('fi')
189
189
  end
@@ -204,13 +204,13 @@ Capybara::SpecHelper.spec '#select' do
204
204
  context 'when `true`' do
205
205
  it 'can match select box approximately' do
206
206
  expect do
207
- @session.select('Finish', from: 'Loc', exact: true)
207
+ @session.select('Finnish', from: 'Loc', exact: true)
208
208
  end.to raise_error(Capybara::ElementNotFound)
209
209
  end
210
210
 
211
211
  it 'can match option approximately' do
212
212
  expect do
213
- @session.select('Fin', from: 'Locale', exact: true)
213
+ @session.select('Fin', from: 'Locale', exact: true)
214
214
  end.to raise_error(Capybara::ElementNotFound)
215
215
  end
216
216
 
@@ -108,7 +108,7 @@
108
108
  <select name="form[locale]" id="form_locale">
109
109
  <option value="sv">Swedish</option>
110
110
  <option selected="selected" value="en">English</option>
111
- <option value="fi">Finish</option>
111
+ <option value="fi">Finnish</option>
112
112
  <option value="no">Norwegian</option>
113
113
  <option value="jo">John's made-up language</option>
114
114
  <option value="jbo"> Lojban </option>
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Capybara
4
- VERSION = '3.21.0'
4
+ VERSION = '3.22.0'
5
5
  end
@@ -2,7 +2,7 @@
2
2
 
3
3
  module Capybara
4
4
  ##
5
- # The Window class represents a browser window.
5
+ # The {Window} class represents a browser window.
6
6
  #
7
7
  # You can get an instance of the class by calling either of:
8
8
  #
@@ -12,12 +12,12 @@ module Capybara
12
12
  # * {Capybara::Session#switch_to_window}
13
13
  #
14
14
  # Note that some drivers (e.g. Selenium) support getting size of/resizing/closing only
15
- # current window. So if you invoke such method for:
15
+ # current window. So if you invoke such method for:
16
16
  #
17
- # * window that is current, Capybara will make 2 Selenium method invocations
18
- # (get handle of current window + get size/resize/close).
19
- # * window that is not current, Capybara will make 4 Selenium method invocations
20
- # (get handle of current window + switch to given handle + get size/resize/close + switch to original handle)
17
+ # * window that is current, Capybara will make 2 Selenium method invocations
18
+ # (get handle of current window + get size/resize/close).
19
+ # * window that is not current, Capybara will make 4 Selenium method invocations
20
+ # (get handle of current window + switch to given handle + get size/resize/close + switch to original handle)
21
21
  #
22
22
  class Window
23
23
  # @return [String] a string that uniquely identifies window within session
@@ -57,12 +57,12 @@ module Capybara
57
57
  # Close window.
58
58
  #
59
59
  # If this method was called for window that is current, then after calling this method
60
- # future invocations of other Capybara methods should raise
61
- # `session.driver.no_such_window_error` until another window will be switched to.
60
+ # future invocations of other Capybara methods should raise
61
+ # {Capybara::Driver::Base#no_such_window_error session.driver.no_such_window_error} until another window will be switched to.
62
62
  #
63
63
  # @!macro about_current
64
64
  # If this method was called for window that is not current, then after calling this method
65
- # current window shouldn remain the same as it was before calling this method.
65
+ # current window should remain the same as it was before calling this method.
66
66
  #
67
67
  def close
68
68
  @driver.close_window(handle)
@@ -93,7 +93,7 @@ module Capybara
93
93
  # Maximize window.
94
94
  #
95
95
  # If a particular driver (e.g. headless driver) doesn't have concept of maximizing it
96
- # may not support this method.
96
+ # may not support this method.
97
97
  #
98
98
  # @macro about_current
99
99
  #
@@ -130,6 +130,16 @@ class MinitestTest < Minitest::Test
130
130
  visit('/with_html')
131
131
  assert_matches_style(find(:css, '#second'), display: 'inline')
132
132
  end
133
+
134
+ def test_assert_ancestor
135
+ option = find(:option, 'Finnish')
136
+ assert_ancestor(option, :css, '#form_locale')
137
+ end
138
+
139
+ def test_assert_sibling
140
+ option = find(:css, '#form_title').find(:option, 'Mrs')
141
+ assert_sibling(option, :option, 'Mr')
142
+ end
133
143
  end
134
144
 
135
145
  RSpec.describe 'capybara/minitest' do
@@ -148,6 +158,6 @@ RSpec.describe 'capybara/minitest' do
148
158
  reporter.start
149
159
  MinitestTest.run reporter, {}
150
160
  reporter.report
151
- expect(output.string).to include('20 runs, 50 assertions, 0 failures, 0 errors, 1 skips')
161
+ expect(output.string).to include('22 runs, 52 assertions, 0 failures, 0 errors, 1 skips')
152
162
  end
153
163
  end
@@ -127,6 +127,16 @@ class MinitestSpecTest < Minitest::Spec
127
127
  find(:css, '#second').must_have_style('display' => 'inline') # deprecated
128
128
  find(:css, '#second').must_match_style('display' => 'inline')
129
129
  end
130
+
131
+ it 'supports ancestor expectations' do
132
+ option = find(:option, 'Finnish')
133
+ option.must_have_ancestor(:css, '#form_locale')
134
+ end
135
+
136
+ it 'supports sibling expectations' do
137
+ option = find(:css, '#form_title').find(:option, 'Mrs')
138
+ option.must_have_sibling(:option, 'Mr')
139
+ end
130
140
  end
131
141
 
132
142
  RSpec.describe 'capybara/minitest/spec' do
@@ -145,7 +155,7 @@ RSpec.describe 'capybara/minitest/spec' do
145
155
  reporter.start
146
156
  MinitestSpecTest.run reporter, {}
147
157
  reporter.report
148
- expect(output.string).to include('20 runs, 42 assertions, 1 failures, 0 errors, 1 skips')
158
+ expect(output.string).to include('22 runs, 44 assertions, 1 failures, 0 errors, 1 skips')
149
159
  # Make sure error messages are displayed
150
160
  expect(output.string).to match(/expected to find select box "non_existing_form_title" .*but there were no matches/)
151
161
  end
@@ -2,7 +2,7 @@
2
2
 
3
3
  require 'spec_helper'
4
4
 
5
- RSpec.describe Capybara::Selector::RegexpDisassembler do
5
+ RSpec.describe Capybara::Selector::RegexpDisassembler, :aggregate_failures do
6
6
  it 'handles strings' do
7
7
  verify_strings(
8
8
  /abcdef/ => %w[abcdef],
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: capybara
3
3
  version: !ruby/object:Gem::Version
4
- version: 3.21.0
4
+ version: 3.22.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Thomas Walpole
@@ -10,7 +10,7 @@ autorequire:
10
10
  bindir: bin
11
11
  cert_chain:
12
12
  - gem-public_cert.pem
13
- date: 2019-05-24 00:00:00.000000000 Z
13
+ date: 2019-05-29 00:00:00.000000000 Z
14
14
  dependencies:
15
15
  - !ruby/object:Gem::Dependency
16
16
  name: addressable
@@ -413,6 +413,7 @@ executables: []
413
413
  extensions: []
414
414
  extra_rdoc_files: []
415
415
  files:
416
+ - ".yardopts"
416
417
  - History.md
417
418
  - License.txt
418
419
  - README.md
@@ -460,8 +461,10 @@ files:
460
461
  - lib/capybara/rspec/matchers/become_closed.rb
461
462
  - lib/capybara/rspec/matchers/compound.rb
462
463
  - lib/capybara/rspec/matchers/count_sugar.rb
464
+ - lib/capybara/rspec/matchers/have_ancestor.rb
463
465
  - lib/capybara/rspec/matchers/have_current_path.rb
464
466
  - lib/capybara/rspec/matchers/have_selector.rb
467
+ - lib/capybara/rspec/matchers/have_sibling.rb
465
468
  - lib/capybara/rspec/matchers/have_text.rb
466
469
  - lib/capybara/rspec/matchers/have_title.rb
467
470
  - lib/capybara/rspec/matchers/match_selector.rb
@@ -579,6 +582,7 @@ files:
579
582
  - lib/capybara/spec/session/go_back_spec.rb
580
583
  - lib/capybara/spec/session/go_forward_spec.rb
581
584
  - lib/capybara/spec/session/has_all_selectors_spec.rb
585
+ - lib/capybara/spec/session/has_ancestor_spec.rb
582
586
  - lib/capybara/spec/session/has_any_selectors_spec.rb
583
587
  - lib/capybara/spec/session/has_button_spec.rb
584
588
  - lib/capybara/spec/session/has_css_spec.rb
@@ -588,6 +592,7 @@ files:
588
592
  - lib/capybara/spec/session/has_none_selectors_spec.rb
589
593
  - lib/capybara/spec/session/has_select_spec.rb
590
594
  - lib/capybara/spec/session/has_selector_spec.rb
595
+ - lib/capybara/spec/session/has_sibling_spec.rb
591
596
  - lib/capybara/spec/session/has_table_spec.rb
592
597
  - lib/capybara/spec/session/has_text_spec.rb
593
598
  - lib/capybara/spec/session/has_title_spec.rb