appium_lib_core 0.1.1 → 1.0.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.rubocop.yml +6 -0
- data/.travis.yml +1 -1
- data/CHANGELOG.md +4 -2
- data/README.md +66 -8
- data/Rakefile +13 -2
- data/appium_lib_core.gemspec +1 -1
- data/lib/appium_lib_core/android/device.rb +1 -1
- data/lib/appium_lib_core/common/base/bridge.rb +6 -6
- data/lib/appium_lib_core/common/base/driver.rb +1 -1
- data/lib/appium_lib_core/common/base/wait.rb +2 -2
- data/lib/appium_lib_core/common/command.rb +1 -1
- data/lib/appium_lib_core/common/device.rb +66 -57
- data/lib/appium_lib_core/device/multi_touch.rb +4 -10
- data/lib/appium_lib_core/device/touch_actions.rb +14 -12
- data/lib/appium_lib_core/driver.rb +28 -23
- data/lib/appium_lib_core/version.rb +2 -2
- data/release_notes.md +18 -0
- data/script/commands.rb +184 -0
- metadata +7 -6
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: e078b7ab6ce69ac4202cb8bfbf1669a621a1f7c3
|
4
|
+
data.tar.gz: 9f9ad00010a0ae6204d5aa92c5838ff5abc2b9a3
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: e128a4e5e56dd1456eee1d3fbc74b2a966254a7cc9bf420b64a70a71122a22913dfb87b843dd6f5c3b88a701ebec8d07e357cd20c5403b026c3dab1e163cbcc9
|
7
|
+
data.tar.gz: da0230b20ef8544d892f87f1caf2f1c2dd5c959bacf2ee5b99f2a673c7269d1d957608e5912204d476491271c8a480137594793775b9438c5c47d611167f02dd
|
data/.rubocop.yml
CHANGED
@@ -1,3 +1,5 @@
|
|
1
|
+
AllCops:
|
2
|
+
TargetRubyVersion: 2.2
|
1
3
|
Metrics/LineLength:
|
2
4
|
Max: 128
|
3
5
|
Metrics/MethodLength:
|
@@ -16,5 +18,9 @@ Style/Documentation:
|
|
16
18
|
Enabled: false
|
17
19
|
Style/AccessorMethodName:
|
18
20
|
Enabled: false
|
21
|
+
Style/CommentedKeyword:
|
22
|
+
Enabled: false
|
23
|
+
Style/PercentLiteralDelimiters:
|
24
|
+
Enabled: false
|
19
25
|
Lint/NestedMethodDefinition:
|
20
26
|
Enabled: false
|
data/.travis.yml
CHANGED
data/CHANGELOG.md
CHANGED
data/README.md
CHANGED
@@ -2,35 +2,93 @@
|
|
2
2
|
|
3
3
|
[![Gem Version](https://badge.fury.io/rb/appium_lib_core.svg)](https://badge.fury.io/rb/appium_lib_core)
|
4
4
|
|
5
|
+
|
6
|
+
[![Build Status](https://travis-ci.org/appium/ruby_lib_core.svg?branch=master)](https://travis-ci.org/appium/ruby_lib_core)
|
7
|
+
|
5
8
|
# Documentation
|
6
9
|
|
7
10
|
- http://www.rubydoc.info/github/appium/ruby_lib_core
|
8
11
|
|
9
|
-
#
|
12
|
+
# Related library
|
10
13
|
- https://github.com/appium/ruby_lib
|
11
14
|
|
12
15
|
# How to start
|
13
|
-
##
|
16
|
+
## Run tests
|
17
|
+
### Unit Tests
|
18
|
+
Run unit tests which check each method and commands, URL, using the webmock.
|
14
19
|
|
15
20
|
```bash
|
21
|
+
$ bundle install
|
22
|
+
$ rake test:unit
|
23
|
+
```
|
24
|
+
|
25
|
+
### Functional Tests
|
26
|
+
Run functional tests which require the Appium server and real device, Simulator/Emulator.
|
27
|
+
|
28
|
+
- Start Appium server
|
29
|
+
```bash
|
16
30
|
$ npm install -g appium
|
17
31
|
$ appium
|
18
32
|
```
|
19
33
|
|
20
|
-
|
21
|
-
|
22
|
-
```bash
|
34
|
+
- Conduct tests
|
35
|
+
```bash
|
23
36
|
$ bundle install
|
24
|
-
$ rake test:func:android # Andorid
|
37
|
+
$ rake test:func:android # Andorid
|
25
38
|
$ rake test:func:ios # iOS
|
26
39
|
```
|
27
40
|
|
41
|
+
## Run a test case
|
42
|
+
1. Launch the Appium server locally.
|
43
|
+
2. Run the following script.
|
44
|
+
|
45
|
+
- `test.rb`
|
46
|
+
```ruby
|
47
|
+
require 'rubygems'
|
48
|
+
require 'appium_lib_core'
|
49
|
+
|
50
|
+
opts = {
|
51
|
+
caps: {
|
52
|
+
platformName: :ios,
|
53
|
+
platformVersion: '11.0',
|
54
|
+
deviceName: 'iPhone Simulator',
|
55
|
+
automationName: 'XCUITest',
|
56
|
+
app: '/path/to/MyiOS.app'
|
57
|
+
},
|
58
|
+
appium_lib: {
|
59
|
+
wait: 30
|
60
|
+
}
|
61
|
+
}
|
62
|
+
@core = Appium::Core.for(self, opts) # create a core driver with `opts` and extend methods into `self`
|
63
|
+
@driver = @core.start_driver
|
64
|
+
|
65
|
+
# Launch iPhone Simulator and `MyiOS.app`
|
66
|
+
@driver.find_element(:accessibility_id, 'some accessibility') # find an element
|
67
|
+
```
|
68
|
+
|
69
|
+
- Run the script
|
70
|
+
```bash
|
71
|
+
# shell 1
|
72
|
+
$ appium
|
73
|
+
|
74
|
+
# shell 2
|
75
|
+
$ ruby test.rb
|
76
|
+
```
|
77
|
+
|
28
78
|
# Release
|
79
|
+
Use [appium_thor](https://github.com/appium/appium_thor) to release this gem.
|
29
80
|
|
30
81
|
```bash
|
31
|
-
$
|
32
|
-
$
|
82
|
+
$ thor bump # bumpy,
|
83
|
+
$ thor release
|
33
84
|
```
|
34
85
|
|
86
|
+
# Contribution
|
87
|
+
1. Fork it ( https://github.com/appium/ruby_lib_core/fork )
|
88
|
+
2. Create your feature branch (git checkout -b my-new-feature)
|
89
|
+
3. Commit your changes (git commit -am 'Add some feature')
|
90
|
+
4. Push to the branch (git push origin my-new-feature)
|
91
|
+
5. Create new Pull Request
|
92
|
+
|
35
93
|
# License
|
36
94
|
Apache License v2
|
data/Rakefile
CHANGED
@@ -54,9 +54,20 @@ YARD::Rake::YardocTask.new do |t|
|
|
54
54
|
t.files = ['lib/**/*.rb']
|
55
55
|
end
|
56
56
|
|
57
|
-
desc
|
57
|
+
desc('Execute RuboCop static code analysis')
|
58
58
|
RuboCop::RakeTask.new(:rubocop) do |t|
|
59
|
-
t.patterns = %w(lib test)
|
59
|
+
t.patterns = %w(lib test script)
|
60
60
|
t.options = %w(-D)
|
61
61
|
t.fail_on_error = true
|
62
62
|
end
|
63
|
+
|
64
|
+
desc("print commands which haven't implemented yet.")
|
65
|
+
namespace :commands do
|
66
|
+
task :mjsonwp do |_t, _args|
|
67
|
+
require './script/commands'
|
68
|
+
c = Script::CommandsChecker.new
|
69
|
+
c.get_mjsonwp_routes
|
70
|
+
c.get_all_command_path './mjsonwp_routes.js'
|
71
|
+
c.all_diff_commands_mjsonwp.each { |key, value| puts("command: #{key}, method: #{value}") }
|
72
|
+
end
|
73
|
+
end
|
data/appium_lib_core.gemspec
CHANGED
@@ -32,6 +32,6 @@ Gem::Specification.new do |spec|
|
|
32
32
|
spec.add_development_dependency 'minitest-reporters', '~> 1.1'
|
33
33
|
spec.add_development_dependency 'webmock', '~> 3.1.0'
|
34
34
|
spec.add_development_dependency 'pry'
|
35
|
-
spec.add_development_dependency 'rubocop'
|
35
|
+
spec.add_development_dependency 'rubocop', '0.51.0'
|
36
36
|
spec.add_development_dependency 'appium_thor', '~> 0.0', '>= 0.0.7'
|
37
37
|
end
|
@@ -118,7 +118,7 @@ module Appium
|
|
118
118
|
app_wait_package = opts.fetch(:app_wait_package, '')
|
119
119
|
app_wait_activity = opts.fetch(:app_wait_activity, '')
|
120
120
|
|
121
|
-
unknown_opts = opts.keys -
|
121
|
+
unknown_opts = opts.keys - %i(app_package app_activity app_wait_package app_wait_activity)
|
122
122
|
raise "Unknown options #{unknown_opts}" unless unknown_opts.empty?
|
123
123
|
|
124
124
|
execute :start_activity, {}, appPackage: app_package,
|
@@ -16,8 +16,8 @@ module Appium
|
|
16
16
|
capabilities = bridge.create_session(desired_capabilities)
|
17
17
|
|
18
18
|
case bridge.dialect
|
19
|
-
when :oss
|
20
|
-
|
19
|
+
when :oss # for MJSONWP
|
20
|
+
CoreBridgeMJSONWP.new(capabilities, bridge.session_id, opts)
|
21
21
|
when :w3c
|
22
22
|
CoreBridgeW3C.new(capabilities, bridge.session_id, opts)
|
23
23
|
else
|
@@ -26,17 +26,17 @@ module Appium
|
|
26
26
|
end
|
27
27
|
end # class Bridge
|
28
28
|
|
29
|
-
class
|
29
|
+
class CoreBridgeMJSONWP < ::Selenium::WebDriver::Remote::OSS::Bridge
|
30
30
|
def commands(command)
|
31
|
-
::Appium::Core::Commands::
|
31
|
+
::Appium::Core::Commands::COMMANDS_EXTEND_MJSONWP[command]
|
32
32
|
end
|
33
|
-
end # class
|
33
|
+
end # class CoreBridgeMJSONWP
|
34
34
|
|
35
35
|
class CoreBridgeW3C < ::Selenium::WebDriver::Remote::W3C::Bridge
|
36
36
|
def commands(command)
|
37
37
|
case command
|
38
38
|
when :status, :is_element_displayed
|
39
|
-
::Appium::Core::Commands::
|
39
|
+
::Appium::Core::Commands::COMMANDS_EXTEND_MJSONWP[command]
|
40
40
|
else
|
41
41
|
::Appium::Core::Commands::COMMANDS_EXTEND_W3C[command]
|
42
42
|
end
|
@@ -16,7 +16,7 @@ module Appium
|
|
16
16
|
def initialize(opts = {})
|
17
17
|
listener = opts.delete(:listener)
|
18
18
|
@bridge = ::Appium::Core::Base::Bridge.handshake(opts)
|
19
|
-
if @bridge.dialect == :oss
|
19
|
+
if @bridge.dialect == :oss # MJSONWP
|
20
20
|
extend ::Selenium::WebDriver::DriverExtensions::HasTouchScreen
|
21
21
|
extend ::Selenium::WebDriver::DriverExtensions::HasLocation
|
22
22
|
extend ::Selenium::WebDriver::DriverExtensions::HasNetworkConnection
|
@@ -6,9 +6,9 @@ module Appium
|
|
6
6
|
require 'timeout' # for wait
|
7
7
|
|
8
8
|
def initialize(opts = {})
|
9
|
-
valid_keys =
|
9
|
+
valid_keys = %i(timeout interval message ignore return_if_true)
|
10
10
|
invalid_keys = []
|
11
|
-
opts.
|
11
|
+
opts.each_key { |key| invalid_keys << key unless valid_keys.include?(key) }
|
12
12
|
# [:one, :two] => :one, :two
|
13
13
|
unless invalid_keys.empty?
|
14
14
|
raise "Invalid keys #{invalid_keys.to_s[1..-2]}. Valid keys are #{valid_keys.to_s[1..-2]}"
|
@@ -70,7 +70,7 @@ module Appium
|
|
70
70
|
COMMANDS = {}.merge(COMMAND).merge(COMMAND_ANDROID).merge(COMMAND_IOS)
|
71
71
|
.merge(COMMAND_NO_ARG).freeze
|
72
72
|
|
73
|
-
|
73
|
+
COMMANDS_EXTEND_MJSONWP = COMMANDS.merge(::Appium::Core::Base::Commands::OSS).freeze
|
74
74
|
COMMANDS_EXTEND_W3C = COMMANDS.merge(::Appium::Core::Base::Commands::W3C).freeze
|
75
75
|
end
|
76
76
|
end
|
@@ -264,6 +264,48 @@ module Appium
|
|
264
264
|
# ime_deactivate #=> Deactivate current IME engine
|
265
265
|
#
|
266
266
|
|
267
|
+
# @!method set_context(context)
|
268
|
+
# Change the context to the given context.
|
269
|
+
# @param [String] context The context to change to
|
270
|
+
#
|
271
|
+
# @example
|
272
|
+
#
|
273
|
+
# @driver.set_context "NATIVE_APP"
|
274
|
+
#
|
275
|
+
|
276
|
+
# @!method current_context
|
277
|
+
# @return [String] The context currently being used.
|
278
|
+
#
|
279
|
+
# @example
|
280
|
+
#
|
281
|
+
# @driver.current_context
|
282
|
+
#
|
283
|
+
|
284
|
+
# @!method available_contexts
|
285
|
+
# @return [Array<String>] All usable contexts, as an array of strings.
|
286
|
+
#
|
287
|
+
# @example
|
288
|
+
#
|
289
|
+
# @driver.available_contexts
|
290
|
+
#
|
291
|
+
|
292
|
+
# Perform a block within the given context, then switch back to the starting context.
|
293
|
+
# @param [String] context The context to switch to for the duration of the block.
|
294
|
+
#
|
295
|
+
# @example
|
296
|
+
#
|
297
|
+
# result = @driver.within_context('NATIVE_APP') do
|
298
|
+
# @driver.find_element :tag, "button"
|
299
|
+
# end # The result of `find_element :tag, "button"`
|
300
|
+
#
|
301
|
+
|
302
|
+
# Change to the default context. This is equivalent to `set_context nil`.
|
303
|
+
#
|
304
|
+
# @example
|
305
|
+
#
|
306
|
+
# @driver.switch_to_default_context
|
307
|
+
#
|
308
|
+
|
267
309
|
####
|
268
310
|
## class << self
|
269
311
|
####
|
@@ -283,8 +325,8 @@ module Appium
|
|
283
325
|
end
|
284
326
|
end
|
285
327
|
|
286
|
-
#
|
287
|
-
# ::Appium::Core::Base::Commands::
|
328
|
+
# Don't define selenium-side methods. We pick up from them.
|
329
|
+
# ::Appium::Core::Base::Commands::MJSONWP.each_key do |method|
|
288
330
|
# add_endpoint_method method
|
289
331
|
# end
|
290
332
|
|
@@ -414,6 +456,7 @@ module Appium
|
|
414
456
|
|
415
457
|
add_touch_actions
|
416
458
|
add_ime_actions
|
459
|
+
add_handling_context
|
417
460
|
end
|
418
461
|
|
419
462
|
# def extended
|
@@ -447,7 +490,7 @@ module Appium
|
|
447
490
|
|
448
491
|
# @private
|
449
492
|
def create_bridge_command(method)
|
450
|
-
::Appium::Core::Base::
|
493
|
+
::Appium::Core::Base::CoreBridgeMJSONWP.class_eval do
|
451
494
|
block_given? ? class_eval(&Proc.new) : define_method(method) { execute method }
|
452
495
|
end
|
453
496
|
::Appium::Core::Base::CoreBridgeW3C.class_eval do
|
@@ -505,63 +548,29 @@ module Appium
|
|
505
548
|
end
|
506
549
|
end
|
507
550
|
end
|
508
|
-
end # class << self
|
509
|
-
|
510
|
-
# @!method set_context(context)
|
511
|
-
# Change the context to the given context.
|
512
|
-
# @param [String] context The context to change to
|
513
|
-
#
|
514
|
-
# @example
|
515
|
-
#
|
516
|
-
# @driver.set_context "NATIVE_APP"
|
517
|
-
#
|
518
|
-
|
519
|
-
# @!method current_context
|
520
|
-
# @return [String] The context currently being used.
|
521
|
-
#
|
522
|
-
# @example
|
523
|
-
#
|
524
|
-
# @driver.current_context
|
525
|
-
#
|
526
551
|
|
527
|
-
|
528
|
-
|
529
|
-
|
530
|
-
|
531
|
-
|
532
|
-
|
533
|
-
|
552
|
+
def add_handling_context
|
553
|
+
add_endpoint_method(:within_context) do
|
554
|
+
def within_context(context)
|
555
|
+
existing_context = current_context
|
556
|
+
set_context context
|
557
|
+
if block_given?
|
558
|
+
result = yield
|
559
|
+
set_context existing_context
|
560
|
+
result
|
561
|
+
else
|
562
|
+
set_context existing_context
|
563
|
+
end
|
564
|
+
end
|
565
|
+
end
|
534
566
|
|
535
|
-
|
536
|
-
|
537
|
-
|
538
|
-
|
539
|
-
|
540
|
-
# result = @driver.within_context('NATIVE_APP') do
|
541
|
-
# @driver.find_element :tag, "button"
|
542
|
-
# end # The result of `find_element :tag, "button"`
|
543
|
-
#
|
544
|
-
def within_context(context)
|
545
|
-
existing_context = current_context
|
546
|
-
set_context context
|
547
|
-
if block_given?
|
548
|
-
result = yield
|
549
|
-
set_context existing_context
|
550
|
-
result
|
551
|
-
else
|
552
|
-
set_context existing_context
|
567
|
+
add_endpoint_method(:switch_to_default_context) do
|
568
|
+
def switch_to_default_context
|
569
|
+
set_context nil
|
570
|
+
end
|
571
|
+
end
|
553
572
|
end
|
554
|
-
end
|
555
|
-
|
556
|
-
# Change to the default context. This is equivalent to `set_context nil`.
|
557
|
-
#
|
558
|
-
# @example
|
559
|
-
#
|
560
|
-
# @driver.switch_to_default_context
|
561
|
-
#
|
562
|
-
def switch_to_default_context
|
563
|
-
set_context nil
|
564
|
-
end
|
573
|
+
end # class << self
|
565
574
|
end # module Device
|
566
575
|
end # module Core
|
567
576
|
end # module Appium
|
@@ -9,17 +9,11 @@ module Appium
|
|
9
9
|
#
|
10
10
|
# @example
|
11
11
|
#
|
12
|
-
#
|
13
|
-
#
|
12
|
+
# @driver = Appium::Core.for(self, opts).start_driver
|
13
|
+
# action_1 = TouchAction.new(@driver).press(x: 45, y: 100).wait(5).release
|
14
|
+
# action_2 = TouchAction.new(@driver).tap(element: el, x: 50, y:5, count: 3)
|
14
15
|
#
|
15
|
-
# multi_touch_action = MultiTouch.new
|
16
|
-
# multi_touch_action.add action_1
|
17
|
-
# multi_touch_action.add action_2
|
18
|
-
# multi_touch_action.perform
|
19
|
-
#
|
20
|
-
# # with an arbitrary driver
|
21
|
-
# driver = Appium::Driver.new(opts, false).start_driver
|
22
|
-
# multi_touch_action = MultiTouch.new(driver)
|
16
|
+
# multi_touch_action = MultiTouch.new(@driver)
|
23
17
|
# multi_touch_action.add action_1
|
24
18
|
# multi_touch_action.add action_2
|
25
19
|
# multi_touch_action.perform
|
@@ -4,16 +4,18 @@ module Appium
|
|
4
4
|
#
|
5
5
|
# Each method returns the object itself, so calls can be chained.
|
6
6
|
#
|
7
|
-
#
|
8
|
-
#
|
9
|
-
#
|
10
|
-
#
|
11
|
-
#
|
12
|
-
#
|
7
|
+
# @example
|
8
|
+
#
|
9
|
+
# @driver = Appium::Core.for(self, opts).start_driver
|
10
|
+
# action = TouchAction.new(@driver).press(x: 45, y: 100).wait(5).release
|
11
|
+
# action.perform
|
12
|
+
# action = TouchAction.new(@driver).swipe(....)
|
13
|
+
# action.perform
|
14
|
+
#
|
13
15
|
module Core
|
14
16
|
class TouchAction
|
15
|
-
ACTIONS
|
16
|
-
COMPLEX_ACTIONS =
|
17
|
+
ACTIONS = %i(move_to long_press double_tap two_finger_tap press release tap wait perform).freeze
|
18
|
+
COMPLEX_ACTIONS = %i(swipe).freeze
|
17
19
|
|
18
20
|
attr_reader :actions, :driver
|
19
21
|
|
@@ -44,7 +46,7 @@ module Appium
|
|
44
46
|
# @option y [integer] y co-ordinate to press on.
|
45
47
|
# @option duration [integer] Number of milliseconds to press.
|
46
48
|
def long_press(opts)
|
47
|
-
args = opts.select { |k, _v|
|
49
|
+
args = opts.select { |k, _v| %i(element x y duration).include? k }
|
48
50
|
args = args_with_ele_ref(args)
|
49
51
|
chain_method(:longPress, args) # longPress is what the appium server expects
|
50
52
|
end
|
@@ -56,7 +58,7 @@ module Appium
|
|
56
58
|
# @option opts [integer] :x x co-ordinate to press on
|
57
59
|
# @option opts [integer] :y y co-ordinate to press on
|
58
60
|
def press(opts)
|
59
|
-
args = opts.select { |k, _v|
|
61
|
+
args = opts.select { |k, _v| %i(element x y).include? k }
|
60
62
|
args = args_with_ele_ref(args)
|
61
63
|
chain_method(:press, args)
|
62
64
|
end
|
@@ -92,7 +94,7 @@ module Appium
|
|
92
94
|
# @option opts [integer] :y y co-ordinate to tap
|
93
95
|
|
94
96
|
def double_tap(opts)
|
95
|
-
args = opts.select { |k, _v|
|
97
|
+
args = opts.select { |k, _v| %i(element x y).include? k }
|
96
98
|
args = args_with_ele_ref(args)
|
97
99
|
chain_method(:doubleTap, args) # doubleTap is what the appium server expects
|
98
100
|
end
|
@@ -103,7 +105,7 @@ module Appium
|
|
103
105
|
# @option opts [integer] :x x co-ordinate to tap
|
104
106
|
# @option opts [integer] :y y co-ordinate to tap
|
105
107
|
def two_finger_tap(opts)
|
106
|
-
args = opts.select { |k, _v|
|
108
|
+
args = opts.select { |k, _v| %i(element x y).include? k }
|
107
109
|
args = args_with_ele_ref(args)
|
108
110
|
chain_method(:twoFingerTap, args) # twoFingerTap is what the appium server expects
|
109
111
|
end
|
@@ -18,41 +18,42 @@ module Appium
|
|
18
18
|
# @return [Hash]
|
19
19
|
attr_reader :automation_name
|
20
20
|
|
21
|
-
# Custom URL for the selenium server. If set this attribute,
|
21
|
+
# Custom URL for the selenium server. If set this attribute, ruby_lib_core try to handshake to the custom url.
|
22
|
+
# False is by default and then "http://127.0.0.1:#{@port}/wd/hub" is used.
|
22
23
|
# @return [String]
|
23
24
|
attr_reader :custom_url
|
24
25
|
|
25
|
-
# Export session id to textfile in /tmp for 3rd party tools
|
26
|
+
# Export session id to textfile in /tmp for 3rd party tools. False bu default.
|
26
27
|
# @return [Boolean]
|
27
28
|
attr_reader :export_session
|
28
29
|
# @return [String] By default, session id is exported in '/tmp/appium_lib_session'
|
29
30
|
attr_reader :export_session_path
|
30
31
|
|
31
32
|
# Default wait time for elements to appear
|
32
|
-
# Returns the default client side wait.
|
33
|
-
#
|
34
|
-
# Provide Appium::Drive like { appium_lib: { wait: 20 } }
|
33
|
+
# Returns the default client side wait. 20 second is by default.
|
34
|
+
# Provide Appium::Drive like { appium_lib: { wait: 30 } }
|
35
35
|
# @return [Integer]
|
36
36
|
attr_reader :default_wait
|
37
37
|
|
38
|
-
# Appium's server port
|
38
|
+
# Appium's server port. 4723 is by default.
|
39
39
|
# Provide Appium::Drive like { appium_lib: { port: 8080 } }
|
40
40
|
# @return [Integer]
|
41
41
|
attr_reader :port
|
42
42
|
|
43
|
-
# Return a time wait timeout
|
43
|
+
# Return a time wait timeout. 30 second is by default.
|
44
44
|
# Wait time for ::Appium::Core::Base::Wait, wait and wait_true
|
45
45
|
# Provide Appium::Drive like { appium_lib: { wait_timeout: 20 } }
|
46
46
|
# @return [Integer]
|
47
47
|
attr_reader :wait_timeout
|
48
48
|
|
49
|
-
# Return a time wait
|
49
|
+
# Return a time to wait interval. 0.5 second is by default.
|
50
50
|
# Wait interval time for ::Appium::Core::Base::Wait, wait and wait_true
|
51
|
-
# Provide Appium::Drive like { appium_lib: { wait_interval:
|
51
|
+
# Provide Appium::Drive like { appium_lib: { wait_interval: 0.1 } }
|
52
52
|
# @return [Integer]
|
53
53
|
attr_reader :wait_interval
|
54
54
|
|
55
55
|
# instance of AbstractEventListener for logging support
|
56
|
+
# Nil by default
|
56
57
|
attr_reader :listener
|
57
58
|
|
58
59
|
# @return [Appium::Core::Base::Driver]
|
@@ -66,12 +67,15 @@ module Appium
|
|
66
67
|
# @example
|
67
68
|
#
|
68
69
|
# require 'rubygems'
|
69
|
-
# require '
|
70
|
+
# require 'appium_lib_core'
|
70
71
|
#
|
71
72
|
# # Start iOS driver
|
72
73
|
# opts = {
|
73
74
|
# caps: {
|
74
75
|
# platformName: :ios,
|
76
|
+
# platformVersion: '11.0',
|
77
|
+
# deviceName: 'iPhone Simulator',
|
78
|
+
# automationName: 'XCUITest',
|
75
79
|
# app: '/path/to/MyiOS.app'
|
76
80
|
# },
|
77
81
|
# appium_lib: {
|
@@ -84,8 +88,8 @@ module Appium
|
|
84
88
|
# listener: nil,
|
85
89
|
# }
|
86
90
|
# }
|
87
|
-
# @
|
88
|
-
# @
|
91
|
+
# @core = Appium::Core.for(self, opts) # create a core driver with `opts` and extend methods into `self`
|
92
|
+
# @core.start_driver(server_url: server_url) # start driver
|
89
93
|
#
|
90
94
|
def self.for(target, opts = {})
|
91
95
|
new(target, opts)
|
@@ -105,7 +109,7 @@ module Appium
|
|
105
109
|
|
106
110
|
extend_for(device: @device, automation_name: @automation_name, target: target)
|
107
111
|
|
108
|
-
self
|
112
|
+
self # rubocop:disable Lint/Void
|
109
113
|
end
|
110
114
|
|
111
115
|
# Creates a new global driver and quits the old one if it exists.
|
@@ -120,7 +124,7 @@ module Appium
|
|
120
124
|
# @example
|
121
125
|
#
|
122
126
|
# require 'rubygems'
|
123
|
-
# require '
|
127
|
+
# require 'appium_lib_core'
|
124
128
|
#
|
125
129
|
# # platformName takes a string or a symbol.
|
126
130
|
#
|
@@ -128,24 +132,25 @@ module Appium
|
|
128
132
|
# opts = {
|
129
133
|
# caps: {
|
130
134
|
# platformName: :ios,
|
135
|
+
# platformVersion: '11.0',
|
136
|
+
# deviceName: 'iPhone Simulator',
|
137
|
+
# automationName: 'XCUITest',
|
131
138
|
# app: '/path/to/MyiOS.app'
|
132
139
|
# },
|
133
140
|
# appium_lib: {
|
134
|
-
#
|
135
|
-
# export_session: false,
|
136
|
-
# port: 8080,
|
137
|
-
# wait: 0,
|
141
|
+
# wait: 20,
|
138
142
|
# wait_timeout: 20,
|
139
143
|
# wait_interval: 0.3,
|
140
|
-
# listener: nil,
|
141
144
|
# }
|
142
145
|
# }
|
143
|
-
#
|
146
|
+
#
|
147
|
+
# @core = Appium::Core.for(self, opts) # create a core driver with `opts` and extend methods into `self`
|
144
148
|
# @driver = @core.start_driver
|
145
149
|
#
|
150
|
+
|
146
151
|
def start_driver(server_url: nil,
|
147
152
|
http_client_ops: { http_client: nil, open_timeout: 999_999, read_timeout: 999_999 })
|
148
|
-
server_url
|
153
|
+
server_url ||= "http://127.0.0.1:#{@port}/wd/hub"
|
149
154
|
|
150
155
|
# open_timeout and read_timeout are explicit wait.
|
151
156
|
open_timeout = http_client_ops.delete(:open_timeout)
|
@@ -204,7 +209,7 @@ module Appium
|
|
204
209
|
#
|
205
210
|
def quit_driver
|
206
211
|
@driver.quit
|
207
|
-
rescue
|
212
|
+
rescue # rubocop:disable Lint/RescueWithoutErrorClass
|
208
213
|
nil
|
209
214
|
end
|
210
215
|
|
@@ -407,7 +412,7 @@ module Appium
|
|
407
412
|
# @private
|
408
413
|
def set_appium_lib_specific_values(appium_lib_opts)
|
409
414
|
@custom_url = appium_lib_opts.fetch :server_url, false
|
410
|
-
@default_wait = appium_lib_opts.fetch :wait,
|
415
|
+
@default_wait = appium_lib_opts.fetch :wait, 20
|
411
416
|
|
412
417
|
# bump current session id into a particular file
|
413
418
|
@export_session = appium_lib_opts.fetch :export_session, false
|
@@ -1,6 +1,6 @@
|
|
1
1
|
module Appium
|
2
2
|
module Core
|
3
|
-
VERSION = '0.
|
4
|
-
DATE = '2017-11-
|
3
|
+
VERSION = '1.0.0'.freeze unless defined? ::Appium::Core::VERSION
|
4
|
+
DATE = '2017-11-12'.freeze unless defined? ::Appium::Core::DATE
|
5
5
|
end
|
6
6
|
end
|
data/release_notes.md
CHANGED
@@ -1,3 +1,21 @@
|
|
1
|
+
#### v1.0.0 2017-11-12
|
2
|
+
|
3
|
+
- [de176fe](https://github.com/appium/ruby_lib_core/commit/de176fe2fbcfaa341392e7f37ee537158ed2e23e) Release 1.0.0
|
4
|
+
- [00fb812](https://github.com/appium/ruby_lib_core/commit/00fb812c71696cc2d265fc3921fb9fbffb4b0d62) update changelog
|
5
|
+
- [30a60ef](https://github.com/appium/ruby_lib_core/commit/30a60ef932e04dbb4e2c0d3619b8f0f36e0b3e26) add script to get diff commands (#9)
|
6
|
+
- [445cf6a](https://github.com/appium/ruby_lib_core/commit/445cf6ab4c3b5fc7cbdec72a1c4f9ba064c2b08a) update comments for touch actions
|
7
|
+
- [1629f3a](https://github.com/appium/ruby_lib_core/commit/1629f3af6d6873171babc0d7231ba36a6b5a94fd) define MJSONWP instead of OSS (#8)
|
8
|
+
- [7b698ca](https://github.com/appium/ruby_lib_core/commit/7b698ca592d96289a8e6ae511e6533ab05ced59c) update readme (#7)
|
9
|
+
- [feb7f00](https://github.com/appium/ruby_lib_core/commit/feb7f009dad5d70e55f773f5b41467587720e6e3) add context related tests
|
10
|
+
- [2716285](https://github.com/appium/ruby_lib_core/commit/27162850c13a67a98a51fee432e21d1cb6df449b) add bundle exec for test
|
11
|
+
- [838c984](https://github.com/appium/ruby_lib_core/commit/838c9843b7342e1b530cbd6bbc92abc6c0ca7fb8) fix rubocop and set the version
|
12
|
+
- [a633825](https://github.com/appium/ruby_lib_core/commit/a633825fc9171407cde3d65c396a98a8cd961f02) set 2.2
|
13
|
+
- [4fee2c9](https://github.com/appium/ruby_lib_core/commit/4fee2c97377c4041cad4bfe583c044b42e6dc8d6) update documentation
|
14
|
+
- [a8b94c0](https://github.com/appium/ruby_lib_core/commit/a8b94c0159943edad0df901813c4a134b027f196) update documentation and comments
|
15
|
+
- [17bf48a](https://github.com/appium/ruby_lib_core/commit/17bf48af1f4bd33202d12c784fa2a78e63c30813) update driver test
|
16
|
+
- [7885baf](https://github.com/appium/ruby_lib_core/commit/7885baf4768abeb0d70ebc47174e3f97096a525e) add unit tests for w3c
|
17
|
+
|
18
|
+
|
1
19
|
#### v0.1.1 2017-11-04
|
2
20
|
|
3
21
|
- [e5adc6d](https://github.com/appium/ruby_lib_core/commit/e5adc6d8d4a5db312dc7c11c73445d78c6239ec5) Release 0.1.1
|
data/script/commands.rb
ADDED
@@ -0,0 +1,184 @@
|
|
1
|
+
require 'net/http'
|
2
|
+
require './lib/appium_lib_core'
|
3
|
+
|
4
|
+
module Script
|
5
|
+
class CommandsChecker
|
6
|
+
attr_reader :spec_commands
|
7
|
+
attr_reader :implemented_mjsonwp_commands, :implemented_w3c_commands, :implemented_core_commands
|
8
|
+
attr_reader :webdriver_oss_commands, :webdriver_w3c_commands
|
9
|
+
|
10
|
+
# Set commands implemented in this core library.
|
11
|
+
#
|
12
|
+
# - implemented_mjsonwp_commands: All commands include ::Selenium::WebDriver::Remote::OSS::Bridge::COMMANDS
|
13
|
+
# - implemented_w3c_commands: All commands include ::Selenium::WebDriver::Remote::W3C::Bridge::COMMANDS
|
14
|
+
# - implemented_core_commands: All commands except for selenium-webdriver's commands
|
15
|
+
# - webdriver_oss_commands: ::Selenium::WebDriver::Remote::OSS::Bridge::COMMANDS
|
16
|
+
# - webdriver_w3c_commands: ::Selenium::WebDriver::Remote::W3C::Bridge::COMMANDS
|
17
|
+
#
|
18
|
+
def initialize
|
19
|
+
@implemented_mjsonwp_commands = convert_driver_commands Appium::Core::Commands::COMMANDS_EXTEND_MJSONWP
|
20
|
+
@implemented_w3c_commands = convert_driver_commands Appium::Core::Commands::COMMANDS_EXTEND_W3C
|
21
|
+
@implemented_core_commands = convert_driver_commands Appium::Core::Commands::COMMANDS
|
22
|
+
|
23
|
+
@webdriver_oss_commands = convert_driver_commands Appium::Core::Base::Commands::OSS
|
24
|
+
@webdriver_w3c_commands = convert_driver_commands Appium::Core::Base::Commands::W3C
|
25
|
+
end
|
26
|
+
|
27
|
+
# Get the bellow url's file.
|
28
|
+
# https://raw.githubusercontent.com/appium/appium-base-driver/master/lib/mjsonwp/routes.js?raw=1
|
29
|
+
#
|
30
|
+
# @param [String] to_path: A file path to routes.js
|
31
|
+
# @return [String] The file path in which has saved `routes.js`.
|
32
|
+
#
|
33
|
+
def get_mjsonwp_routes(to_path = './mjsonwp_routes.js')
|
34
|
+
uri = URI 'https://raw.githubusercontent.com/appium/appium-base-driver/master/lib/mjsonwp/routes.js?raw=1'
|
35
|
+
result = Net::HTTP.get uri
|
36
|
+
|
37
|
+
File.delete to_path
|
38
|
+
File.write to_path, result
|
39
|
+
to_path
|
40
|
+
end
|
41
|
+
|
42
|
+
# @private
|
43
|
+
HTTP_METHOD_MATCH = /GET:|POST:|DELETE:|PUT:|PATCH:/
|
44
|
+
# @private
|
45
|
+
WD_HUB_PREFIX_MATCH = "'/wd/hub/".freeze
|
46
|
+
|
47
|
+
# Read routes.js and set the values in @spec_commands
|
48
|
+
#
|
49
|
+
# @param [String] path: A file path to routes.js
|
50
|
+
# @return [Hash] @spec_commands
|
51
|
+
#
|
52
|
+
def get_all_command_path(path = './mjsonwp_routes.js')
|
53
|
+
raise "No file in #{path}" unless File.exist? path
|
54
|
+
|
55
|
+
current_command = ''
|
56
|
+
@spec_commands = File.read(path).lines.each_with_object({}) do |line, memo|
|
57
|
+
if line =~ /#{WD_HUB_PREFIX_MATCH}.+'/
|
58
|
+
current_command = gsub_set(line.slice(/#{WD_HUB_PREFIX_MATCH}.+'/))
|
59
|
+
memo[current_command] = []
|
60
|
+
elsif line =~ HTTP_METHOD_MATCH
|
61
|
+
memo[current_command] << line.slice(HTTP_METHOD_MATCH).chop.downcase.to_sym
|
62
|
+
end
|
63
|
+
memo
|
64
|
+
end
|
65
|
+
end
|
66
|
+
|
67
|
+
# All commands which haven't been implemented in ruby core library yet.
|
68
|
+
# @return [Hash]
|
69
|
+
#
|
70
|
+
def all_diff_commands_mjsonwp
|
71
|
+
result = compare_commands(@spec_commands, @implemented_mjsonwp_commands)
|
72
|
+
|
73
|
+
white_list.each { |v| result.delete v }
|
74
|
+
w3c_spec.each { |v| result.delete v }
|
75
|
+
|
76
|
+
result
|
77
|
+
end
|
78
|
+
|
79
|
+
# All commands which haven't been implemented in ruby core library yet.
|
80
|
+
# @return [Hash]
|
81
|
+
#
|
82
|
+
def all_diff_commands_w3c
|
83
|
+
result = compare_commands(@spec_commands, @implemented_w3c_commands)
|
84
|
+
white_list.each { |v| result.delete v }
|
85
|
+
mjsonwp_spec.each { |v| result.delete v }
|
86
|
+
result
|
87
|
+
end
|
88
|
+
|
89
|
+
# Commands, only this core library, which haven't been implemented in ruby core library yet.
|
90
|
+
# @return [Hash]
|
91
|
+
#
|
92
|
+
def diff_except_for_webdriver
|
93
|
+
result = compare_commands(@spec_commands, @implemented_core_commands)
|
94
|
+
white_list.each { |v| result.delete v }
|
95
|
+
result
|
96
|
+
end
|
97
|
+
|
98
|
+
def diff_webdriver_oss
|
99
|
+
result = compare_commands(@spec_commands, @webdriver_oss_commands)
|
100
|
+
white_list.each { |v| result.delete v }
|
101
|
+
w3c_spec.each { |v| result.delete v }
|
102
|
+
result
|
103
|
+
end
|
104
|
+
|
105
|
+
def diff_webdriver_w3c
|
106
|
+
result = compare_commands(@spec_commands, @webdriver_w3c_commands)
|
107
|
+
white_list.each { |v| result.delete v }
|
108
|
+
mjsonwp_spec.each { |v| result.delete v }
|
109
|
+
result
|
110
|
+
end
|
111
|
+
|
112
|
+
def compare_commands(command1, with_command2)
|
113
|
+
return {} if command1.nil?
|
114
|
+
return command1 if with_command2.nil?
|
115
|
+
|
116
|
+
result = {}
|
117
|
+
command1.each_key do |key|
|
118
|
+
if with_command2.key? key
|
119
|
+
diff = command1[key] - with_command2[key]
|
120
|
+
result[key] = diff unless diff.empty?
|
121
|
+
else
|
122
|
+
result[key] = command1[key]
|
123
|
+
end
|
124
|
+
end
|
125
|
+
result
|
126
|
+
end
|
127
|
+
|
128
|
+
private
|
129
|
+
|
130
|
+
# rubocop:disable Lint/PercentStringArray
|
131
|
+
def white_list
|
132
|
+
%w(
|
133
|
+
'/wd/hub/session'
|
134
|
+
'/wd/hub/sessions'
|
135
|
+
).map { |v| gsub_set(v) }
|
136
|
+
end
|
137
|
+
|
138
|
+
# https://raw.githubusercontent.com/appium/appium-base-driver/master/lib/mjsonwp/routes.js
|
139
|
+
def mjsonwp_spec
|
140
|
+
%w(
|
141
|
+
'/wd/hub/session/:sessionId/alert_text'
|
142
|
+
'/wd/hub/session/:sessionId/accept_alert'
|
143
|
+
'/wd/hub/session/:sessionId/dismiss_alert'
|
144
|
+
).map { |v| gsub_set(v) }
|
145
|
+
end
|
146
|
+
|
147
|
+
def w3c_spec
|
148
|
+
%w(
|
149
|
+
'/wd/hub/session/:sessionId/alert/text'
|
150
|
+
'/wd/hub/session/:sessionId/alert/accept'
|
151
|
+
'/wd/hub/session/:sessionId/alert/dismiss'
|
152
|
+
'/wd/hub/session/:sessionId/element/:elementId/rect'
|
153
|
+
).map { |v| gsub_set(v) }
|
154
|
+
end
|
155
|
+
# rubocop:enable Lint/PercentStringArray
|
156
|
+
|
157
|
+
def gsub_set(line)
|
158
|
+
return nil if line.gsub(/(\A#{WD_HUB_PREFIX_MATCH}|'\z)/, '').nil?
|
159
|
+
|
160
|
+
line.gsub(/(\A#{WD_HUB_PREFIX_MATCH}|'\z)/, '')
|
161
|
+
.sub(':sessionId', ':session_id')
|
162
|
+
.sub('element/:elementId', 'element/:id')
|
163
|
+
.sub(':windowhandle', ':window_handle')
|
164
|
+
.sub('equals/:otherId', 'equals/:other')
|
165
|
+
.sub('css/:propertyName', 'css/:property_name')
|
166
|
+
.sub('element/:id/pageIndex', 'element/:id/page_index')
|
167
|
+
end
|
168
|
+
|
169
|
+
def convert_driver_commands(from)
|
170
|
+
from.each_with_object({}) do |command, memo|
|
171
|
+
method = command[1][0]
|
172
|
+
key = command[1][1]
|
173
|
+
|
174
|
+
if memo[key]
|
175
|
+
memo[key] << method
|
176
|
+
else
|
177
|
+
memo[key] = [method]
|
178
|
+
end
|
179
|
+
|
180
|
+
memo
|
181
|
+
end
|
182
|
+
end
|
183
|
+
end
|
184
|
+
end
|
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: 0.
|
4
|
+
version: 1.0.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Kazuaki MATSUO
|
8
8
|
autorequire:
|
9
9
|
bindir: exe
|
10
10
|
cert_chain: []
|
11
|
-
date: 2017-11-
|
11
|
+
date: 2017-11-12 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: selenium-webdriver
|
@@ -146,16 +146,16 @@ dependencies:
|
|
146
146
|
name: rubocop
|
147
147
|
requirement: !ruby/object:Gem::Requirement
|
148
148
|
requirements:
|
149
|
-
- -
|
149
|
+
- - '='
|
150
150
|
- !ruby/object:Gem::Version
|
151
|
-
version:
|
151
|
+
version: 0.51.0
|
152
152
|
type: :development
|
153
153
|
prerelease: false
|
154
154
|
version_requirements: !ruby/object:Gem::Requirement
|
155
155
|
requirements:
|
156
|
-
- -
|
156
|
+
- - '='
|
157
157
|
- !ruby/object:Gem::Version
|
158
|
-
version:
|
158
|
+
version: 0.51.0
|
159
159
|
- !ruby/object:Gem::Dependency
|
160
160
|
name: appium_thor
|
161
161
|
requirement: !ruby/object:Gem::Requirement
|
@@ -235,6 +235,7 @@ files:
|
|
235
235
|
- lib/appium_lib_core/patch.rb
|
236
236
|
- lib/appium_lib_core/version.rb
|
237
237
|
- release_notes.md
|
238
|
+
- script/commands.rb
|
238
239
|
homepage: https://github.com/appium/ruby_lib_core/
|
239
240
|
licenses:
|
240
241
|
- Apache-2.0
|