page_magic 2.0.0.alpha1 → 2.0.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 (90) hide show
  1. checksums.yaml +4 -4
  2. data/.rubocop.yml +5 -2
  3. data/.zsh_config +5 -5
  4. data/Dockerfile +2 -1
  5. data/Gemfile +2 -1
  6. data/Gemfile.lock +9 -5
  7. data/Makefile +7 -3
  8. data/README.md +16 -4
  9. data/VERSION +1 -1
  10. data/lib/active_support/core_ext/object/to_query.rb +6 -6
  11. data/lib/page_magic.rb +15 -16
  12. data/lib/page_magic/class_methods.rb +1 -1
  13. data/lib/page_magic/comparator.rb +37 -0
  14. data/lib/page_magic/comparator/fuzzy.rb +23 -0
  15. data/lib/page_magic/comparator/literal.rb +22 -0
  16. data/lib/page_magic/comparator/null.rb +26 -0
  17. data/lib/page_magic/comparator/parameter_map.rb +52 -0
  18. data/lib/page_magic/drivers.rb +2 -2
  19. data/lib/page_magic/element.rb +19 -8
  20. data/lib/page_magic/element/locators.rb +4 -4
  21. data/lib/page_magic/element/not_found.rb +38 -0
  22. data/lib/page_magic/element/query.rb +19 -27
  23. data/lib/page_magic/element/query/multiple_results.rb +21 -0
  24. data/lib/page_magic/element/query/prefetched_result.rb +26 -0
  25. data/lib/page_magic/element/query/single_result.rb +20 -0
  26. data/lib/page_magic/element/selector.rb +38 -16
  27. data/lib/page_magic/element/selector/methods.rb +18 -0
  28. data/lib/page_magic/element/selector/model.rb +21 -0
  29. data/lib/page_magic/element_context.rb +5 -21
  30. data/lib/page_magic/element_definition_builder.rb +17 -24
  31. data/lib/page_magic/elements.rb +62 -102
  32. data/lib/page_magic/elements/config.rb +103 -0
  33. data/lib/page_magic/elements/inheritance_hooks.rb +15 -0
  34. data/lib/page_magic/elements/types.rb +25 -0
  35. data/lib/page_magic/exceptions.rb +3 -0
  36. data/lib/page_magic/instance_methods.rb +2 -2
  37. data/lib/page_magic/mapping.rb +79 -0
  38. data/lib/page_magic/session.rb +10 -32
  39. data/lib/page_magic/session_methods.rb +1 -1
  40. data/lib/page_magic/transitions.rb +49 -0
  41. data/lib/page_magic/utils/string.rb +4 -0
  42. data/lib/page_magic/utils/url.rb +20 -0
  43. data/lib/page_magic/watcher.rb +10 -17
  44. data/lib/page_magic/watchers.rb +28 -15
  45. data/spec/page_magic/class_methods_spec.rb +64 -37
  46. data/spec/page_magic/comparator/fuzzy_spec.rb +44 -0
  47. data/spec/page_magic/comparator/literal_spec.rb +41 -0
  48. data/spec/page_magic/comparator/null_spec.rb +35 -0
  49. data/spec/page_magic/comparator/parameter_map_spec.rb +75 -0
  50. data/spec/page_magic/driver_spec.rb +25 -29
  51. data/spec/page_magic/drivers/poltergeist_spec.rb +4 -7
  52. data/spec/page_magic/drivers/rack_test_spec.rb +4 -9
  53. data/spec/page_magic/drivers/selenium_spec.rb +9 -12
  54. data/spec/page_magic/drivers_spec.rb +36 -29
  55. data/spec/page_magic/element/locators_spec.rb +26 -25
  56. data/spec/page_magic/element/not_found_spec.rb +24 -0
  57. data/spec/page_magic/element/query/multiple_results_spec.rb +14 -0
  58. data/spec/page_magic/element/query/single_result_spec.rb +21 -0
  59. data/spec/page_magic/element/query_spec.rb +26 -47
  60. data/spec/page_magic/element/selector_spec.rb +118 -110
  61. data/spec/page_magic/element_context_spec.rb +46 -88
  62. data/spec/page_magic/element_definition_builder_spec.rb +12 -71
  63. data/spec/page_magic/element_spec.rb +256 -0
  64. data/spec/page_magic/elements/config_spec.rb +200 -0
  65. data/spec/page_magic/elements_spec.rb +87 -138
  66. data/spec/page_magic/instance_methods_spec.rb +63 -63
  67. data/spec/page_magic/mapping_spec.rb +181 -0
  68. data/spec/page_magic/session_methods_spec.rb +27 -25
  69. data/spec/page_magic/session_spec.rb +109 -198
  70. data/spec/page_magic/transitions_spec.rb +43 -0
  71. data/spec/page_magic/utils/string_spec.rb +20 -27
  72. data/spec/page_magic/utils/url_spec.rb +9 -0
  73. data/spec/page_magic/wait_methods_spec.rb +14 -22
  74. data/spec/page_magic/watcher_spec.rb +22 -0
  75. data/spec/page_magic/watchers_spec.rb +56 -62
  76. data/spec/page_magic_spec.rb +27 -24
  77. data/spec/spec_helper.rb +7 -3
  78. data/spec/support/shared_examples.rb +15 -17
  79. metadata +48 -15
  80. data/lib/page_magic/element/query_builder.rb +0 -61
  81. data/lib/page_magic/element/selector_methods.rb +0 -16
  82. data/lib/page_magic/matcher.rb +0 -130
  83. data/spec/element_spec.rb +0 -251
  84. data/spec/page_magic/element/query_builder_spec.rb +0 -110
  85. data/spec/page_magic/matcher_spec.rb +0 -338
  86. data/spec/support/shared_contexts/files_context.rb +0 -9
  87. data/spec/support/shared_contexts/nested_elements_html_context.rb +0 -18
  88. data/spec/support/shared_contexts/rack_application_context.rb +0 -11
  89. data/spec/support/shared_contexts/webapp_fixture_context.rb +0 -41
  90. data/spec/watcher_spec.rb +0 -64
@@ -0,0 +1,41 @@
1
+ RSpec.describe PageMagic::Comparator::Literal do
2
+ describe 'match?' do
3
+ context 'when parameter is the same' do
4
+ it 'returns true' do
5
+ expect(described_class.new('/')).to be_match('/')
6
+ end
7
+ end
8
+
9
+ context 'when it parameter is not the same' do
10
+ it 'returns false' do
11
+ expect(described_class.new('/')).not_to be_match('foo')
12
+ end
13
+ end
14
+ end
15
+
16
+ describe '#fuzzy?' do
17
+ it 'returns false' do
18
+ expect(described_class.new('value')).not_to be_fuzzy
19
+ end
20
+ end
21
+
22
+ describe '#<=>' do
23
+ context 'when other is `Null`' do
24
+ it 'is greater' do
25
+ expect(described_class.new('/') <=> PageMagic::Comparator::Null.new).to be 1
26
+ end
27
+ end
28
+
29
+ context 'when other is `Fuzzy`' do
30
+ it 'is greater' do
31
+ expect(described_class.new('/') <=> PageMagic::Comparator::Fuzzy.new(//)).to be 1
32
+ end
33
+ end
34
+
35
+ context 'when other is `Literal`' do
36
+ it 'is equal' do
37
+ expect(described_class.new('/') <=> described_class.new('/')).to be 0
38
+ end
39
+ end
40
+ end
41
+ end
@@ -0,0 +1,35 @@
1
+ RSpec.describe PageMagic::Comparator::Null do
2
+ describe '#fuzzy?' do
3
+ context 'when one value is fuzzy' do
4
+ it 'returns true' do
5
+ expect(described_class.new).not_to be_fuzzy
6
+ end
7
+ end
8
+ end
9
+
10
+ describe 'match?' do
11
+ it 'returns false' do
12
+ expect(described_class.new).to be_match(true)
13
+ end
14
+ end
15
+
16
+ describe '#<=>' do
17
+ context 'when other is `Null`' do
18
+ it 'is equal' do
19
+ expect(described_class.new <=> described_class.new).to be 0
20
+ end
21
+ end
22
+
23
+ context 'when other is `Fuzzy`' do
24
+ it 'is greater' do
25
+ expect(described_class.new <=> PageMagic::Comparator::Fuzzy.new(//)).to be 1
26
+ end
27
+ end
28
+
29
+ context 'when other is `Literal`' do
30
+ it 'is greater' do
31
+ expect(described_class.new <=> PageMagic::Comparator::Literal.new('/')).to be 1
32
+ end
33
+ end
34
+ end
35
+ end
@@ -0,0 +1,75 @@
1
+ RSpec.describe PageMagic::Comparator::ParameterMap do
2
+ describe '#fuzzy?' do
3
+ context 'when one value is fuzzy' do
4
+ it 'returns true' do
5
+ map = described_class.new({ param1: //, param2: '' })
6
+ expect(map).to be_fuzzy
7
+ end
8
+ end
9
+
10
+ context 'when all values are literal' do
11
+ it 'returns true' do
12
+ map = described_class.new({ param1: '', param2: '' })
13
+ expect(map).not_to be_fuzzy
14
+ end
15
+ end
16
+ end
17
+
18
+ describe '#match?' do
19
+ context 'when param has compatible params' do
20
+ it 'returns true' do
21
+ expect(described_class.new({ param: '1' })).to be_match(param: '1')
22
+ end
23
+ end
24
+
25
+ context 'when it does not have compatible params' do
26
+ it 'returns false' do
27
+ expect(described_class.new({ param: '1' })).not_to be_match(param: '2')
28
+ end
29
+ end
30
+
31
+ context 'when it does not meet all of the requirements' do
32
+ it 'returns false' do
33
+ expect(described_class.new({ param: '1', another_param: '2' })).not_to be_match(param: '1')
34
+ end
35
+ end
36
+ end
37
+
38
+ describe '#<=>' do
39
+ context 'when other is empty' do
40
+ context 'and self is empty' do
41
+ it 'is equal' do
42
+ expect(described_class.new({}) <=> described_class.new({})).to be 0
43
+ end
44
+ end
45
+
46
+ context 'self is not empty' do
47
+ it 'is greater' do
48
+ expect(described_class.new({ param: 1 }) <=> described_class.new({})).to be 1
49
+ end
50
+ end
51
+ end
52
+
53
+ context 'when other contains matchers' do
54
+ context 'when other has the same number' do
55
+ context 'and matchers are of the same type' do
56
+ it 'is equal' do
57
+ expect(described_class.new({ param: // }) <=> described_class.new({ param: // })).to be 0
58
+ end
59
+ end
60
+
61
+ context 'and has less literal matchers' do
62
+ it 'is lesser' do
63
+ expect(described_class.new({ param: '' }) <=> described_class.new({ param: // })).to be 1
64
+ end
65
+ end
66
+ end
67
+
68
+ context 'when other has the less' do
69
+ it 'is lesser' do
70
+ expect(described_class.new({ param: // }) <=> described_class.new({})).to be 1
71
+ end
72
+ end
73
+ end
74
+ end
75
+ end
@@ -1,43 +1,39 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'page_magic/driver'
4
-
5
- module PageMagic
6
- describe Driver do
7
- subject do
8
- described_class.new :custom_browser
3
+ RSpec.describe PageMagic::Driver do
4
+ describe '#build' do
5
+ it 'returns the result of the block passed to the driver class constructor' do
6
+ subject = described_class.new(:custom_browser) do
7
+ :driver
8
+ end
9
+ expect(subject.build(:rack_app, browser: :custom_browser, options: {})).to eq(:driver)
9
10
  end
10
11
 
11
- describe '#build' do
12
- it 'returns the result of the block passed to the driver class constructor' do
13
- subject = described_class.new(:custom_browser) do
14
- :driver
15
- end
16
- expect(subject.build(:rack_app, browser: :custom_browser, options: :options)).to eq(:driver)
12
+ it 'passes rack app to the handler' do
13
+ subject = described_class.new(:custom_browser) do |app, options, browser|
14
+ expect(app).to eq(:rack_app)
15
+ expect(options).to eq(:options)
16
+ expect(browser).to eq(:browser)
17
17
  end
18
18
 
19
- it 'passes rack app to the handler' do
20
- subject = described_class.new(:custom_browser) do |app, options, browser|
21
- expect(app).to eq(:rack_app)
22
- expect(options).to eq(:options)
23
- expect(browser).to eq(:browser)
24
- end
19
+ subject.build(:rack_app, options: :options, browser: :browser)
20
+ end
21
+ end
25
22
 
26
- subject.build(:rack_app, options: :options, browser: :browser)
27
- end
23
+ describe '#supports?' do
24
+ subject do
25
+ described_class.new :custom_browser
28
26
  end
29
27
 
30
- describe '#supports?' do
31
- context 'browser is in supported browsers' do
32
- it 'returns true' do
33
- expect(subject.support?(:custom_browser)).to eq(true)
34
- end
28
+ context 'browser is in supported browsers' do
29
+ it 'returns true' do
30
+ expect(subject.support?(:custom_browser)).to eq(true)
35
31
  end
32
+ end
36
33
 
37
- context 'browser is not in supported browsers' do
38
- it 'returns false' do
39
- expect(subject.support?(:unsupported_browser)).to eq(false)
40
- end
34
+ context 'browser is not in supported browsers' do
35
+ it 'returns false' do
36
+ expect(subject.support?(:unsupported_browser)).to eq(false)
41
37
  end
42
38
  end
43
39
  end
@@ -1,11 +1,8 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'page_magic/drivers/poltergeist'
4
- module PageMagic
5
- describe Drivers::Poltergeist do
6
- it "is capybara's poltergeist driver" do
7
- driver = described_class.build(:app, browser: :poltergeist, options: {})
8
- expect(driver).to be_a(Capybara::Poltergeist::Driver)
9
- end
3
+ RSpec.describe PageMagic::Drivers::Poltergeist do
4
+ it "is capybara's poltergeist driver" do
5
+ driver = described_class.build(:app, browser: :poltergeist, options: {})
6
+ expect(driver).to be_a(Capybara::Poltergeist::Driver)
10
7
  end
11
8
  end
@@ -1,13 +1,8 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'page_magic/drivers/rack_test'
4
- module PageMagic
5
- class Drivers
6
- describe RackTest do
7
- it "is capybara's rack test driver" do
8
- driver = described_class.build(:app, browser: :rack_test, options: {})
9
- expect(driver).to be_a(Capybara::RackTest::Driver)
10
- end
11
- end
3
+ RSpec.describe PageMagic::Drivers::RackTest do
4
+ it "is capybara's rack test driver" do
5
+ driver = described_class.build(:app, browser: :rack_test, options: {})
6
+ expect(driver).to be_a(Capybara::RackTest::Driver)
12
7
  end
13
8
  end
@@ -1,18 +1,15 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'page_magic/drivers/selenium'
4
- module PageMagic
5
- describe Drivers::Selenium do
6
- subject do
7
- described_class.build(:app, browser: :selenium, options: {})
8
- end
3
+ RSpec.describe PageMagic::Drivers::Selenium do
4
+ subject do
5
+ described_class.build(:app, browser: :selenium, options: {})
6
+ end
9
7
 
10
- it 'is selenium' do
11
- expect(subject).to be_a(Capybara::Selenium::Driver)
12
- end
8
+ it 'is selenium' do
9
+ expect(subject).to be_a(Capybara::Selenium::Driver)
10
+ end
13
11
 
14
- it 'sets the browser option' do
15
- expect(subject.options[:browser]).to be(:selenium)
16
- end
12
+ it 'sets the browser option' do
13
+ expect(subject.options[:browser]).to be(:selenium)
17
14
  end
18
15
  end
@@ -1,41 +1,48 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'page_magic/drivers'
4
- module PageMagic
5
- describe Drivers do
6
- subject { described_class.new }
7
- let(:expected_driver) { Driver.new(:browser_driver) }
8
-
9
- describe '#find' do
10
- it 'returns the registered driver' do
11
- subject.register expected_driver
12
- expect(subject.find(:browser_driver)).to eq(expected_driver)
13
- end
3
+ RSpec.describe PageMagic::Drivers do
4
+ describe '#find' do
5
+ it 'returns the registered driver' do
6
+ drivers = described_class.new
7
+ expected_driver = PageMagic::Driver.new(:browser_driver)
8
+
9
+ drivers.register expected_driver
10
+ expect(drivers.find(:browser_driver)).to eq(expected_driver)
14
11
  end
12
+ end
15
13
 
16
- describe '#load' do
17
- include_context :files
18
- it 'loads the drivers in the specified path' do
19
- class_definition = <<-RUBY
20
- class CustomDriver;
21
- def self.support? browser
22
- true
23
- end
14
+ describe '#load' do
15
+ require 'tmpdir'
16
+
17
+ def scratch_dir
18
+ @scratch_dir ||= Dir.mktmpdir
19
+ end
20
+
21
+ let(:class_definition) do
22
+ <<-RUBY
23
+ class CustomDriver;
24
+ def self.support?(_browser)
25
+ true
24
26
  end
25
- RUBY
27
+ end
28
+ RUBY
29
+ end
26
30
 
27
- File.write("#{scratch_dir}/custom_driver.rb", class_definition)
31
+ it 'loads the drivers in the specified path' do
32
+ File.write("#{scratch_dir}/custom_driver.rb", class_definition)
28
33
 
29
- subject.load(scratch_dir)
30
- expect(subject.find(:custom_browser)).to be(::CustomDriver)
31
- end
34
+ drivers = described_class.new
35
+ drivers.load(scratch_dir)
36
+ expect(drivers.find(:custom_browser)).to be(::CustomDriver)
32
37
  end
38
+ end
33
39
 
34
- describe '#register' do
35
- it 'stores the driver' do
36
- subject.register expected_driver
37
- expect(subject.all).to eq([expected_driver])
38
- end
40
+ describe '#register' do
41
+ it 'stores the driver' do
42
+ drivers = described_class.new
43
+ expected_driver = PageMagic::Driver.new(:browser_driver)
44
+ drivers.register expected_driver
45
+ expect(drivers.all).to eq([expected_driver])
39
46
  end
40
47
  end
41
48
  end
@@ -1,34 +1,35 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- module PageMagic
4
- class Element
5
- describe Locators do
6
- subject(:element_clazz) do
7
- Class.new do
8
- extend(Elements)
9
- include(Locators)
10
- end
11
- end
12
- subject { element_clazz.new }
3
+ RSpec.describe PageMagic::Element::Locators do
4
+ subject { element_clazz.new }
13
5
 
14
- describe '#element_by_name' do
15
- it 'returns the required element' do
16
- selector = { id: 'child' }
17
- element_clazz.element :child1, selector
18
- element_clazz.element :child2, id: 'child 2'
6
+ let(:element_clazz) do
7
+ Class.new do
8
+ extend(PageMagic::Elements)
9
+ include(PageMagic::Element::Locators)
10
+ end
11
+ end
19
12
 
20
- expected_builder = ElementDefinitionBuilder.new(definition_class: Element, type: :element, selector: selector)
13
+ describe '#element_by_name' do
14
+ it 'returns the required element' do
15
+ selector = { id: 'child' }
16
+ element_clazz.element :child1, selector
17
+ element_clazz.element :child2, id: 'child 2'
21
18
 
22
- expect(subject.element_by_name(:child1)).to eq(expected_builder)
23
- end
19
+ child_1_builder = PageMagic::ElementDefinitionBuilder.new(
20
+ definition_class: PageMagic::Element,
21
+ selector: PageMagic::Element::Selector.find(:id).build(:element, 'child')
22
+ )
23
+
24
+ expect(subject.element_by_name(:child1)).to eq(child_1_builder)
25
+ end
24
26
 
25
- context 'element not found' do
26
- it 'raises an error' do
27
- expected_message = (described_class::ELEMENT_NOT_DEFINED_MSG % :child)
28
- command = proc { subject.element_by_name(:child) }
29
- expect(&command).to raise_exception ElementMissingException, expected_message
30
- end
31
- end
27
+ context 'element not found' do
28
+ it 'raises an error' do
29
+ expected_message = (described_class::ELEMENT_NOT_DEFINED_MSG % :child)
30
+ expect do
31
+ subject.element_by_name(:child)
32
+ end.to raise_exception PageMagic::ElementMissingException, expected_message
32
33
  end
33
34
  end
34
35
  end
@@ -0,0 +1,24 @@
1
+ # frozen_string_literal: true
2
+
3
+ describe PageMagic::Element::NotFound do
4
+ describe '#method_missing' do
5
+ it 'raises an error' do
6
+ subject = described_class.new(Exception.new('message'))
7
+ expect { subject.any_missing_method }.to raise_exception(PageMagic::ElementMissingException, 'message')
8
+ end
9
+ end
10
+
11
+ describe '#visible?' do
12
+ it 'returns false' do
13
+ subject = described_class.new(Exception.new('message'))
14
+ expect(subject.visible?).to eq(false)
15
+ end
16
+ end
17
+
18
+ describe '#present?' do
19
+ it 'returns false' do
20
+ subject = described_class.new(Exception.new('message'))
21
+ expect(subject.present?).to eq(false)
22
+ end
23
+ end
24
+ end