appium_lib_core 5.4.0 → 5.5.1

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: d218a7a8a40159dbd710c8aec292346297a92b98f7026456fd7a29c5794f2914
4
- data.tar.gz: 9606b1256c653c693ed17b344cec7fe2adaf58e8f5f95c9be3f0b9b3811cd79c
3
+ metadata.gz: 36c3e5d802524fd73d0bd2f3f4c383dc8ca315b5fab8d91126aa38360023513e
4
+ data.tar.gz: 3133b9cacbc2ccb65d44be5abc2ead266e70b84603a37d33f4697d71e5a28320
5
5
  SHA512:
6
- metadata.gz: 9cf6fda7cec0c09f3b83e0bd786d3a914a8d24c1f1f6f355570c83f9ae1b33c486608370d6a4c5b5cd2aeab73df802509dce93d6de46efcf12cd8a86e3d9c6f9
7
- data.tar.gz: 4f57441793ffeb9b40d9f6cc5d1456e836b05cd166775d2ec3c2319767daf36e44f66b498b69fa3b4f5f3e304718fd5a32fa717b732983294ed8713d0950c33a
6
+ metadata.gz: 606343375d1a70d5b0d3f6c8b3a01d5bb4cb3b7668bfe622bae0ba3d35ca57997c1dd1b081934cade812a74bce250fa8fd0d3328d98dd94da451a34677021ef3
7
+ data.tar.gz: 7315f007b57556ba24d615aea8fc48d05808a89f6cb408b400a560e5ea032827b732b20c15f3682e36abe48f3d30fcfd6896368e21a479e1adecf73b30459cc3
data/CHANGELOG.md CHANGED
@@ -10,6 +10,21 @@ Read `release_notes.md` for commit level details.
10
10
 
11
11
  ### Deprecations
12
12
 
13
+ ## [5.5.1] - 2022-10-10
14
+
15
+ ### Bug fixes
16
+ - Keep converting String to Symbol for `capabilities`, `caps` and `appium_lib` for the backward compatibility
17
+ - Wrong `automationName` and `platformName` detection in this library before starting a session
18
+
19
+ ### Deprecations
20
+ - Converting `capabilities`, `caps` and `appium_lib` from String to Symbol
21
+ - They are expected to be Symbol. Nothing affects existing users who already give the above keys as Symbol for `Appium::Core.for`.
22
+
23
+ ## [5.5.0] - 2022-10-09
24
+
25
+ ### Bug fixes
26
+ - Removed forcefully converting keys of capabilities into symbol, which caused unexpected capabilities format issue [ruby_lib/945](https://github.com/appium/ruby_lib/issues/945)
27
+
13
28
  ## [5.4.0] - 2022-10-01
14
29
 
15
30
  ### Enhancements
@@ -53,8 +53,8 @@ module Appium
53
53
  # Override
54
54
  # Creates session handling.
55
55
  #
56
- # @param [::Selenium::WebDriver::Remote::Capabilities, Hash] capabilities A capability
57
- # @return [::Selenium::WebDriver::Remote::Capabilities]
56
+ # @param [::Appium::Core::Base::Capabilities, Hash] capabilities A capability
57
+ # @return [::Appium::Core::Base::Capabilities]
58
58
  #
59
59
  # @example
60
60
  #
@@ -89,10 +89,10 @@ module Appium
89
89
  # Append +appium:+ prefix for Appium following W3C spec
90
90
  # https://www.w3.org/TR/webdriver/#dfn-validate-capabilities
91
91
  #
92
- # @param [::Selenium::WebDriver::Remote::Capabilities, Hash] capabilities A capability
93
- # @return [::Selenium::WebDriver::Remote::Capabilities]
92
+ # @param [::Appium::Core::Base::Capabilities, Hash] capabilities A capability
93
+ # @return [::Appium::Core::Base::Capabilities]
94
94
  def add_appium_prefix(capabilities)
95
- w3c_capabilities = ::Selenium::WebDriver::Remote::Capabilities.new
95
+ w3c_capabilities = ::Appium::Core::Base::Capabilities.new
96
96
 
97
97
  capabilities = capabilities.send(:capabilities) unless capabilities.is_a?(Hash)
98
98
 
@@ -111,12 +111,12 @@ module Appium
111
111
 
112
112
  private
113
113
 
114
- def camel_case(str)
115
- str.gsub(/_([a-z])/) { Regexp.last_match(1).upcase }
114
+ def camel_case(str_or_sym)
115
+ str_or_sym.to_s.gsub(/_([a-z])/) { Regexp.last_match(1).upcase }
116
116
  end
117
117
 
118
118
  def extension_prefix?(capability_name)
119
- snake_cased_capability_names = ::Selenium::WebDriver::Remote::Capabilities::KNOWN.map(&:to_s)
119
+ snake_cased_capability_names = ::Appium::Core::Base::Capabilities::KNOWN.map(&:to_s)
120
120
  camel_cased_capability_names = snake_cased_capability_names.map { |v| camel_case(v) }
121
121
 
122
122
  # Check 'EXTENSION_CAPABILITY_PATTERN'
@@ -126,7 +126,7 @@ module Appium
126
126
  end
127
127
 
128
128
  def json_create(value)
129
- ::Selenium::WebDriver::Remote::Capabilities.json_create(value)
129
+ ::Appium::Core::Base::Capabilities.json_create(value)
130
130
  end
131
131
 
132
132
  public
@@ -182,7 +182,7 @@ module Appium
182
182
 
183
183
  # Port from MJSONWP
184
184
  def session_capabilities
185
- ::Selenium::WebDriver::Remote::Capabilities.json_create execute(:get_capabilities)
185
+ ::Appium::Core::Base::Capabilities.json_create execute(:get_capabilities)
186
186
  end
187
187
 
188
188
  # Override for safe. Newer ruby selenium webdriver already has the same code
@@ -345,6 +345,9 @@ module Appium
345
345
  element_id = element_id_from(arg)
346
346
  return ::Appium::Core::Element.new(self, element_id) if element_id
347
347
 
348
+ shadow_root_id = shadow_root_id_from(arg)
349
+ return ::Selenium::WebDriver::Remote::ShadowRoot.new self, shadow_root_id if shadow_root_id
350
+
348
351
  arg.each { |k, v| arg[k] = unwrap_script_result(v) }
349
352
  else
350
353
  arg
@@ -15,22 +15,14 @@
15
15
  module Appium
16
16
  module Core
17
17
  class Base
18
- module Capabilities
19
- # @private
20
- # @param [Hash] opts_caps Capabilities for Appium server. All capability keys are converted to lowerCamelCase when
21
- # this client sends capabilities to Appium server as JSON format.
22
- # @return [::Selenium::WebDriver::Remote::Capabilities] Return instance of Appium::Core::Base::Capabilities
23
- # inherited ::Selenium::WebDriver::Remote::Capabilities
24
- def self.create_capabilities(opts_caps = {})
25
- # TODO: Move to 'Options' way instead of 'Capabilities'.
26
- # Selenium 5 will have Options instead of 'Capabilities'.
27
- # https://github.com/SeleniumHQ/selenium/blob/trunk/rb/lib/selenium/webdriver/common/options.rb
28
- # Then, Ruby client also shoud move to the Options way.
29
- # Appium's capabilities could change by depending on Appium versions. So it does not have
30
- # standard options like chrome and firefox etc. So, the implementation should differ from
31
- # other browsers. But here should inherit `Options` to follow Selenium.
32
- ::Selenium::WebDriver::Remote::Capabilities.new(opts_caps)
33
- end
18
+ class Capabilities < ::Selenium::WebDriver::Remote::Capabilities
19
+ # TODO: Move to 'Options' way instead of 'Capabilities'.
20
+ # Selenium 5 will have Options instead of 'Capabilities'.
21
+ # https://github.com/SeleniumHQ/selenium/blob/trunk/rb/lib/selenium/webdriver/common/options.rb
22
+ # Then, Ruby client also shoud move to the Options way.
23
+ # Appium's capabilities could change by depending on Appium versions. So it does not have
24
+ # standard options like chrome and firefox etc. So, the implementation should differ from
25
+ # other browsers. But here should inherit `Options` to follow Selenium.
34
26
  end
35
27
  end
36
28
  end
@@ -17,10 +17,6 @@ module Appium
17
17
  module Error
18
18
  class CoreError < StandardError; end
19
19
 
20
- # Capability related errors
21
- class NoCapabilityError < CoreError; end
22
- class CapabilityStructureError < CoreError; end
23
-
24
20
  # Appium related errors
25
21
  class NotSupportedAppiumServer < CoreError; end
26
22
  class NoSuchElementError < CoreError; end
@@ -293,8 +293,11 @@ module Appium
293
293
  @delegate_target = self # for testing purpose
294
294
  @automation_name = nil # initialise before 'set_automation_name'
295
295
 
296
- opts = Appium.symbolize_keys opts
297
- validate_keys(opts)
296
+ # TODO: Remove when we implement Options
297
+ # The symbolize_keys is to keep compatiility for the legacy code, which allows capabilities to give 'string' as the key.
298
+ # The toplevel `caps`, `capabilities` and `appium_lib` are expected to be symbol.
299
+ # FIXME: First, please try to remove `nested: true` to `nested: false`.
300
+ opts = Appium.symbolize_keys(opts, nested: true)
298
301
 
299
302
  @custom_url = opts.delete :url
300
303
  @caps = get_caps(opts)
@@ -371,7 +374,7 @@ module Appium
371
374
  begin
372
375
  @driver = ::Appium::Core::Base::Driver.new(listener: @listener,
373
376
  http_client: @http_client,
374
- capabilities: @caps, # ::Selenium::WebDriver::Remote::Capabilities
377
+ capabilities: @caps, # ::Appium::Core::Base::Capabilities
375
378
  url: @custom_url,
376
379
  wait_timeout: @wait_timeout,
377
380
  wait_interval: @wait_interval,
@@ -489,14 +492,24 @@ module Appium
489
492
 
490
493
  private
491
494
 
495
+ def convert_to_symbol(value)
496
+ if value.nil?
497
+ value
498
+ else
499
+ value.to_sym
500
+ end
501
+ end
502
+
492
503
  # @private
493
504
  def extend_for(device:, automation_name:) # rubocop:disable Metrics/CyclomaticComplexity
494
505
  extend Appium::Core
495
506
  extend Appium::Core::Device
496
507
 
497
- case device
508
+ sym_automation_name = convert_to_symbol(automation_name)
509
+
510
+ case convert_to_symbol(device)
498
511
  when :android
499
- case automation_name
512
+ case sym_automation_name
500
513
  when :espresso
501
514
  ::Appium::Core::Android::Espresso::Bridge.for self
502
515
  when :uiautomator2
@@ -507,7 +520,7 @@ module Appium
507
520
  ::Appium::Core::Android::Uiautomator1::Bridge.for self
508
521
  end
509
522
  when :ios, :tvos
510
- case automation_name
523
+ case sym_automation_name
511
524
  when :safari
512
525
  ::Appium::Logger.debug('SafariDriver for iOS')
513
526
  when :xcuitest
@@ -516,7 +529,7 @@ module Appium
516
529
  ::Appium::Core::Ios::Uiautomation::Bridge.for self
517
530
  end
518
531
  when :mac
519
- case automation_name
532
+ case sym_automation_name
520
533
  when :safari
521
534
  ::Appium::Logger.debug('SafariDriver for macOS')
522
535
  when :gecko
@@ -528,7 +541,7 @@ module Appium
528
541
  ::Appium::Logger.debug('macOS Native')
529
542
  end
530
543
  when :windows
531
- case automation_name
544
+ case sym_automation_name
532
545
  when :gecko
533
546
  ::Appium::Logger.debug('Gecko Driver for Windows')
534
547
  else
@@ -538,7 +551,7 @@ module Appium
538
551
  # https://github.com/Samsung/appium-tizen-driver
539
552
  ::Appium::Logger.debug('tizen')
540
553
  else
541
- case automation_name
554
+ case sym_automation_name
542
555
  when :youiengine
543
556
  # https://github.com/YOU-i-Labs/appium-youiengine-driver
544
557
  ::Appium::Logger.debug('YouiEngine')
@@ -555,32 +568,9 @@ module Appium
555
568
  self
556
569
  end
557
570
 
558
- # @private
559
- def validate_keys(opts)
560
- flatten_ops = flatten_hash_keys(opts)
561
-
562
- raise Error::NoCapabilityError unless opts.member?(:caps) || opts.member?(:capabilities)
563
-
564
- if !opts.member?(:appium_lib) && flatten_ops.member?(:appium_lib)
565
- raise Error::CapabilityStructureError, 'Please check the value of appium_lib in the capability'
566
- end
567
-
568
- true
569
- end
570
-
571
- # @private
572
- def flatten_hash_keys(hash, flatten_keys_result = [])
573
- hash.each do |key, value|
574
- flatten_keys_result << key
575
- flatten_hash_keys(value, flatten_keys_result) if value.is_a?(Hash)
576
- end
577
-
578
- flatten_keys_result
579
- end
580
-
581
571
  # @private
582
572
  def get_caps(opts)
583
- Core::Base::Capabilities.create_capabilities(opts[:caps] || opts[:capabilities] || {})
573
+ Core::Base::Capabilities.new(opts[:caps] || opts[:capabilities] || {})
584
574
  end
585
575
 
586
576
  # @private
@@ -593,6 +583,7 @@ module Appium
593
583
  # The path can be local, HTTP/S, Windows Share and other path like 'sauce-storage:'.
594
584
  # Use @caps[:app] without modifications if the path isn't HTTP/S or local path.
595
585
  def set_app_path
586
+ # FIXME: maybe `:app` should check `app` as well.
596
587
  return unless @caps && @caps[:app] && !@caps[:app].empty?
597
588
  return if @caps[:app] =~ URI::DEFAULT_PARSER.make_regexp
598
589
 
@@ -631,7 +622,8 @@ module Appium
631
622
  # @private
632
623
  def set_appium_device
633
624
  # https://code.google.com/p/selenium/source/browse/spec-draft.md?repo=mobile
634
- @device = @caps[:platformName]
625
+ # TODO: check if the Appium.symbolize_keys(opts, nested: false) enoug with this
626
+ @device = @caps[:platformName] || @caps['platformName']
635
627
  return @device unless @device
636
628
 
637
629
  @device = @device.is_a?(Symbol) ? @device.downcase : @device.downcase.strip.intern
@@ -639,7 +631,9 @@ module Appium
639
631
 
640
632
  # @private
641
633
  def set_automation_name
642
- @automation_name = @caps[:automationName] if @caps[:automationName]
634
+ # TODO: check if the Appium.symbolize_keys(opts, nested: false) enoug with this
635
+ candidate = @caps[:automationName] || @caps['automationName']
636
+ @automation_name = candidate if candidate
643
637
  @automation_name = if @automation_name
644
638
  @automation_name.is_a?(Symbol) ? @automation_name.downcase : @automation_name.downcase.strip.intern
645
639
  end
@@ -14,7 +14,7 @@
14
14
 
15
15
  module Appium
16
16
  module Core
17
- VERSION = '5.4.0' unless defined? ::Appium::Core::VERSION
18
- DATE = '2022-10-01' unless defined? ::Appium::Core::DATE
17
+ VERSION = '5.5.1' unless defined? ::Appium::Core::VERSION
18
+ DATE = '2022-10-10' unless defined? ::Appium::Core::DATE
19
19
  end
20
20
  end
@@ -21,16 +21,25 @@ require_relative 'appium_lib_core/device'
21
21
  require_relative 'appium_lib_core/element'
22
22
 
23
23
  module Appium
24
- # convert all keys (including nested) to symbols
24
+ # @private
25
+ #
26
+ # convert the top level keys to symbols.
25
27
  #
26
- # based on deep_symbolize_keys & deep_transform_keys from rails
27
- # https://github.com/rails/docrails/blob/a3b1105ada3da64acfa3843b164b14b734456a50/activesupport/lib/active_support/core_ext/hash/keys.rb#L84
28
28
  # @param [Hash] hash Hash value to make symbolise
29
- def self.symbolize_keys(hash)
29
+ def self.symbolize_keys(hash, nested: false, enable_deprecation_msg: true)
30
+ # FIXME: As https://github.com/appium/ruby_lib/issues/945, we must remove this implicit string to symbol.
31
+ # But appium_lib_core's some capability handling expect to be symbol, so we should test to remove
32
+ # the mehotds which expect the symbol first.
30
33
  raise ::Appium::Core::Error::ArgumentError, 'symbolize_keys requires a hash' unless hash.is_a? Hash
31
34
 
32
35
  hash.each_with_object({}) do |pair, acc|
33
36
  key = begin
37
+ if enable_deprecation_msg && !(pair[0].is_a? Symbol)
38
+ ::Appium::Logger.warn("[Deprecation] The key '#{pair[0]}' must be a symbol while currently it " \
39
+ "is #{pair[0].class.name}. Please define the key as a Symbol. " \
40
+ 'Converting it to Symbol for now.')
41
+ end
42
+
34
43
  pair[0].to_sym
35
44
  rescue StandardError => e
36
45
  ::Appium::Logger.warn(e.message)
@@ -38,7 +47,11 @@ module Appium
38
47
  end
39
48
 
40
49
  value = pair[1]
41
- acc[key] = value.is_a?(Hash) ? symbolize_keys(value) : value
50
+ acc[key] = if nested
51
+ value.is_a?(Hash) ? symbolize_keys(value, nested: false, enable_deprecation_msg: true) : value
52
+ else
53
+ value
54
+ end
42
55
  end
43
56
  end
44
57
 
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: appium_lib_core
3
3
  version: !ruby/object:Gem::Version
4
- version: 5.4.0
4
+ version: 5.5.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - Kazuaki MATSUO
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2022-10-01 00:00:00.000000000 Z
11
+ date: 2022-10-10 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: selenium-webdriver