selenium-webdriver 4.1.0 → 4.23.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (172) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGES +405 -1
  3. data/Gemfile +3 -0
  4. data/LICENSE +1 -1
  5. data/NOTICE +1 -1
  6. data/README.md +3 -3
  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 +38 -40
  11. data/lib/selenium/webdriver/atoms/findElements.js +27 -27
  12. data/lib/selenium/webdriver/atoms/getAttribute.js +6 -100
  13. data/lib/selenium/webdriver/atoms/isDisplayed.js +24 -96
  14. data/lib/selenium/webdriver/atoms/mutationListener.js +0 -0
  15. data/lib/selenium/webdriver/atoms.rb +5 -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_handler.rb +63 -0
  24. data/lib/selenium/webdriver/bidi/log_inspector.rb +147 -0
  25. data/lib/selenium/webdriver/bidi/navigate_result.rb +33 -0
  26. data/lib/selenium/webdriver/bidi/session.rb +51 -0
  27. data/lib/selenium/webdriver/bidi/struct.rb +44 -0
  28. data/lib/selenium/webdriver/bidi.rb +66 -0
  29. data/lib/selenium/webdriver/chrome/driver.rb +9 -29
  30. data/lib/selenium/webdriver/chrome/features.rb +9 -67
  31. data/lib/selenium/webdriver/chrome/options.rb +3 -223
  32. data/lib/selenium/webdriver/chrome/profile.rb +3 -83
  33. data/lib/selenium/webdriver/chrome/service.rb +4 -19
  34. data/lib/selenium/webdriver/chrome.rb +0 -16
  35. data/lib/selenium/webdriver/chromium/driver.rb +61 -0
  36. data/lib/selenium/webdriver/chromium/features.rb +99 -0
  37. data/lib/selenium/webdriver/chromium/options.rb +243 -0
  38. data/lib/selenium/webdriver/chromium/profile.rb +113 -0
  39. data/lib/selenium/webdriver/chromium.rb +29 -0
  40. data/lib/selenium/webdriver/common/action_builder.rb +60 -22
  41. data/lib/selenium/webdriver/common/child_process.rb +130 -0
  42. data/lib/selenium/webdriver/common/driver.rb +46 -90
  43. data/lib/selenium/webdriver/common/driver_extensions/downloads_files.rb +0 -2
  44. data/lib/selenium/webdriver/common/driver_extensions/full_page_screenshot.rb +0 -1
  45. data/lib/selenium/webdriver/common/driver_extensions/has_addons.rb +0 -2
  46. data/lib/selenium/webdriver/common/driver_extensions/has_apple_permissions.rb +0 -2
  47. data/lib/selenium/webdriver/common/driver_extensions/has_authentication.rb +0 -2
  48. data/lib/selenium/webdriver/common/driver_extensions/{has_remote_status.rb → has_bidi.rb} +10 -5
  49. data/lib/selenium/webdriver/common/driver_extensions/has_casting.rb +10 -1
  50. data/lib/selenium/webdriver/common/driver_extensions/has_cdp.rb +0 -2
  51. data/lib/selenium/webdriver/common/driver_extensions/has_context.rb +1 -4
  52. data/lib/selenium/webdriver/common/driver_extensions/has_debugger.rb +0 -2
  53. data/lib/selenium/webdriver/common/driver_extensions/has_devtools.rb +0 -2
  54. data/lib/selenium/webdriver/common/driver_extensions/has_fedcm_dialog.rb +55 -0
  55. data/lib/selenium/webdriver/common/driver_extensions/has_file_downloads.rb +65 -0
  56. data/lib/selenium/webdriver/common/driver_extensions/has_launching.rb +0 -2
  57. data/lib/selenium/webdriver/common/driver_extensions/has_log_events.rb +2 -3
  58. data/lib/selenium/webdriver/common/driver_extensions/has_network_conditions.rb +0 -2
  59. data/lib/selenium/webdriver/common/driver_extensions/has_network_interception.rb +2 -69
  60. data/lib/selenium/webdriver/common/driver_extensions/has_permissions.rb +0 -2
  61. data/lib/selenium/webdriver/common/driver_extensions/has_pinned_scripts.rb +1 -3
  62. data/lib/selenium/webdriver/common/driver_finder.rb +97 -0
  63. data/lib/selenium/webdriver/common/element.rb +8 -8
  64. data/lib/selenium/webdriver/common/error.rb +27 -4
  65. data/lib/selenium/webdriver/common/fedcm/account.rb +50 -0
  66. data/lib/selenium/webdriver/common/fedcm/dialog.rb +74 -0
  67. data/lib/selenium/webdriver/common/fedcm.rb +27 -0
  68. data/lib/selenium/webdriver/common/html5/shared_web_storage.rb +2 -2
  69. data/lib/selenium/webdriver/common/interactions/input_device.rb +10 -4
  70. data/lib/selenium/webdriver/common/interactions/interaction.rb +12 -25
  71. data/lib/selenium/webdriver/common/interactions/interactions.rb +24 -4
  72. data/lib/selenium/webdriver/common/interactions/key_actions.rb +5 -1
  73. data/lib/selenium/webdriver/common/interactions/key_input.rb +11 -27
  74. data/lib/selenium/webdriver/common/interactions/none_input.rb +10 -8
  75. data/lib/selenium/webdriver/common/interactions/pause.rb +49 -0
  76. data/lib/selenium/webdriver/common/interactions/pointer_actions.rb +59 -71
  77. data/lib/selenium/webdriver/common/{driver_extensions/has_network_connection.rb → interactions/pointer_cancel.rb} +19 -11
  78. data/lib/selenium/webdriver/common/interactions/pointer_event_properties.rb +63 -0
  79. data/lib/selenium/webdriver/common/interactions/pointer_input.rb +15 -84
  80. data/lib/selenium/webdriver/common/interactions/pointer_move.rb +60 -0
  81. data/lib/selenium/webdriver/common/interactions/pointer_press.rb +85 -0
  82. data/lib/selenium/webdriver/common/interactions/scroll.rb +59 -0
  83. data/lib/selenium/webdriver/common/interactions/scroll_origin.rb +48 -0
  84. data/lib/selenium/webdriver/common/interactions/typing_interaction.rb +54 -0
  85. data/lib/selenium/webdriver/common/interactions/wheel_actions.rb +114 -0
  86. data/lib/selenium/webdriver/common/interactions/wheel_input.rb +42 -0
  87. data/lib/selenium/webdriver/common/keys.rb +1 -0
  88. data/lib/selenium/webdriver/common/local_driver.rb +53 -0
  89. data/lib/selenium/webdriver/common/logger.rb +93 -28
  90. data/lib/selenium/webdriver/common/manager.rb +1 -28
  91. data/lib/selenium/webdriver/common/options.rb +19 -19
  92. data/lib/selenium/webdriver/common/platform.rb +12 -52
  93. data/lib/selenium/webdriver/common/port_prober.rb +1 -1
  94. data/lib/selenium/webdriver/common/profile_helper.rb +1 -1
  95. data/lib/selenium/webdriver/common/proxy.rb +4 -4
  96. data/lib/selenium/webdriver/common/script.rb +45 -0
  97. data/lib/selenium/webdriver/common/search_context.rb +10 -8
  98. data/lib/selenium/webdriver/common/selenium_manager.rb +104 -0
  99. data/lib/selenium/webdriver/common/service.rb +21 -30
  100. data/lib/selenium/webdriver/common/service_manager.rb +8 -15
  101. data/lib/selenium/webdriver/common/shadow_root.rb +2 -3
  102. data/lib/selenium/webdriver/common/socket_lock.rb +3 -3
  103. data/lib/selenium/webdriver/common/socket_poller.rb +3 -3
  104. data/lib/selenium/webdriver/common/takes_screenshot.rb +6 -5
  105. data/lib/selenium/webdriver/common/target_locator.rb +2 -3
  106. data/lib/selenium/webdriver/common/timeouts.rb +2 -2
  107. data/lib/selenium/webdriver/common/virtual_authenticator/credential.rb +85 -0
  108. data/lib/selenium/webdriver/common/virtual_authenticator/virtual_authenticator.rb +72 -0
  109. data/lib/selenium/webdriver/common/virtual_authenticator/virtual_authenticator_options.rb +62 -0
  110. data/lib/selenium/webdriver/common/websocket_connection.rb +176 -0
  111. data/lib/selenium/webdriver/common/window.rb +6 -6
  112. data/lib/selenium/webdriver/common/zipper.rb +1 -1
  113. data/lib/selenium/webdriver/common.rb +26 -5
  114. data/lib/selenium/webdriver/devtools/console_event.rb +0 -2
  115. data/lib/selenium/webdriver/devtools/exception_event.rb +0 -2
  116. data/lib/selenium/webdriver/devtools/mutation_event.rb +0 -2
  117. data/lib/selenium/webdriver/devtools/network_interceptor.rb +173 -0
  118. data/lib/selenium/webdriver/devtools/pinned_script.rb +0 -2
  119. data/lib/selenium/webdriver/devtools/request.rb +1 -3
  120. data/lib/selenium/webdriver/devtools/response.rb +1 -3
  121. data/lib/selenium/webdriver/devtools.rb +17 -114
  122. data/lib/selenium/webdriver/edge/driver.rb +9 -3
  123. data/lib/selenium/webdriver/edge/features.rb +8 -4
  124. data/lib/selenium/webdriver/edge/options.rb +17 -5
  125. data/lib/selenium/webdriver/edge/profile.rb +2 -2
  126. data/lib/selenium/webdriver/edge/service.rb +8 -7
  127. data/lib/selenium/webdriver/edge.rb +0 -2
  128. data/lib/selenium/webdriver/firefox/driver.rb +9 -2
  129. data/lib/selenium/webdriver/firefox/features.rb +11 -7
  130. data/lib/selenium/webdriver/firefox/options.rb +10 -16
  131. data/lib/selenium/webdriver/firefox/profile.rb +21 -17
  132. data/lib/selenium/webdriver/firefox/profiles_ini.rb +1 -1
  133. data/lib/selenium/webdriver/firefox/service.rb +0 -18
  134. data/lib/selenium/webdriver/firefox/util.rb +46 -0
  135. data/lib/selenium/webdriver/firefox.rb +1 -14
  136. data/lib/selenium/webdriver/ie/driver.rb +7 -1
  137. data/lib/selenium/webdriver/ie/features.rb +34 -0
  138. data/lib/selenium/webdriver/ie/options.rb +6 -4
  139. data/lib/selenium/webdriver/ie/service.rb +0 -22
  140. data/lib/selenium/webdriver/ie.rb +4 -17
  141. data/lib/selenium/webdriver/remote/bidi_bridge.rb +44 -0
  142. data/lib/selenium/webdriver/remote/{commands.rb → bridge/commands.rb} +22 -9
  143. data/lib/selenium/webdriver/remote/bridge/locator_converter.rb +76 -0
  144. data/lib/selenium/webdriver/remote/bridge.rb +147 -99
  145. data/lib/selenium/webdriver/remote/capabilities.rb +5 -55
  146. data/lib/selenium/webdriver/remote/driver.rb +35 -14
  147. data/lib/selenium/webdriver/remote/features.rb +75 -0
  148. data/lib/selenium/webdriver/remote/http/common.rb +24 -6
  149. data/lib/selenium/webdriver/remote/http/curb.rb +1 -3
  150. data/lib/selenium/webdriver/remote/http/default.rb +8 -14
  151. data/lib/selenium/webdriver/remote/response.rb +8 -34
  152. data/lib/selenium/webdriver/remote/server_error.rb +2 -2
  153. data/lib/selenium/webdriver/remote.rb +2 -1
  154. data/lib/selenium/webdriver/safari/driver.rb +7 -1
  155. data/lib/selenium/webdriver/safari/features.rb +5 -3
  156. data/lib/selenium/webdriver/safari/options.rb +5 -1
  157. data/lib/selenium/webdriver/safari/service.rb +10 -4
  158. data/lib/selenium/webdriver/safari.rb +1 -15
  159. data/lib/selenium/webdriver/support/color.rb +22 -22
  160. data/lib/selenium/webdriver/support/event_firing_bridge.rb +4 -4
  161. data/lib/selenium/webdriver/support/guards/guard.rb +14 -14
  162. data/lib/selenium/webdriver/support/guards/guard_condition.rb +1 -3
  163. data/lib/selenium/webdriver/support/guards.rb +2 -2
  164. data/lib/selenium/webdriver/support/relative_locator.rb +0 -1
  165. data/lib/selenium/webdriver/support/select.rb +3 -1
  166. data/lib/selenium/webdriver/version.rb +1 -1
  167. data/lib/selenium/webdriver.rb +7 -5
  168. data/selenium-webdriver.gemspec +20 -16
  169. metadata +135 -47
  170. data/lib/selenium/webdriver/remote/http/persistent.rb +0 -65
  171. data/lib/selenium/webdriver/support/cdp/domain.rb.erb +0 -63
  172. data/lib/selenium/webdriver/support/cdp_client_generator.rb +0 -108
@@ -25,11 +25,12 @@ module Selenium
25
25
 
26
26
  KEY = 'moz:firefoxOptions'
27
27
 
28
- # see: https://firefox-source-docs.mozilla.org/testing/geckodriver/Capabilities.html
28
+ # see: https://developer.mozilla.org/en-US/docs/Web/WebDriver/Capabilities/firefoxOptions
29
29
  CAPABILITIES = {binary: 'binary',
30
30
  args: 'args',
31
31
  log: 'log',
32
32
  prefs: 'prefs',
33
+ env: 'env',
33
34
  android_package: 'androidPackage',
34
35
  android_activity: 'androidActivity',
35
36
  android_device_serial: 'androidDeviceSerial',
@@ -44,7 +45,7 @@ module Selenium
44
45
  #
45
46
  # @example
46
47
  # options = Selenium::WebDriver::Firefox::Options.new(args: ['--host=127.0.0.1'])
47
- # driver = Selenium::WebDriver.for :firefox, capabilities: options
48
+ # driver = Selenium::WebDriver.for :firefox, options: options
48
49
  #
49
50
  # @param [Hash] opts the pre-defined options to create the Firefox::Options with
50
51
  # @option opts [String] :binary Path to the Firefox executable to use
@@ -56,12 +57,17 @@ module Selenium
56
57
  #
57
58
 
58
59
  def initialize(log_level: nil, **opts)
59
- @debugger_address = opts.delete(:debugger_address)
60
+ @debugger_address = opts.delete(:debugger_address) { true }
61
+ opts[:accept_insecure_certs] = true unless opts.key?(:accept_insecure_certs)
60
62
 
61
63
  super(**opts)
62
64
 
63
65
  @options[:args] ||= []
64
66
  @options[:prefs] ||= {}
67
+ # Firefox 129 onwards the CDP protocol will not be enabled by default. Setting this preference will enable it.
68
+ # https://fxdx.dev/deprecating-cdp-support-in-firefox-embracing-the-future-with-webdriver-bidi/.
69
+ @options[:prefs]['remote.active-protocols'] = 3
70
+ @options[:env] ||= {}
65
71
  @options[:log] ||= {level: log_level} if log_level
66
72
 
67
73
  process_profile(@options.delete(:profile))
@@ -96,18 +102,6 @@ module Selenium
96
102
  @options[:prefs][name] = value
97
103
  end
98
104
 
99
- #
100
- # Run Firefox in headless mode.
101
- #
102
- # @example Enable headless mode
103
- # options = Selenium::WebDriver::Firefox::Options.new
104
- # options.headless!
105
- #
106
-
107
- def headless!
108
- add_argument '-headless'
109
- end
110
-
111
105
  #
112
106
  # Sets Firefox profile.
113
107
  #
@@ -175,7 +169,7 @@ module Selenium
175
169
  end
176
170
 
177
171
  def camelize?(key)
178
- key != "prefs"
172
+ key != 'prefs'
179
173
  end
180
174
  end # Options
181
175
  end # Firefox
@@ -24,17 +24,23 @@ module Selenium
24
24
  include ProfileHelper
25
25
 
26
26
  VALID_PREFERENCE_TYPES = [TrueClass, FalseClass, Integer, Float, String].freeze
27
+ WEBDRIVER_PREFS = {
28
+ port: 'webdriver_firefox_port',
29
+ log_file: 'webdriver.log.file'
30
+ }.freeze
27
31
 
28
32
  DEFAULT_PREFERENCES = {
29
- "browser.newtabpage.enabled" => false,
30
- "browser.startup.homepage" => "about:blank",
31
- "browser.usedOnWindows10.introURL" => "about:blank",
32
- "network.captive-portal-service.enabled" => false,
33
- "security.csp.enable" => false
33
+ 'browser.newtabpage.enabled' => false,
34
+ 'browser.startup.homepage' => 'about:blank',
35
+ 'browser.usedOnWindows10.introURL' => 'about:blank',
36
+ 'network.captive-portal-service.enabled' => false,
37
+ 'security.csp.enable' => false
34
38
  }.freeze
35
39
 
36
- attr_reader :name, :log_file
37
- attr_writer :secure_ssl, :load_no_focus_lib
40
+ LOCK_FILES = %w[.parentlock parent.lock lock].freeze
41
+
42
+ attr_reader :name, :log_file
43
+ attr_writer :secure_ssl, :load_no_focus_lib
38
44
 
39
45
  class << self
40
46
  def ini
@@ -96,7 +102,7 @@ module Selenium
96
102
  raise TypeError, "expected one of #{VALID_PREFERENCE_TYPES.inspect}, got #{value.inspect}:#{value.class}"
97
103
  end
98
104
 
99
- if value.is_a?(String) && stringified?(value)
105
+ if value.is_a?(String) && Util.stringified?(value)
100
106
  raise ArgumentError, "preference values must be plain strings: #{key.inspect} => #{value.inspect}"
101
107
  end
102
108
 
@@ -143,7 +149,7 @@ module Selenium
143
149
  end
144
150
  end
145
151
 
146
- alias_method :as_json, :encoded
152
+ alias as_json encoded
147
153
 
148
154
  private
149
155
 
@@ -160,7 +166,7 @@ module Selenium
160
166
  destination = File.join(directory, 'extensions')
161
167
 
162
168
  @extensions.each do |name, extension|
163
- WebDriver.logger.debug({extenstion: name}.inspect)
169
+ WebDriver.logger.debug({extension: name}.inspect, id: :firefox_profile)
164
170
  extension.write_to(destination)
165
171
  end
166
172
  end
@@ -176,7 +182,7 @@ module Selenium
176
182
  end
177
183
 
178
184
  def delete_lock_files(directory)
179
- %w[.parentlock parent.lock].each do |name|
185
+ LOCK_FILES.each do |name|
180
186
  FileUtils.rm_f File.join(directory, name)
181
187
  end
182
188
  end
@@ -204,8 +210,8 @@ module Selenium
204
210
  File.read(path).split("\n").each do |line|
205
211
  next unless line =~ /user_pref\("([^"]+)"\s*,\s*(.+?)\);/
206
212
 
207
- key = Regexp.last_match(1).strip
208
- value = Regexp.last_match(2).strip
213
+ key = Regexp.last_match(1)&.strip
214
+ value = Regexp.last_match(2)&.strip
209
215
 
210
216
  # wrap the value in an array to make it a valid JSON string.
211
217
  prefs[key] = JSON.parse("[#{value}]").first
@@ -221,11 +227,9 @@ module Selenium
221
227
  end
222
228
  end
223
229
  end
230
+ end
224
231
 
225
- def stringified?(str)
226
- /^".*"$/.match?(str)
227
- end
228
- end # Profile
232
+ # Profile
229
233
  end # Firefox
230
234
  end # WebDriver
231
235
  end # Selenium
@@ -52,7 +52,7 @@ module Selenium
52
52
  when /^\[Profile/
53
53
  name, path = nil if path_for(name, is_relative, path)
54
54
  when /^Name=(.+)$/
55
- name = Regexp.last_match(1).strip
55
+ name = Regexp.last_match(1)&.strip
56
56
  when /^IsRelative=(.+)$/
57
57
  is_relative = Regexp.last_match(1).strip == '1'
58
58
  when /^Path=(.+)$/
@@ -23,25 +23,7 @@ module Selenium
23
23
  class Service < WebDriver::Service
24
24
  DEFAULT_PORT = 4444
25
25
  EXECUTABLE = 'geckodriver'
26
- MISSING_TEXT = <<~ERROR
27
- Unable to find Mozilla geckodriver. Please download the server from
28
- https://github.com/mozilla/geckodriver/releases and place it somewhere on your PATH.
29
- More info at https://developer.mozilla.org/en-US/docs/Mozilla/QA/Marionette/WebDriver.
30
- ERROR
31
26
  SHUTDOWN_SUPPORTED = false
32
-
33
- private
34
-
35
- # NOTE: This processing is deprecated
36
- def extract_service_args(driver_opts)
37
- driver_args = super
38
- driver_opts = driver_opts.dup
39
- driver_args << "--binary=#{driver_opts[:binary]}" if driver_opts.key?(:binary)
40
- driver_args << "--log=#{driver_opts[:log]}" if driver_opts.key?(:log)
41
- driver_args << "--marionette-port=#{driver_opts[:marionette_port]}" if driver_opts.key?(:marionette_port)
42
- driver_args << "--host=#{driver_opts[:host]}" if driver_opts.key?(:host)
43
- driver_args
44
- end
45
27
  end # Service
46
28
  end # Firefox
47
29
  end # WebDriver
@@ -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 Firefox
23
+ # @api private
24
+ module Util
25
+ module_function
26
+
27
+ def app_data_path
28
+ case Platform.os
29
+ when :windows
30
+ "#{ENV.fetch('APPDATA')}\\Mozilla\\Firefox"
31
+ when :macosx
32
+ "#{Platform.home}/Library/Application Support/Firefox"
33
+ when :unix, :linux
34
+ "#{Platform.home}/.mozilla/firefox"
35
+ else
36
+ raise "Unknown os: #{Platform.os}"
37
+ end
38
+ end
39
+
40
+ def stringified?(str)
41
+ str =~ /^".*"$/
42
+ end
43
+ end # Util
44
+ end # Firefox
45
+ end # WebDriver
46
+ end # Selenium
@@ -24,6 +24,7 @@ require 'rexml/document'
24
24
  module Selenium
25
25
  module WebDriver
26
26
  module Firefox
27
+ autoload :Util, 'selenium/webdriver/firefox/util'
27
28
  autoload :Extension, 'selenium/webdriver/firefox/extension'
28
29
  autoload :ProfilesIni, 'selenium/webdriver/firefox/profiles_ini'
29
30
  autoload :Profile, 'selenium/webdriver/firefox/profile'
@@ -41,20 +42,6 @@ module Selenium
41
42
  # until WebDriver Bidi is available.
42
43
  DEVTOOLS_VERSION = 85
43
44
 
44
- def self.driver_path=(path)
45
- WebDriver.logger.deprecate 'Selenium::WebDriver::Firefox#driver_path=',
46
- 'Selenium::WebDriver::Firefox::Service#driver_path=',
47
- id: :driver_path
48
- Selenium::WebDriver::Firefox::Service.driver_path = path
49
- end
50
-
51
- def self.driver_path
52
- WebDriver.logger.deprecate 'Selenium::WebDriver::Firefox#driver_path',
53
- 'Selenium::WebDriver::Firefox::Service#driver_path',
54
- id: :driver_path
55
- Selenium::WebDriver::Firefox::Service.driver_path
56
- end
57
-
58
45
  def self.path=(path)
59
46
  Platform.assert_executable path
60
47
  @path = path
@@ -20,7 +20,6 @@
20
20
  module Selenium
21
21
  module WebDriver
22
22
  module IE
23
-
24
23
  #
25
24
  # Driver implementation for Internet Explorer supporting
26
25
  # both OSS and W3C dialects of JSON wire protocol.
@@ -30,6 +29,13 @@ module Selenium
30
29
  class Driver < WebDriver::Driver
31
30
  EXTENSIONS = [DriverExtensions::HasWebStorage].freeze
32
31
 
32
+ include LocalDriver
33
+
34
+ def initialize(options: nil, service: nil, url: nil, **opts)
35
+ caps, url = initialize_local_driver(options, service, url)
36
+ super(caps: caps, url: url, **opts)
37
+ end
38
+
33
39
  def browser
34
40
  :internet_explorer
35
41
  end
@@ -0,0 +1,34 @@
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 IE
23
+ module Features
24
+ def command_list
25
+ self.class::COMMANDS
26
+ end
27
+
28
+ def commands(command)
29
+ command_list[command]
30
+ end
31
+ end # Bridge
32
+ end # Ie
33
+ end # WebDriver
34
+ end # Selenium
@@ -41,7 +41,9 @@ module Selenium
41
41
  use_per_process_proxy: 'ie.usePerProcessProxy',
42
42
  use_legacy_file_upload_dialog_handling: 'ie.useLegacyFileUploadDialogHandling',
43
43
  attach_to_edge_chrome: 'ie.edgechromium',
44
- edge_executable_path: 'ie.edgepath'
44
+ edge_executable_path: 'ie.edgepath',
45
+ ignore_process_match: 'ie.ignoreprocessmatch',
46
+ silent: 'silent'
45
47
  }.freeze
46
48
  BROWSER = 'internet explorer'
47
49
 
@@ -52,12 +54,12 @@ module Selenium
52
54
  #
53
55
  # @example
54
56
  # options = Selenium::WebDriver::IE::Options.new(args: ['--host=127.0.0.1'])
55
- # driver = Selenium::WebDriver.for(:ie, capabilities: options)
57
+ # driver = Selenium::WebDriver.for(:ie, options: options)
56
58
  #
57
59
  # @example
58
60
  # options = Selenium::WebDriver::IE::Options.new
59
61
  # options.element_scroll_behavior = Selenium::WebDriver::IE::Options::SCROLL_BOTTOM
60
- # driver = Selenium::WebDriver.for(:ie, capabilities: options)
62
+ # driver = Selenium::WebDriver.for(:ie, options: options)
61
63
  #
62
64
  # @param [Hash] opts the pre-defined options
63
65
  # @option opts [Array<String>] args
@@ -80,7 +82,7 @@ module Selenium
80
82
 
81
83
  def initialize(**opts)
82
84
  @args = (opts.delete(:args) || []).to_set
83
- super(**opts)
85
+ super
84
86
 
85
87
  @options[:native_events] = true if @options[:native_events].nil?
86
88
  end
@@ -23,29 +23,7 @@ module Selenium
23
23
  class Service < WebDriver::Service
24
24
  DEFAULT_PORT = 5555
25
25
  EXECUTABLE = 'IEDriverServer'
26
- MISSING_TEXT = <<~ERROR
27
- Unable to find IEDriverServer. Please download the server from
28
- https://www.selenium.dev/downloads/ and place it somewhere on your PATH.
29
- More info at https://github.com/SeleniumHQ/selenium/wiki/InternetExplorerDriver.
30
- ERROR
31
26
  SHUTDOWN_SUPPORTED = true
32
-
33
- private
34
-
35
- # NOTE: This processing is deprecated
36
- def extract_service_args(driver_opts)
37
- driver_args = super
38
- driver_opts = driver_opts.dup
39
- driver_args << "--log-level=#{driver_opts[:log_level].to_s.upcase}" if driver_opts.key?(:log_level)
40
- driver_args << "--log-file=#{driver_opts[:log_file]}" if driver_opts.key?(:log_file)
41
- if driver_opts.key?(:implementation)
42
- driver_args << "--implementation=#{driver_opts[:implementation].to_s.upcase}"
43
- end
44
- driver_args << "--host=#{driver_opts[:host]}" if driver_opts.key?(:host)
45
- driver_args << "--extract_path=#{driver_opts[:extract_path]}" if driver_opts.key?(:extract_path)
46
- driver_args << "--silent" if driver_opts[:silent] == true
47
- driver_args
48
- end
49
27
  end # Server
50
28
  end # IE
51
29
  end # WebDriver
@@ -20,23 +20,10 @@
20
20
  module Selenium
21
21
  module WebDriver
22
22
  module IE
23
- autoload :Driver, 'selenium/webdriver/ie/driver'
24
- autoload :Options, 'selenium/webdriver/ie/options'
25
- autoload :Service, 'selenium/webdriver/ie/service'
26
-
27
- def self.driver_path=(path)
28
- WebDriver.logger.deprecate 'Selenium::WebDriver::IE#driver_path=',
29
- 'Selenium::WebDriver::IE::Service#driver_path=',
30
- id: :driver_path
31
- Selenium::WebDriver::IE::Service.driver_path = path
32
- end
33
-
34
- def self.driver_path
35
- WebDriver.logger.deprecate 'Selenium::WebDriver::IE#driver_path',
36
- 'Selenium::WebDriver::IE::Service#driver_path',
37
- id: :driver_path
38
- Selenium::WebDriver::IE::Service.driver_path
39
- end
23
+ autoload :Features, 'selenium/webdriver/ie/features'
24
+ autoload :Driver, 'selenium/webdriver/ie/driver'
25
+ autoload :Options, 'selenium/webdriver/ie/options'
26
+ autoload :Service, 'selenium/webdriver/ie/service'
40
27
  end # IE
41
28
  end # WebDriver
42
29
  end # Selenium
@@ -0,0 +1,44 @@
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 Remote
23
+ class BiDiBridge < Bridge
24
+ attr_reader :bidi
25
+
26
+ def create_session(capabilities)
27
+ super
28
+ socket_url = @capabilities[:web_socket_url]
29
+ @bidi = Selenium::WebDriver::BiDi.new(url: socket_url)
30
+ end
31
+
32
+ def quit
33
+ super
34
+ ensure
35
+ bidi.close
36
+ end
37
+
38
+ def close
39
+ execute(:close_window).tap { |handles| bidi.close if handles.empty? }
40
+ end
41
+ end # BiDiBridge
42
+ end # Remote
43
+ end # WebDriver
44
+ end # Selenium
@@ -20,7 +20,6 @@
20
20
  module Selenium
21
21
  module WebDriver
22
22
  module Remote
23
-
24
23
  #
25
24
  # https://w3c.github.io/webdriver/#endpoints
26
25
  # @api private
@@ -60,10 +59,6 @@ module Selenium
60
59
  fullscreen_window: [:post, 'session/:session_id/window/fullscreen'],
61
60
  minimize_window: [:post, 'session/:session_id/window/minimize'],
62
61
  maximize_window: [:post, 'session/:session_id/window/maximize'],
63
- set_window_size: [:post, 'session/:session_id/window/size'],
64
- get_window_size: [:get, 'session/:session_id/window/size'],
65
- set_window_position: [:post, 'session/:session_id/window/position'],
66
- get_window_position: [:get, 'session/:session_id/window/position'],
67
62
  set_window_rect: [:post, 'session/:session_id/window/rect'],
68
63
  get_window_rect: [:get, 'session/:session_id/window/rect'],
69
64
  switch_to_frame: [:post, 'session/:session_id/frame'],
@@ -130,7 +125,6 @@ module Selenium
130
125
  #
131
126
 
132
127
  element_click: [:post, 'session/:session_id/element/:id/click'],
133
- element_tap: [:post, 'session/:session_id/element/:id/tap'],
134
128
  element_clear: [:post, 'session/:session_id/element/:id/clear'],
135
129
  element_send_keys: [:post, 'session/:session_id/element/:id/value'],
136
130
 
@@ -151,12 +145,31 @@ module Selenium
151
145
  take_element_screenshot: [:get, 'session/:session_id/element/:id/screenshot'],
152
146
 
153
147
  #
154
- # server extensions
148
+ # virtual-authenticator
155
149
  #
156
150
 
157
- upload_file: [:post, 'session/:session_id/se/file']
158
- }.freeze
151
+ add_virtual_authenticator: [:post, 'session/:session_id/webauthn/authenticator'],
152
+ remove_virtual_authenticator: [:delete, 'session/:session_id/webauthn/authenticator/:authenticatorId'],
153
+ add_credential: [:post, 'session/:session_id/webauthn/authenticator/:authenticatorId/credential'],
154
+ get_credentials: [:get, 'session/:session_id/webauthn/authenticator/:authenticatorId/credentials'],
155
+ remove_credential: [:delete,
156
+ 'session/:session_id/webauthn/authenticator/:authenticatorId/credentials/:credentialId'],
157
+ remove_all_credentials: [:delete, 'session/:session_id/webauthn/authenticator/:authenticatorId/credentials'],
158
+ set_user_verified: [:post, 'session/:session_id/webauthn/authenticator/:authenticatorId/uv'],
159
+
160
+ #
161
+ # federated-credential management
162
+ #
159
163
 
164
+ get_fedcm_title: [:get, 'session/:session_id/fedcm/gettitle'],
165
+ get_fedcm_dialog_type: [:get, 'session/:session_id/fedcm/getdialogtype'],
166
+ get_fedcm_account_list: [:get, 'session/:session_id/fedcm/accountlist'],
167
+ click_fedcm_dialog_button: [:post, 'session/:session_id/fedcm/clickdialogbutton'],
168
+ cancel_fedcm_dialog: [:post, 'session/:session_id/fedcm/canceldialog'],
169
+ select_fedcm_account: [:post, 'session/:session_id/fedcm/selectaccount'],
170
+ set_fedcm_delay: [:post, 'session/:session_id/fedcm/setdelayenabled'],
171
+ reset_fedcm_cooldown: [:post, 'session/:session_id/fedcm/resetcooldown']
172
+ }.freeze
160
173
  end # Bridge
161
174
  end # Remote
162
175
  end # WebDriver
@@ -0,0 +1,76 @@
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 Remote
23
+ class Bridge
24
+ class LocatorConverter
25
+ ESCAPE_CSS_REGEXP = /(['"\\#.:;,!?+<>=~*^$|%&@`{}\-\[\]()])/
26
+ UNICODE_CODE_POINT = 30
27
+
28
+ #
29
+ # Converts a locator to a specification compatible one.
30
+ # @param [String, Symbol] how
31
+ # @param [String] what
32
+ #
33
+
34
+ def convert(how, what)
35
+ how = SearchContext.finders[how.to_sym] || how
36
+
37
+ case how
38
+ when 'class name'
39
+ how = 'css selector'
40
+ what = ".#{escape_css(what.to_s)}"
41
+ when 'id'
42
+ how = 'css selector'
43
+ what = "##{escape_css(what.to_s)}"
44
+ when 'name'
45
+ how = 'css selector'
46
+ what = "*[name='#{escape_css(what.to_s)}']"
47
+ end
48
+
49
+ if what.is_a?(Hash)
50
+ what = what.each_with_object({}) do |(h, w), hash|
51
+ h, w = convert(h.to_s, w)
52
+ hash[h] = w
53
+ end
54
+ end
55
+
56
+ [how, what]
57
+ end
58
+
59
+ private
60
+
61
+ #
62
+ # Escapes invalid characters in CSS selector.
63
+ # @see https://mathiasbynens.be/notes/css-escapes
64
+ #
65
+
66
+ def escape_css(string)
67
+ string = string.gsub(ESCAPE_CSS_REGEXP) { |match| "\\#{match}" }
68
+ string = "\\#{UNICODE_CODE_POINT + Integer(string[0])} #{string[1..]}" if string[0]&.match?(/[[:digit:]]/)
69
+
70
+ string
71
+ end
72
+ end # LocatorConverter
73
+ end # Bridge
74
+ end # Remote
75
+ end # WebDriver
76
+ end # Selenium