selenium-webdriver 4.0.0.rc3 → 4.13.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (158) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGES +338 -0
  3. data/Gemfile +2 -0
  4. data/LICENSE +1 -1
  5. data/NOTICE +1 -1
  6. data/README.md +2 -2
  7. data/bin/linux/selenium-manager +0 -0
  8. data/bin/macos/selenium-manager +0 -0
  9. data/bin/windows/selenium-manager.exe +0 -0
  10. data/lib/selenium/server.rb +90 -79
  11. data/lib/selenium/webdriver/atoms/findElements.js +5 -6
  12. data/lib/selenium/webdriver/atoms/getAttribute.js +0 -0
  13. data/lib/selenium/webdriver/atoms/isDisplayed.js +0 -0
  14. data/lib/selenium/webdriver/atoms/mutationListener.js +0 -0
  15. data/lib/selenium/webdriver/atoms.rb +2 -3
  16. data/lib/selenium/webdriver/bidi/browsing_context.rb +88 -0
  17. data/lib/selenium/webdriver/bidi/browsing_context_info.rb +35 -0
  18. data/lib/selenium/webdriver/bidi/log/base_log_entry.rb +35 -0
  19. data/lib/selenium/webdriver/bidi/log/console_log_entry.rb +35 -0
  20. data/lib/selenium/webdriver/{common/driver_extensions/has_location.rb → bidi/log/filter_by.rb} +14 -11
  21. data/lib/selenium/webdriver/bidi/log/generic_log_entry.rb +33 -0
  22. data/lib/selenium/webdriver/bidi/log/javascript_log_entry.rb +33 -0
  23. data/lib/selenium/webdriver/bidi/log_inspector.rb +143 -0
  24. data/lib/selenium/webdriver/bidi/navigate_result.rb +33 -0
  25. data/lib/selenium/webdriver/bidi/session.rb +51 -0
  26. data/lib/selenium/webdriver/bidi.rb +56 -0
  27. data/lib/selenium/webdriver/chrome/driver.rb +9 -29
  28. data/lib/selenium/webdriver/chrome/features.rb +6 -68
  29. data/lib/selenium/webdriver/chrome/options.rb +3 -223
  30. data/lib/selenium/webdriver/chrome/profile.rb +3 -83
  31. data/lib/selenium/webdriver/chrome/service.rb +4 -19
  32. data/lib/selenium/webdriver/chrome.rb +0 -16
  33. data/lib/selenium/webdriver/chromium/driver.rb +60 -0
  34. data/lib/selenium/webdriver/chromium/features.rb +103 -0
  35. data/lib/selenium/webdriver/chromium/options.rb +243 -0
  36. data/lib/selenium/webdriver/chromium/profile.rb +113 -0
  37. data/lib/selenium/webdriver/chromium.rb +29 -0
  38. data/lib/selenium/webdriver/common/action_builder.rb +62 -22
  39. data/lib/selenium/webdriver/common/child_process.rb +124 -0
  40. data/lib/selenium/webdriver/common/driver.rb +31 -81
  41. data/lib/selenium/webdriver/common/driver_extensions/downloads_files.rb +0 -2
  42. data/lib/selenium/webdriver/common/driver_extensions/full_page_screenshot.rb +0 -1
  43. data/lib/selenium/webdriver/common/driver_extensions/has_addons.rb +0 -2
  44. data/lib/selenium/webdriver/common/driver_extensions/has_apple_permissions.rb +0 -2
  45. data/lib/selenium/webdriver/common/driver_extensions/has_authentication.rb +0 -2
  46. data/lib/selenium/webdriver/common/driver_extensions/{has_remote_status.rb → has_bidi.rb} +10 -5
  47. data/lib/selenium/webdriver/common/driver_extensions/has_casting.rb +10 -1
  48. data/lib/selenium/webdriver/common/driver_extensions/has_cdp.rb +0 -2
  49. data/lib/selenium/webdriver/common/driver_extensions/has_context.rb +1 -4
  50. data/lib/selenium/webdriver/common/driver_extensions/has_debugger.rb +0 -2
  51. data/lib/selenium/webdriver/common/driver_extensions/has_devtools.rb +0 -2
  52. data/lib/selenium/webdriver/common/driver_extensions/has_launching.rb +0 -2
  53. data/lib/selenium/webdriver/common/driver_extensions/has_log_events.rb +1 -2
  54. data/lib/selenium/webdriver/common/driver_extensions/has_network_conditions.rb +9 -2
  55. data/lib/selenium/webdriver/common/driver_extensions/has_network_interception.rb +2 -69
  56. data/lib/selenium/webdriver/common/driver_extensions/has_permissions.rb +0 -2
  57. data/lib/selenium/webdriver/common/driver_extensions/has_pinned_scripts.rb +1 -3
  58. data/lib/selenium/webdriver/common/driver_finder.rb +45 -0
  59. data/lib/selenium/webdriver/common/element.rb +8 -8
  60. data/lib/selenium/webdriver/common/error.rb +28 -5
  61. data/lib/selenium/webdriver/common/html5/shared_web_storage.rb +2 -2
  62. data/lib/selenium/webdriver/common/interactions/input_device.rb +10 -4
  63. data/lib/selenium/webdriver/common/interactions/interaction.rb +12 -25
  64. data/lib/selenium/webdriver/common/interactions/interactions.rb +24 -4
  65. data/lib/selenium/webdriver/common/interactions/key_actions.rb +5 -1
  66. data/lib/selenium/webdriver/common/interactions/key_input.rb +11 -27
  67. data/lib/selenium/webdriver/common/interactions/none_input.rb +10 -8
  68. data/lib/selenium/webdriver/common/interactions/pause.rb +49 -0
  69. data/lib/selenium/webdriver/common/interactions/pointer_actions.rb +59 -70
  70. data/lib/selenium/webdriver/common/{driver_extensions/has_network_connection.rb → interactions/pointer_cancel.rb} +19 -11
  71. data/lib/selenium/webdriver/common/interactions/pointer_event_properties.rb +63 -0
  72. data/lib/selenium/webdriver/common/interactions/pointer_input.rb +15 -84
  73. data/lib/selenium/webdriver/common/interactions/pointer_move.rb +60 -0
  74. data/lib/selenium/webdriver/common/interactions/pointer_press.rb +85 -0
  75. data/lib/selenium/webdriver/common/interactions/scroll.rb +59 -0
  76. data/lib/selenium/webdriver/common/interactions/scroll_origin.rb +48 -0
  77. data/lib/selenium/webdriver/common/interactions/typing_interaction.rb +54 -0
  78. data/lib/selenium/webdriver/common/interactions/wheel_actions.rb +113 -0
  79. data/lib/selenium/webdriver/common/interactions/wheel_input.rb +42 -0
  80. data/lib/selenium/webdriver/common/keys.rb +1 -0
  81. data/lib/selenium/webdriver/common/local_driver.rb +46 -0
  82. data/lib/selenium/webdriver/common/logger.rb +90 -25
  83. data/lib/selenium/webdriver/common/manager.rb +0 -27
  84. data/lib/selenium/webdriver/common/options.rb +14 -20
  85. data/lib/selenium/webdriver/common/platform.rb +5 -51
  86. data/lib/selenium/webdriver/common/port_prober.rb +1 -1
  87. data/lib/selenium/webdriver/common/profile_helper.rb +2 -8
  88. data/lib/selenium/webdriver/common/proxy.rb +2 -2
  89. data/lib/selenium/webdriver/common/search_context.rb +0 -6
  90. data/lib/selenium/webdriver/common/selenium_manager.rb +134 -0
  91. data/lib/selenium/webdriver/common/service.rb +21 -30
  92. data/lib/selenium/webdriver/common/service_manager.rb +8 -15
  93. data/lib/selenium/webdriver/common/shadow_root.rb +2 -3
  94. data/lib/selenium/webdriver/common/socket_lock.rb +3 -3
  95. data/lib/selenium/webdriver/common/socket_poller.rb +31 -20
  96. data/lib/selenium/webdriver/common/takes_screenshot.rb +2 -3
  97. data/lib/selenium/webdriver/common/target_locator.rb +2 -3
  98. data/lib/selenium/webdriver/common/timeouts.rb +2 -2
  99. data/lib/selenium/webdriver/common/virtual_authenticator/credential.rb +85 -0
  100. data/lib/selenium/webdriver/common/virtual_authenticator/virtual_authenticator.rb +72 -0
  101. data/lib/selenium/webdriver/common/virtual_authenticator/virtual_authenticator_options.rb +62 -0
  102. data/lib/selenium/webdriver/common/websocket_connection.rb +164 -0
  103. data/lib/selenium/webdriver/common/window.rb +6 -6
  104. data/lib/selenium/webdriver/common/zipper.rb +4 -10
  105. data/lib/selenium/webdriver/common.rb +21 -5
  106. data/lib/selenium/webdriver/devtools/console_event.rb +0 -2
  107. data/lib/selenium/webdriver/devtools/exception_event.rb +0 -2
  108. data/lib/selenium/webdriver/devtools/mutation_event.rb +0 -2
  109. data/lib/selenium/webdriver/devtools/network_interceptor.rb +173 -0
  110. data/lib/selenium/webdriver/devtools/pinned_script.rb +0 -2
  111. data/lib/selenium/webdriver/devtools/request.rb +1 -3
  112. data/lib/selenium/webdriver/devtools/response.rb +1 -3
  113. data/lib/selenium/webdriver/devtools.rb +17 -103
  114. data/lib/selenium/webdriver/edge/driver.rb +9 -3
  115. data/lib/selenium/webdriver/edge/features.rb +4 -4
  116. data/lib/selenium/webdriver/edge/options.rb +17 -5
  117. data/lib/selenium/webdriver/edge/profile.rb +2 -2
  118. data/lib/selenium/webdriver/edge/service.rb +8 -7
  119. data/lib/selenium/webdriver/edge.rb +0 -2
  120. data/lib/selenium/webdriver/firefox/driver.rb +9 -2
  121. data/lib/selenium/webdriver/firefox/features.rb +6 -6
  122. data/lib/selenium/webdriver/firefox/options.rb +9 -14
  123. data/lib/selenium/webdriver/firefox/profile.rb +8 -12
  124. data/lib/selenium/webdriver/firefox/service.rb +0 -18
  125. data/lib/selenium/webdriver/firefox/util.rb +46 -0
  126. data/lib/selenium/webdriver/firefox.rb +1 -14
  127. data/lib/selenium/webdriver/ie/driver.rb +7 -1
  128. data/lib/selenium/webdriver/ie/options.rb +2 -1
  129. data/lib/selenium/webdriver/ie/service.rb +0 -22
  130. data/lib/selenium/webdriver/ie.rb +0 -14
  131. data/lib/selenium/webdriver/remote/{commands.rb → bridge/commands.rb} +15 -8
  132. data/lib/selenium/webdriver/remote/bridge.rb +70 -37
  133. data/lib/selenium/webdriver/remote/capabilities.rb +3 -53
  134. data/lib/selenium/webdriver/remote/driver.rb +31 -14
  135. data/lib/selenium/webdriver/remote/http/common.rb +3 -3
  136. data/lib/selenium/webdriver/remote/http/curb.rb +1 -3
  137. data/lib/selenium/webdriver/remote/http/default.rb +8 -14
  138. data/lib/selenium/webdriver/remote/response.rb +2 -3
  139. data/lib/selenium/webdriver/remote/server_error.rb +1 -1
  140. data/lib/selenium/webdriver/remote.rb +5 -5
  141. data/lib/selenium/webdriver/safari/driver.rb +7 -1
  142. data/lib/selenium/webdriver/safari/features.rb +0 -2
  143. data/lib/selenium/webdriver/safari/options.rb +5 -1
  144. data/lib/selenium/webdriver/safari/service.rb +10 -4
  145. data/lib/selenium/webdriver/safari.rb +1 -15
  146. data/lib/selenium/webdriver/support/color.rb +22 -22
  147. data/lib/selenium/webdriver/support/guards/guard.rb +0 -2
  148. data/lib/selenium/webdriver/support/guards/guard_condition.rb +1 -3
  149. data/lib/selenium/webdriver/support/guards.rb +1 -1
  150. data/lib/selenium/webdriver/support/relative_locator.rb +0 -1
  151. data/lib/selenium/webdriver/support/select.rb +4 -2
  152. data/lib/selenium/webdriver/version.rb +1 -1
  153. data/lib/selenium/webdriver.rb +7 -5
  154. data/selenium-webdriver.gemspec +15 -13
  155. metadata +79 -65
  156. data/lib/selenium/webdriver/remote/http/persistent.rb +0 -65
  157. data/lib/selenium/webdriver/support/cdp/domain.rb.erb +0 -63
  158. data/lib/selenium/webdriver/support/cdp_client_generator.rb +0 -108
@@ -0,0 +1,48 @@
1
+ # frozen_string_literal: true
2
+
3
+ # Licensed to the Software Freedom Conservancy (SFC) under one
4
+ # or more contributor license agreements. See the NOTICE file
5
+ # distributed with this work for additional information
6
+ # regarding copyright ownership. The SFC licenses this file
7
+ # to you under the Apache License, Version 2.0 (the
8
+ # "License"); you may not use this file except in compliance
9
+ # with the License. You may obtain a copy of the License at
10
+ #
11
+ # http://www.apache.org/licenses/LICENSE-2.0
12
+ #
13
+ # Unless required by applicable law or agreed to in writing,
14
+ # software distributed under the License is distributed on an
15
+ # "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16
+ # KIND, either express or implied. See the License for the
17
+ # specific language governing permissions and limitations
18
+ # under the License.
19
+
20
+ module Selenium
21
+ module WebDriver
22
+ module WheelActions
23
+ class ScrollOrigin
24
+ class << self
25
+ def element(element, x_offset = 0, y_offset = 0)
26
+ new(element, x_offset, y_offset)
27
+ end
28
+
29
+ def viewport(x_offset = 0, y_offset = 0)
30
+ new(:viewport, x_offset, y_offset)
31
+ end
32
+ end
33
+
34
+ attr_reader :origin, :x_offset, :y_offset
35
+
36
+ #
37
+ # Use a static method to access
38
+ # @api private
39
+ #
40
+ def initialize(origin, x_offset, y_offset)
41
+ @origin = origin
42
+ @x_offset = x_offset
43
+ @y_offset = y_offset
44
+ end
45
+ end # ScrollOrigin
46
+ end # WheelActions
47
+ end # WebDriver
48
+ end # Selenium
@@ -0,0 +1,54 @@
1
+ # frozen_string_literal: true
2
+
3
+ # Licensed to the Software Freedom Conservancy (SFC) under one
4
+ # or more contributor license agreements. See the NOTICE file
5
+ # distributed with this work for additional information
6
+ # regarding copyright ownership. The SFC licenses this file
7
+ # to you under the Apache License, Version 2.0 (the
8
+ # "License"); you may not use this file except in compliance
9
+ # with the License. You may obtain a copy of the License at
10
+ #
11
+ # http://www.apache.org/licenses/LICENSE-2.0
12
+ #
13
+ # Unless required by applicable law or agreed to in writing,
14
+ # software distributed under the License is distributed on an
15
+ # "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16
+ # KIND, either express or implied. See the License for the
17
+ # specific language governing permissions and limitations
18
+ # under the License.
19
+
20
+ module Selenium
21
+ module WebDriver
22
+ module Interactions
23
+ #
24
+ # Actions related to pressing keys.
25
+ #
26
+ # @api private
27
+ #
28
+
29
+ class TypingInteraction < Interaction
30
+ attr_reader :type
31
+
32
+ def initialize(source, type, key)
33
+ super(source)
34
+ @type = assert_type(type)
35
+ @key = Keys.encode_key(key)
36
+ end
37
+
38
+ def assert_source(source)
39
+ raise TypeError, "#{source.type} is not a valid input type" unless source.is_a? KeyInput
40
+ end
41
+
42
+ def assert_type(type)
43
+ raise TypeError, "#{type.inspect} is not a valid key subtype" unless KeyInput::SUBTYPES.key? type
44
+
45
+ KeyInput::SUBTYPES[type]
46
+ end
47
+
48
+ def encode
49
+ {type: @type, value: @key}
50
+ end
51
+ end # TypingInteraction
52
+ end # Interactions
53
+ end # WebDriver
54
+ end # Selenium
@@ -0,0 +1,113 @@
1
+ # frozen_string_literal: true
2
+
3
+ # Licensed to the Software Freedom Conservancy (SFC) under one
4
+ # or more contributor license agreements. See the NOTICE file
5
+ # distributed with this work for additional information
6
+ # regarding copyright ownership. The SFC licenses this file
7
+ # to you under the Apache License, Version 2.0 (the
8
+ # "License"); you may not use this file except in compliance
9
+ # with the License. You may obtain a copy of the License at
10
+ #
11
+ # http://www.apache.org/licenses/LICENSE-2.0
12
+ #
13
+ # Unless required by applicable law or agreed to in writing,
14
+ # software distributed under the License is distributed on an
15
+ # "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16
+ # KIND, either express or implied. See the License for the
17
+ # specific language governing permissions and limitations
18
+ # under the License.
19
+
20
+ module Selenium
21
+ module WebDriver
22
+ module WheelActions
23
+ attr_writer :default_scroll_duration
24
+
25
+ #
26
+ # By default this is set to 250ms in the ActionBuilder constructor
27
+ # It can be overridden with default_scroll_duration=
28
+ #
29
+
30
+ def default_scroll_duration
31
+ @default_scroll_duration ||= @duration / 1000.0 # convert ms to seconds
32
+ end
33
+
34
+ #
35
+ # If the element is outside the viewport, scrolls the bottom of the element to the bottom of the viewport.
36
+ #
37
+ # @example Scroll to element
38
+ # el = driver.find_element(id: "some_id")
39
+ # driver.action.scroll_to(element).perform
40
+ #
41
+ # @param [Object] Which element to scroll into the viewport.
42
+ # @return [Selenium::WebDriver::WheelActions] A self reference.
43
+ def scroll_to(element, device: nil)
44
+ scroll(origin: element, device: device)
45
+ end
46
+
47
+ #
48
+ # Scrolls by provided amounts with the origin in the top left corner of the viewport.
49
+ #
50
+ # @example Scroll viewport by a specified amount
51
+ # el = driver.find_element(id: "some_id")
52
+ # driver.action.scroll_by(100, 200).perform
53
+ #
54
+ # @param [Integer] delta_x Distance along X axis to scroll using the wheel. A negative value scrolls left.
55
+ # @param [Integer] delta_y Distance along Y axis to scroll using the wheel. A negative value scrolls up.
56
+ # @return [Selenium::WebDriver::WheelActions] A self reference.
57
+ def scroll_by(delta_x, delta_y, device: nil)
58
+ scroll(delta_x: delta_x, delta_y: delta_y, device: device)
59
+ end
60
+
61
+ #
62
+ # Scrolls by provided amount based on a provided origin.
63
+ #
64
+ # The scroll origin is either the center of an element or the upper left of the viewport plus any offsets.
65
+ # If the origin is an element, and the element is not in the viewport, the bottom of the element will first
66
+ # be scrolled to the bottom of the viewport.
67
+ #
68
+ # @example Scroll from element by a specified amount
69
+ # el = driver.find_element(id: "some_id")
70
+ # origin = WheelActions::ScrollOrigin.element(el)
71
+ # driver.action.scroll_from(origin, 0, 200).perform
72
+ #
73
+ # @example Scroll from element by a specified amount with an offset
74
+ # el = driver.find_element(id: "some_id")
75
+ # origin = WheelActions::ScrollOrigin.element(el, 10, 10)
76
+ # driver.action.scroll_from(origin, 100, 200).perform
77
+ #
78
+ # @example Scroll viewport by a specified amount with an offset
79
+ # origin = WheelActions::ScrollOrigin.viewport(10, 10)
80
+ # driver.action.scroll_from(origin, 0, 200).perform
81
+ #
82
+ # @param [ScrollOrigin] scroll_origin Where scroll originates (viewport or element center) plus provided offsets.
83
+ # @param [Integer] delta_x Distance along X axis to scroll using the wheel. A negative value scrolls left.
84
+ # @param [Integer] delta_y Distance along Y axis to scroll using the wheel. A negative value scrolls up.
85
+ # @return [Selenium::WebDriver::WheelActions] A self reference.
86
+ # @raise [Error::MoveTargetOutOfBoundsError] If the origin with offset is outside the viewport.
87
+ def scroll_from(scroll_origin, delta_x, delta_y, device: nil)
88
+ raise TypeError, "#{scroll_origin.inspect} isn't a valid ScrollOrigin" unless scroll_origin.is_a?(ScrollOrigin)
89
+
90
+ scroll(x: scroll_origin.x_offset,
91
+ y: scroll_origin.y_offset,
92
+ delta_x: delta_x,
93
+ delta_y: delta_y,
94
+ origin: scroll_origin.origin,
95
+ device: device)
96
+ end
97
+
98
+ private
99
+
100
+ def scroll(**opts)
101
+ opts[:duration] = default_scroll_duration
102
+ wheel = wheel_input(opts.delete(:device))
103
+ wheel.create_scroll(**opts)
104
+ tick(wheel)
105
+ self
106
+ end
107
+
108
+ def wheel_input(name = nil)
109
+ device(name: name, type: Interactions::WHEEL) || add_wheel_input('wheel')
110
+ end
111
+ end # WheelActions
112
+ end # WebDriver
113
+ end # Selenium
@@ -0,0 +1,42 @@
1
+ # frozen_string_literal: true
2
+
3
+ # Licensed to the Software Freedom Conservancy (SFC) under one
4
+ # or more contributor license agreements. See the NOTICE file
5
+ # distributed with this work for additional information
6
+ # regarding copyright ownership. The SFC licenses this file
7
+ # to you under the Apache License, Version 2.0 (the
8
+ # "License"); you may not use this file except in compliance
9
+ # with the License. You may obtain a copy of the License at
10
+ #
11
+ # http://www.apache.org/licenses/LICENSE-2.0
12
+ #
13
+ # Unless required by applicable law or agreed to in writing,
14
+ # software distributed under the License is distributed on an
15
+ # "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16
+ # KIND, either express or implied. See the License for the
17
+ # specific language governing permissions and limitations
18
+ # under the License.
19
+
20
+ module Selenium
21
+ module WebDriver
22
+ module Interactions
23
+ #
24
+ # Creates actions specific to Pointer Input devices
25
+ #
26
+ # @api private
27
+ #
28
+
29
+ class WheelInput < InputDevice
30
+ def initialize(name = nil)
31
+ super(name)
32
+ @type = Interactions::WHEEL
33
+ end
34
+
35
+ def create_scroll(**opts)
36
+ opts[:source] = self
37
+ add_action(Scroll.new(**opts))
38
+ end
39
+ end # PointerInput
40
+ end # Interactions
41
+ end # WebDriver
42
+ end # Selenium
@@ -90,6 +90,7 @@ module Selenium
90
90
  meta: "\ue03D",
91
91
  command: "\ue03D", # alias
92
92
  left_meta: "\ue03D", # alias
93
+ zenkaku_hankaku: "\uE040",
93
94
  right_shift: "\ue050",
94
95
  right_control: "\ue051",
95
96
  right_alt: "\ue052",
@@ -0,0 +1,46 @@
1
+ # frozen_string_literal: true
2
+
3
+ # Licensed to the Software Freedom Conservancy (SFC) under one
4
+ # or more contributor license agreements. See the NOTICE file
5
+ # distributed with this work for additional information
6
+ # regarding copyright ownership. The SFC licenses this file
7
+ # to you under the Apache License, Version 2.0 (the
8
+ # "License"); you may not use this file except in compliance
9
+ # with the License. You may obtain a copy of the License at
10
+ #
11
+ # http://www.apache.org/licenses/LICENSE-2.0
12
+ #
13
+ # Unless required by applicable law or agreed to in writing,
14
+ # software distributed under the License is distributed on an
15
+ # "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16
+ # KIND, either express or implied. See the License for the
17
+ # specific language governing permissions and limitations
18
+ # under the License.
19
+
20
+ module Selenium
21
+ module WebDriver
22
+ module LocalDriver
23
+ def initialize_local_driver(options, service, url)
24
+ raise ArgumentError, "Can't initialize #{self.class} with :url" if url
25
+
26
+ service ||= Service.send(browser)
27
+ caps = process_options(options, service)
28
+ url = service_url(service)
29
+
30
+ [caps, url]
31
+ end
32
+
33
+ def process_options(options, service)
34
+ default_options = Options.send(browser)
35
+ options ||= default_options
36
+
37
+ unless options.is_a?(default_options.class)
38
+ raise ArgumentError, ":options must be an instance of #{default_options.class}"
39
+ end
40
+
41
+ service.executable_path ||= WebDriver::DriverFinder.path(options, service.class)
42
+ options.as_json
43
+ end
44
+ end
45
+ end
46
+ end
@@ -38,19 +38,31 @@ module Selenium
38
38
 
39
39
  def_delegators :@logger,
40
40
  :close,
41
- :debug, :debug?,
42
- :info, :info?,
41
+ :debug?,
42
+ :info?,
43
43
  :warn?,
44
- :error, :error?,
44
+ :error?,
45
45
  :fatal, :fatal?,
46
- :level, :level=
46
+ :level
47
47
 
48
48
  #
49
49
  # @param [String] progname Allow child projects to use Selenium's Logger pattern
50
50
  #
51
- def initialize(progname = 'Selenium')
52
- @logger = create_logger(progname)
53
- @ignored = []
51
+ def initialize(progname = 'Selenium', default_level: nil, ignored: nil, allowed: nil)
52
+ default_level ||= $DEBUG || ENV.key?('DEBUG') ? :debug : :warn
53
+
54
+ @logger = create_logger(progname, level: default_level)
55
+ @ignored = Array(ignored)
56
+ @allowed = Array(allowed)
57
+ @first_warning = false
58
+ end
59
+
60
+ def level=(level)
61
+ if level == :info && @logger.level == :info
62
+ info(':info is now the default log level, to see additional logging, set log level to :debug')
63
+ end
64
+
65
+ @logger.level = level
54
66
  end
55
67
 
56
68
  #
@@ -80,27 +92,64 @@ module Selenium
80
92
  #
81
93
  # Will not log the provided ID.
82
94
  #
83
- # @param [Array, Symbol] id
95
+ # @param [Array, Symbol] ids
96
+ #
97
+ def ignore(*ids)
98
+ @ignored += Array(ids).flatten
99
+ end
100
+
101
+ #
102
+ # Will only log the provided ID.
84
103
  #
85
- def ignore(id)
86
- Array(id).each { |ignore| @ignored << ignore }
104
+ # @param [Array, Symbol] ids
105
+ #
106
+ def allow(ids)
107
+ @allowed += Array(ids).flatten
87
108
  end
88
109
 
89
110
  #
90
- # Overrides default #warn to skip ignored messages by provided id
111
+ # Used to supply information of interest for debugging a problem
112
+ # Overrides default #debug to skip ignored messages by provided id
91
113
  #
92
114
  # @param [String] message
93
115
  # @param [Symbol, Array<Sybmol>] id
94
116
  # @yield see #deprecate
95
117
  #
96
- def warn(message, id: [])
97
- id = Array(id)
98
- return if (@ignored & id).any?
118
+ def debug(message, id: [], &block)
119
+ discard_or_log(:debug, message, id, &block)
120
+ end
99
121
 
100
- msg = id.empty? ? message : "[#{id.map(&:inspect).join(', ')}] #{message} "
101
- msg += " #{yield}" if block_given?
122
+ #
123
+ # Used to supply information of general interest
124
+ #
125
+ # @param [String] message
126
+ # @param [Symbol, Array<Sybmol>] id
127
+ # @yield see #deprecate
128
+ #
129
+ def info(message, id: [], &block)
130
+ discard_or_log(:info, message, id, &block)
131
+ end
102
132
 
103
- @logger.warn { msg }
133
+ #
134
+ # Used to supply information that suggests an error occurred
135
+ #
136
+ # @param [String] message
137
+ # @param [Symbol, Array<Sybmol>] id
138
+ # @yield see #deprecate
139
+ #
140
+ def error(message, id: [], &block)
141
+ discard_or_log(:error, message, id, &block)
142
+ end
143
+
144
+ #
145
+ # Used to supply information that suggests action be taken by user
146
+ #
147
+ # @param [String] message
148
+ # @param [Symbol, Array<Sybmol>] id
149
+ # @yield see #deprecate
150
+ #
151
+ def warn(message, id: [], &block)
152
+ discard_or_log(:warn, message, id, &block)
104
153
  end
105
154
 
106
155
  #
@@ -114,11 +163,11 @@ module Selenium
114
163
  #
115
164
  def deprecate(old, new = nil, id: [], reference: '', &block)
116
165
  id = Array(id)
117
- return if @ignored.include?(:deprecations) || (@ignored & id).any?
166
+ return if @ignored.include?(:deprecations)
118
167
 
119
- ids = id.empty? ? '' : "[#{id.map(&:inspect).join(', ')}] "
168
+ id << :deprecations if @allowed.include?(:deprecations)
120
169
 
121
- message = +"[DEPRECATION] #{ids}#{old} is deprecated"
170
+ message = +"[DEPRECATION] #{old} is deprecated"
122
171
  message << if new
123
172
  ". Use #{new} instead."
124
173
  else
@@ -126,15 +175,15 @@ module Selenium
126
175
  end
127
176
  message << " See explanation for this deprecation: #{reference}." unless reference.empty?
128
177
 
129
- warn message, &block
178
+ discard_or_log(:warn, message, id, &block)
130
179
  end
131
180
 
132
181
  private
133
182
 
134
- def create_logger(name)
183
+ def create_logger(name, level:)
135
184
  logger = ::Logger.new($stdout)
136
185
  logger.progname = name
137
- logger.level = default_level
186
+ logger.level = level
138
187
  logger.formatter = proc do |severity, time, progname, msg|
139
188
  "#{time.strftime('%F %T')} #{severity} #{progname} #{msg}\n"
140
189
  end
@@ -142,8 +191,24 @@ module Selenium
142
191
  logger
143
192
  end
144
193
 
145
- def default_level
146
- $DEBUG || ENV.key?('DEBUG') ? :debug : :warn
194
+ def discard_or_log(level, message, id)
195
+ id = Array(id)
196
+ return if (@ignored & id).any?
197
+ return if @allowed.any? && (@allowed & id).none?
198
+
199
+ return if ::Logger::Severity.const_get(level.upcase) < @logger.level
200
+
201
+ unless @first_warning
202
+ @first_warning = true
203
+ info("Details on how to use and modify Selenium logger:\n", id: [:logger_info]) do
204
+ "https://selenium.dev/documentation/webdriver/troubleshooting/logging\n"
205
+ end
206
+ end
207
+
208
+ msg = id.empty? ? message : "[#{id.map(&:inspect).join(', ')}] #{message} "
209
+ msg += " #{yield}" if block_given?
210
+
211
+ @logger.send(level) { msg }
147
212
  end
148
213
  end # Logger
149
214
  end # WebDriver
@@ -104,33 +104,6 @@ module Selenium
104
104
  @timeouts ||= Timeouts.new(@bridge)
105
105
  end
106
106
 
107
- def logs
108
- WebDriver.logger.deprecate('Manager#logs', 'Chrome::Driver#logs')
109
- @logs ||= Logs.new(@bridge)
110
- end
111
-
112
- #
113
- # @param type [Symbol] Supports two values: :tab and :window.
114
- # @return [String] The value of the window handle
115
- #
116
- def new_window(type = :tab)
117
- WebDriver.logger.deprecate('Manager#new_window', 'TargetLocator#new_window', id: :new_window) do
118
- 'e.g., `driver.switch_to.new_window(:tab)`'
119
- end
120
- case type
121
- when :tab, :window
122
- result = @bridge.new_window(type)
123
- unless result.key?('handle')
124
- raise UnknownError, "the driver did not return a handle. " \
125
- "The returned result: #{result.inspect}"
126
- end
127
- result['handle']
128
- else
129
- raise ArgumentError, "invalid argument for type. Got: '#{type.inspect}'. " \
130
- "Try :tab or :window"
131
- end
132
- end
133
-
134
107
  def window
135
108
  @window ||= Window.new(@bridge)
136
109
  end
@@ -38,12 +38,12 @@ module Selenium
38
38
  def ie(**opts)
39
39
  IE::Options.new(**opts)
40
40
  end
41
- alias_method :internet_explorer, :ie
41
+ alias internet_explorer ie
42
42
 
43
43
  def edge(**opts)
44
44
  Edge::Options.new(**opts)
45
45
  end
46
- alias_method :microsoftedge, :edge
46
+ alias microsoftedge edge
47
47
 
48
48
  def safari(**opts)
49
49
  Safari::Options.new(**opts)
@@ -66,17 +66,10 @@ module Selenium
66
66
 
67
67
  attr_accessor :options
68
68
 
69
- def initialize(options: nil, **opts)
69
+ def initialize(**opts)
70
70
  self.class.set_capabilities
71
71
 
72
- @options = if options
73
- WebDriver.logger.deprecate(":options as keyword for initializing #{self.class}",
74
- "custom values directly in #new constructor",
75
- id: :options_options)
76
- opts.merge(options)
77
- else
78
- opts
79
- end
72
+ @options = opts
80
73
  @options[:browser_name] = self.class::BROWSER
81
74
  end
82
75
 
@@ -92,7 +85,7 @@ module Selenium
92
85
  #
93
86
 
94
87
  def add_option(name, value = nil)
95
- @options[name.keys.first] = name.values.first if value.nil? && name.is_a?(Hash)
88
+ name, value = name.first if value.nil? && name.is_a?(Hash)
96
89
  @options[name] = value
97
90
  end
98
91
 
@@ -102,7 +95,7 @@ module Selenium
102
95
  as_json == other.as_json
103
96
  end
104
97
 
105
- alias_method :eql?, :==
98
+ alias eql? ==
106
99
 
107
100
  #
108
101
  # @api private
@@ -113,11 +106,14 @@ module Selenium
113
106
 
114
107
  w3c_options = process_w3c_options(options)
115
108
 
116
- self.class::CAPABILITIES.each do |capability_alias, capability_name|
109
+ browser_options = self.class::CAPABILITIES.each_with_object({}) do |(capability_alias, capability_name), hash|
117
110
  capability_value = options.delete(capability_alias)
118
- options[capability_name] = capability_value if !capability_value.nil? && !options.key?(capability_name)
111
+ hash[capability_name] = capability_value unless capability_value.nil?
119
112
  end
120
- browser_options = defined?(self.class::KEY) ? {self.class::KEY => options} : options
113
+
114
+ raise Error::WebDriverError, "These options are not w3c compliant: #{options}" unless options.empty?
115
+
116
+ browser_options = {self.class::KEY => browser_options} if defined?(self.class::KEY)
121
117
 
122
118
  process_browser_options(browser_options)
123
119
  generate_as_json(w3c_options.merge(browser_options))
@@ -130,7 +126,7 @@ module Selenium
130
126
  end
131
127
 
132
128
  def process_w3c_options(options)
133
- w3c_options = options.select { |key, _val| w3c?(key) }
129
+ w3c_options = options.select { |key, val| w3c?(key) && !val.nil? }
134
130
  w3c_options[:unhandled_prompt_behavior] &&= w3c_options[:unhandled_prompt_behavior]&.to_s&.tr('_', ' ')
135
131
  options.delete_if { |key, _val| w3c?(key) }
136
132
  w3c_options
@@ -179,8 +175,6 @@ module Selenium
179
175
  def camel_case(str)
180
176
  str.gsub(/_([a-z])/) { Regexp.last_match(1).upcase }
181
177
  end
182
- end
183
-
184
- # Options
178
+ end # Options
185
179
  end # WebDriver
186
180
  end # Selenium