appium_lib 9.6.1 → 9.7.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.rubocop.yml +2 -2
- data/CHANGELOG.md +43 -0
- data/Rakefile +1 -1
- data/appium_lib.gemspec +1 -1
- data/docs/android_docs.md +440 -1295
- data/docs/docs.md +10 -103
- data/docs/index_paths.md +2 -0
- data/docs/ios_docs.md +725 -1674
- data/docs/migration.md +17 -0
- data/lib/appium_lib.rb +1 -2
- data/lib/appium_lib/android/android.rb +20 -0
- data/lib/appium_lib/android/{helper.rb → common/helper.rb} +1 -1
- data/lib/appium_lib/android/uiautomator2.rb +5 -4
- data/lib/appium_lib/android/uiautomator2/bridge.rb +16 -0
- data/lib/appium_lib/appium.rb +201 -0
- data/lib/appium_lib/common/helper.rb +18 -20
- data/lib/appium_lib/common/log.rb +24 -0
- data/lib/appium_lib/common/multi_touch.rb +89 -0
- data/lib/appium_lib/common/touch_actions.rb +48 -0
- data/lib/appium_lib/common/wait.rb +10 -49
- data/lib/appium_lib/core/android.rb +4 -0
- data/lib/appium_lib/core/android/device.rb +142 -0
- data/lib/appium_lib/core/android/search_context.rb +17 -0
- data/lib/appium_lib/core/android/uiautomator1/bridge.rb +16 -0
- data/lib/appium_lib/core/android/uiautomator2/bridge.rb +16 -0
- data/lib/appium_lib/core/android_uiautomator2.rb +4 -0
- data/lib/appium_lib/core/common.rb +6 -0
- data/lib/appium_lib/core/common/base.rb +8 -0
- data/lib/appium_lib/core/common/base/bridge.rb +47 -0
- data/lib/appium_lib/core/common/base/capabilities.rb +16 -0
- data/lib/appium_lib/core/common/base/command.rb +10 -0
- data/lib/appium_lib/core/common/base/driver.rb +40 -0
- data/lib/appium_lib/core/common/base/http_default.rb +12 -0
- data/lib/appium_lib/core/common/base/search_context.rb +89 -0
- data/lib/appium_lib/core/common/base/wait.rb +56 -0
- data/lib/appium_lib/{common → core/common}/command.rb +20 -16
- data/lib/appium_lib/core/common/device.rb +470 -0
- data/lib/appium_lib/core/common/error.rb +13 -0
- data/lib/appium_lib/core/common/log.rb +30 -0
- data/lib/appium_lib/{logger.rb → core/common/logger.rb} +2 -0
- data/lib/appium_lib/core/core.rb +38 -0
- data/lib/appium_lib/core/device/multi_touch.rb +213 -0
- data/lib/appium_lib/core/device/touch_actions.rb +206 -0
- data/lib/appium_lib/core/driver.rb +274 -0
- data/lib/appium_lib/core/ios.rb +6 -0
- data/lib/appium_lib/core/ios/device.rb +44 -0
- data/lib/appium_lib/core/ios/search_context.rb +27 -0
- data/lib/appium_lib/core/ios/uiautomation/bridge.rb +17 -0
- data/lib/appium_lib/core/ios/uiautomation/patch.rb +20 -0
- data/lib/appium_lib/core/ios/xcuitest/bridge.rb +18 -0
- data/lib/appium_lib/{ios → core/ios}/xcuitest/device.rb +5 -5
- data/lib/appium_lib/{ios → core/ios}/xcuitest/search_context.rb +13 -9
- data/lib/appium_lib/core/ios_xcuitest.rb +7 -0
- data/lib/appium_lib/core/patch.rb +56 -0
- data/lib/appium_lib/driver.rb +174 -446
- data/lib/appium_lib/ios/{errors.rb → common/errors.rb} +0 -0
- data/lib/appium_lib/ios/{helper.rb → common/helper.rb} +9 -110
- data/lib/appium_lib/ios/ios.rb +20 -0
- data/lib/appium_lib/ios/xcuitest.rb +1 -3
- data/lib/appium_lib/ios/xcuitest/bridge.rb +19 -0
- data/lib/appium_lib/ios/xcuitest/command.rb +4 -1
- data/lib/appium_lib/ios/xcuitest/{gestures.rb → command/gestures.rb} +1 -1
- data/lib/appium_lib/ios/xcuitest/element.rb +1 -18
- data/lib/appium_lib/ios/xcuitest/helper.rb +0 -6
- data/lib/appium_lib/sauce_labs.rb +29 -0
- data/lib/appium_lib/version.rb +5 -0
- data/release_notes.md +8 -0
- metadata +50 -25
- data/lib/appium_lib/android/client_xpath.rb +0 -51
- data/lib/appium_lib/android/device.rb +0 -39
- data/lib/appium_lib/android/mobile_methods.rb +0 -15
- data/lib/appium_lib/android/patch.rb +0 -16
- data/lib/appium_lib/capabilities.rb +0 -13
- data/lib/appium_lib/common/element/window.rb +0 -10
- data/lib/appium_lib/common/error.rb +0 -8
- data/lib/appium_lib/common/patch.rb +0 -190
- data/lib/appium_lib/common/search_context.rb +0 -10
- data/lib/appium_lib/common/version.rb +0 -5
- data/lib/appium_lib/device/device.rb +0 -611
- data/lib/appium_lib/device/multi_touch.rb +0 -225
- data/lib/appium_lib/device/touch_actions.rb +0 -230
- data/lib/appium_lib/ios/mobile_methods.rb +0 -25
- data/lib/appium_lib/ios/patch.rb +0 -22
|
@@ -1,51 +0,0 @@
|
|
|
1
|
-
require 'nokogiri'
|
|
2
|
-
|
|
3
|
-
module Appium
|
|
4
|
-
module Android
|
|
5
|
-
def _nodeset_to_uiselector(opts = {})
|
|
6
|
-
results = ''
|
|
7
|
-
|
|
8
|
-
nodes = opts[:nodes]
|
|
9
|
-
first = opts[:first]
|
|
10
|
-
|
|
11
|
-
nodes = [nodes[0]] if first
|
|
12
|
-
|
|
13
|
-
nodes.each do |node|
|
|
14
|
-
results += %(new UiSelector().className("#{node.name}").instance(#{node.attr('instance')});)
|
|
15
|
-
end
|
|
16
|
-
|
|
17
|
-
results.strip
|
|
18
|
-
end
|
|
19
|
-
|
|
20
|
-
def _client_xpath(opts = {})
|
|
21
|
-
root_node = Nokogiri::XML(get_source).children.first
|
|
22
|
-
|
|
23
|
-
instance = Hash.new(-1)
|
|
24
|
-
|
|
25
|
-
root_node.traverse do |node|
|
|
26
|
-
number = instance[node.name] += 1
|
|
27
|
-
node.set_attribute 'instance', number
|
|
28
|
-
end
|
|
29
|
-
|
|
30
|
-
nodes = root_node.xpath(opts[:xpath])
|
|
31
|
-
first = opts[:first]
|
|
32
|
-
|
|
33
|
-
_nodeset_to_uiselector nodes: nodes, first: first
|
|
34
|
-
end
|
|
35
|
-
|
|
36
|
-
# @deprecated Please use :uiautomator or :xpath strategy directly
|
|
37
|
-
def client_xpath(xpath)
|
|
38
|
-
warn '[DEPRECATION] client_xpath will be removed. Please use :uiautomator or :xpath strategy directly.'
|
|
39
|
-
find_element :uiautomator, _client_xpath(xpath: xpath, first: true)
|
|
40
|
-
end
|
|
41
|
-
|
|
42
|
-
# @deprecated Please use :uiautomator or :xpath strategy directly
|
|
43
|
-
def client_xpaths(xpath)
|
|
44
|
-
warn '[DEPRECATION] client_xpaths will be removed. Please use :uiautomator or :xpath strategy directly.'
|
|
45
|
-
find_elements :uiautomator, _client_xpath(xpath: xpath, first: false)
|
|
46
|
-
end
|
|
47
|
-
end
|
|
48
|
-
end
|
|
49
|
-
|
|
50
|
-
# http://stackoverflow.com/questions/9199415/getting-first-node-in-xpath-result-set
|
|
51
|
-
# '(//android.widget.TextView)[1]' not '//android.widget.TextView[1]'
|
|
@@ -1,39 +0,0 @@
|
|
|
1
|
-
require 'base64'
|
|
2
|
-
|
|
3
|
-
module Appium
|
|
4
|
-
module Android
|
|
5
|
-
module Device
|
|
6
|
-
extend Forwardable
|
|
7
|
-
|
|
8
|
-
# @!method hide_keyboard
|
|
9
|
-
# Hide the onscreen keyboard
|
|
10
|
-
# @param [String] close_key The name of the key which closes the keyboard.
|
|
11
|
-
# Defaults to 'Done' for iOS(except for XCUITest).
|
|
12
|
-
# @param [Symbol] strategy The symbol of the strategy which closes the keyboard.
|
|
13
|
-
# XCUITest ignore this argument.
|
|
14
|
-
# Default for iOS is `:pressKey`. Default for Android is `:tapOutside`.
|
|
15
|
-
# ```ruby
|
|
16
|
-
# hide_keyboard # Close a keyboard with the 'Done' button
|
|
17
|
-
# hide_keyboard('Finished') # Close a keyboard with the 'Finished' button
|
|
18
|
-
# hide_keyboard(nil, :tapOutside) # Close a keyboard with tapping out side of keyboard
|
|
19
|
-
# ```
|
|
20
|
-
|
|
21
|
-
class << self
|
|
22
|
-
def extended(_mod)
|
|
23
|
-
::Appium::Device.extend_webdriver_with_forwardable
|
|
24
|
-
|
|
25
|
-
::Appium::Device.add_endpoint_method(:hide_keyboard) do
|
|
26
|
-
def hide_keyboard(close_key = nil, strategy = nil)
|
|
27
|
-
option = {}
|
|
28
|
-
|
|
29
|
-
option[:key] = close_key if close_key
|
|
30
|
-
option[:strategy] = strategy || :tapOutside # default to pressKey
|
|
31
|
-
|
|
32
|
-
execute :hide_keyboard, {}, option
|
|
33
|
-
end
|
|
34
|
-
end
|
|
35
|
-
end
|
|
36
|
-
end # class << self
|
|
37
|
-
end # module Device
|
|
38
|
-
end # module Android
|
|
39
|
-
end # module Appium
|
|
@@ -1,15 +0,0 @@
|
|
|
1
|
-
module Appium
|
|
2
|
-
module Android
|
|
3
|
-
class << self
|
|
4
|
-
# @!method uiautomator_find
|
|
5
|
-
# find_element/s can be used with a [UISelector](http://developer.android.com/tools/help/uiautomator/UiSelector.html).
|
|
6
|
-
#
|
|
7
|
-
# ```ruby
|
|
8
|
-
# find_elements :uiautomator, 'new UiSelector().clickable(true)'
|
|
9
|
-
# ```
|
|
10
|
-
def extended(_mod)
|
|
11
|
-
::Appium::Driver::SearchContext::FINDERS[:uiautomator] = '-android uiautomator'
|
|
12
|
-
end
|
|
13
|
-
end # class << self
|
|
14
|
-
end # module Android
|
|
15
|
-
end # module Appium
|
|
@@ -1,16 +0,0 @@
|
|
|
1
|
-
module Appium
|
|
2
|
-
module Android
|
|
3
|
-
# @private
|
|
4
|
-
# class_eval inside a method because class Selenium::WebDriver::Element
|
|
5
|
-
# will trigger as soon as the file is required. in contrast a method
|
|
6
|
-
# will trigger only when invoked.
|
|
7
|
-
def patch_webdriver_element
|
|
8
|
-
Selenium::WebDriver::Element.class_eval do
|
|
9
|
-
# Cross platform way of entering text into a textfield
|
|
10
|
-
def type(text)
|
|
11
|
-
send_keys text
|
|
12
|
-
end
|
|
13
|
-
end
|
|
14
|
-
end
|
|
15
|
-
end # Android
|
|
16
|
-
end # Appium
|
|
@@ -1,13 +0,0 @@
|
|
|
1
|
-
module Appium
|
|
2
|
-
class Driver
|
|
3
|
-
module Capabilities
|
|
4
|
-
# @param [Hash] opts_caps Capabilities for Appium server. All capability keys are converted to lowerCamelCase when
|
|
5
|
-
# this client sends capabilities to Appium server as JSON format.
|
|
6
|
-
# @return [::Selenium::WebDriver::Remote::W3C::Capabilities] Return instance of Appium::Driver::Capabilities
|
|
7
|
-
# inherited ::Selenium::WebDriver::Remote::W3C::Capabilities
|
|
8
|
-
def self.init_caps_for_appium(opts_caps = {})
|
|
9
|
-
::Selenium::WebDriver::Remote::W3C::Capabilities.new(opts_caps)
|
|
10
|
-
end
|
|
11
|
-
end
|
|
12
|
-
end
|
|
13
|
-
end
|
|
@@ -1,190 +0,0 @@
|
|
|
1
|
-
require_relative 'version'
|
|
2
|
-
|
|
3
|
-
module Appium
|
|
4
|
-
module Common
|
|
5
|
-
# Implement useful features for element.
|
|
6
|
-
class Selenium::WebDriver::Element # rubocop:disable Style/ClassAndModuleChildren
|
|
7
|
-
# Note: For testing .text should be used over value, and name.
|
|
8
|
-
|
|
9
|
-
# Returns the value attribute
|
|
10
|
-
#
|
|
11
|
-
# Fixes NoMethodError: undefined method `value' for Selenium::WebDriver::Element
|
|
12
|
-
def value
|
|
13
|
-
attribute :value
|
|
14
|
-
end
|
|
15
|
-
|
|
16
|
-
# Returns the name attribute
|
|
17
|
-
#
|
|
18
|
-
# Fixes NoMethodError: undefined method `name' for Selenium::WebDriver::Element
|
|
19
|
-
def name
|
|
20
|
-
attribute :name
|
|
21
|
-
end
|
|
22
|
-
|
|
23
|
-
# For use with mobile tap.
|
|
24
|
-
#
|
|
25
|
-
# ```ruby
|
|
26
|
-
# execute_script 'mobile: tap', :x => 0.0, :y => 0.98
|
|
27
|
-
# ```
|
|
28
|
-
#
|
|
29
|
-
# @return [OpenStruct] the relative x, y in a struct. ex: { x: 0.50, y: 0.20 }
|
|
30
|
-
def location_rel(driver = $driver)
|
|
31
|
-
# TODO: Remove with 'refine Appium ruby binding'
|
|
32
|
-
# https://github.com/appium/ruby_lib/issues/602
|
|
33
|
-
if ::Appium.selenium_webdriver_version_more?('3.4.0')
|
|
34
|
-
rect = self.rect
|
|
35
|
-
location_x = rect.x.to_f
|
|
36
|
-
location_y = rect.y.to_f
|
|
37
|
-
|
|
38
|
-
size_width = rect.width.to_f
|
|
39
|
-
size_height = rect.height.to_f
|
|
40
|
-
else
|
|
41
|
-
location = self.location
|
|
42
|
-
location_x = location.x.to_f
|
|
43
|
-
location_y = location.y.to_f
|
|
44
|
-
|
|
45
|
-
size = self.size
|
|
46
|
-
size_width = size.width.to_f
|
|
47
|
-
size_height = size.height.to_f
|
|
48
|
-
end
|
|
49
|
-
|
|
50
|
-
center_x = location_x + (size_width / 2.0)
|
|
51
|
-
center_y = location_y + (size_height / 2.0)
|
|
52
|
-
|
|
53
|
-
w = driver.window_size
|
|
54
|
-
OpenStruct.new(x: "#{center_x} / #{w.width.to_f}",
|
|
55
|
-
y: "#{center_y} / #{w.height.to_f}")
|
|
56
|
-
end
|
|
57
|
-
end
|
|
58
|
-
end # module Common
|
|
59
|
-
end # module Appium
|
|
60
|
-
|
|
61
|
-
# Print JSON posted to Appium. Not scoped to an Appium module.
|
|
62
|
-
#
|
|
63
|
-
# Requires from lib/selenium/webdriver/remote.rb
|
|
64
|
-
require 'selenium/webdriver/remote/capabilities'
|
|
65
|
-
require 'selenium/webdriver/remote/w3c/capabilities'
|
|
66
|
-
require 'selenium/webdriver/remote/bridge'
|
|
67
|
-
require 'selenium/webdriver/remote/oss/bridge'
|
|
68
|
-
require 'selenium/webdriver/remote/w3c/bridge'
|
|
69
|
-
require 'selenium/webdriver/remote/server_error'
|
|
70
|
-
require 'selenium/webdriver/remote/response'
|
|
71
|
-
require 'selenium/webdriver/remote/oss/commands'
|
|
72
|
-
require 'selenium/webdriver/remote/w3c/commands'
|
|
73
|
-
require 'selenium/webdriver/remote/http/common'
|
|
74
|
-
require 'selenium/webdriver/remote/http/default'
|
|
75
|
-
|
|
76
|
-
# @private
|
|
77
|
-
# Show http calls to the Selenium server.
|
|
78
|
-
#
|
|
79
|
-
# Invaluable for debugging.
|
|
80
|
-
def patch_webdriver_bridge
|
|
81
|
-
Selenium::WebDriver::Remote::Bridge.class_eval do
|
|
82
|
-
# Code from lib/selenium/webdriver/remote/bridge.rb
|
|
83
|
-
|
|
84
|
-
def execute(command, opts = {}, command_hash = nil)
|
|
85
|
-
verb, path = commands(command) || raise(ArgumentError, "unknown command: #{command.inspect}")
|
|
86
|
-
path = path.dup
|
|
87
|
-
|
|
88
|
-
path[':session_id'] = @session_id if path.include?(':session_id')
|
|
89
|
-
|
|
90
|
-
begin
|
|
91
|
-
opts.each do |key, value|
|
|
92
|
-
path[key.inspect] = escaper.escape(value.to_s)
|
|
93
|
-
end
|
|
94
|
-
rescue IndexError
|
|
95
|
-
raise ArgumentError, "#{opts.inspect} invalid for #{command.inspect}"
|
|
96
|
-
end
|
|
97
|
-
|
|
98
|
-
# convert /// into /
|
|
99
|
-
path.gsub!(/\/+/, '/')
|
|
100
|
-
|
|
101
|
-
# change path from session/efac972c-941a-499c-803c-d7d008749/execute
|
|
102
|
-
# to /execute
|
|
103
|
-
# path may be nil, session, or not have anything after the session_id.
|
|
104
|
-
path_str = path
|
|
105
|
-
path_str = '/' + path_str unless path_str.nil? || path_str.length <= 0 || path_str[0] == '/'
|
|
106
|
-
path_match = path.match(/.*\h{8}-?\h{4}-?\h{4}-?\h{4}-?\h{12}/)
|
|
107
|
-
path_str = path.sub(path_match[0], '') unless path_match.nil?
|
|
108
|
-
|
|
109
|
-
Appium::Logger.info "#{verb} #{path_str}"
|
|
110
|
-
|
|
111
|
-
# must check to see if command_hash is a hash. sometimes it's not.
|
|
112
|
-
if command_hash.is_a?(Hash) && !command_hash.empty?
|
|
113
|
-
print_command = command_hash.clone
|
|
114
|
-
|
|
115
|
-
print_command.delete :args if print_command[:args] == []
|
|
116
|
-
|
|
117
|
-
if print_command[:using] == '-android uiautomator'
|
|
118
|
-
value = print_command[:value].split(';').map { |v| "#{v};" }
|
|
119
|
-
print_command[:value] = value.length == 1 ? value[0] : value
|
|
120
|
-
|
|
121
|
-
# avoid backslash escape quotes in strings. "\"a\"" => "a"
|
|
122
|
-
Appium::Logger.info print_command.ai.gsub('\"', '"')
|
|
123
|
-
else
|
|
124
|
-
Appium::Logger.ap_info print_command
|
|
125
|
-
end
|
|
126
|
-
elsif command_hash
|
|
127
|
-
# non-standard command hash
|
|
128
|
-
# It's important to output this for debugging problems.
|
|
129
|
-
# for example invalid JSON will not be a Hash
|
|
130
|
-
Appium::Logger.ap_info command_hash
|
|
131
|
-
end
|
|
132
|
-
|
|
133
|
-
if !$driver.nil? && $driver.global_webdriver_http_sleep
|
|
134
|
-
warn '[DEPRECATION] global_webdriver_http_sleep will be removed. Please arrange with timeout.'
|
|
135
|
-
|
|
136
|
-
delay = $driver.global_webdriver_http_sleep
|
|
137
|
-
sleep delay if delay > 0
|
|
138
|
-
end
|
|
139
|
-
# Appium::Logger.info "verb: #{verb}, path #{path}, command_hash #{command_hash.to_json}"
|
|
140
|
-
http.call(verb, path, command_hash)
|
|
141
|
-
end # def
|
|
142
|
-
end # class
|
|
143
|
-
end
|
|
144
|
-
|
|
145
|
-
# Print Appium's origValue error messages.
|
|
146
|
-
# rubocop:disable Style/ClassAndModuleChildren
|
|
147
|
-
# rubocop:disable Style/AndOr
|
|
148
|
-
class Selenium::WebDriver::Remote::Response
|
|
149
|
-
# @private
|
|
150
|
-
def error_message
|
|
151
|
-
val = value
|
|
152
|
-
|
|
153
|
-
case val
|
|
154
|
-
when Hash
|
|
155
|
-
msg = val['origValue'] || val['message'] or return 'unknown error'
|
|
156
|
-
msg << ": #{val['alert']['text'].inspect}" if val['alert'].is_a?(Hash) && val['alert']['text']
|
|
157
|
-
msg << " (#{val['class']})" if val['class']
|
|
158
|
-
when String
|
|
159
|
-
msg = val
|
|
160
|
-
else
|
|
161
|
-
msg = "unknown error, status=#{status}: #{val.inspect}"
|
|
162
|
-
end
|
|
163
|
-
|
|
164
|
-
msg
|
|
165
|
-
end
|
|
166
|
-
end
|
|
167
|
-
|
|
168
|
-
class Selenium::WebDriver::Remote::Http::Common # rubocop:disable Style/ClassAndModuleChildren
|
|
169
|
-
remove_const :DEFAULT_HEADERS if defined? DEFAULT_HEADERS
|
|
170
|
-
DEFAULT_HEADERS = { 'Accept' => CONTENT_TYPE, 'User-Agent' => "appium/ruby_lib/#{::Appium::VERSION}" }.freeze
|
|
171
|
-
end
|
|
172
|
-
|
|
173
|
-
def patch_remote_driver_commands
|
|
174
|
-
Selenium::WebDriver::Remote::OSS::Bridge.class_eval do
|
|
175
|
-
def commands(command)
|
|
176
|
-
::Appium::Driver::Commands::COMMANDS_EXTEND_OSS[command]
|
|
177
|
-
end
|
|
178
|
-
end
|
|
179
|
-
|
|
180
|
-
Selenium::WebDriver::Remote::W3C::Bridge.class_eval do
|
|
181
|
-
def commands(command)
|
|
182
|
-
case command
|
|
183
|
-
when :status, :is_element_displayed
|
|
184
|
-
::Appium::Driver::Commands::COMMANDS_EXTEND_OSS[command]
|
|
185
|
-
else
|
|
186
|
-
::Appium::Driver::Commands::COMMANDS_EXTEND_W3C[command]
|
|
187
|
-
end
|
|
188
|
-
end
|
|
189
|
-
end
|
|
190
|
-
end
|
|
@@ -1,611 +0,0 @@
|
|
|
1
|
-
require 'base64'
|
|
2
|
-
|
|
3
|
-
module Appium
|
|
4
|
-
module Device
|
|
5
|
-
extend Forwardable
|
|
6
|
-
|
|
7
|
-
# @!method app_strings
|
|
8
|
-
# Return the hash of all localization strings.
|
|
9
|
-
# ```ruby
|
|
10
|
-
# app_strings #=> "TransitionsTitle"=>"Transitions", "WebTitle"=>"Web"
|
|
11
|
-
# ```
|
|
12
|
-
|
|
13
|
-
# @!method background_app
|
|
14
|
-
# Backgrounds the app for a set number of seconds.
|
|
15
|
-
# This is a blocking application
|
|
16
|
-
# @param [Integer] seconds How many seconds to background the app for.
|
|
17
|
-
#
|
|
18
|
-
# ```ruby
|
|
19
|
-
# background_app
|
|
20
|
-
# background_app(5)
|
|
21
|
-
# background_app(-1) #=> the app never come back. https://github.com/appium/appium/issues/7741
|
|
22
|
-
# ```
|
|
23
|
-
|
|
24
|
-
# @!method current_activity
|
|
25
|
-
# Get current activity name
|
|
26
|
-
# @return [String] An activity name
|
|
27
|
-
#
|
|
28
|
-
# ```ruby
|
|
29
|
-
# current_activity # '.ApiDemos'
|
|
30
|
-
# ```
|
|
31
|
-
|
|
32
|
-
# @!method current_package
|
|
33
|
-
# Get current package name
|
|
34
|
-
# @return [String] A package name
|
|
35
|
-
#
|
|
36
|
-
# ```ruby
|
|
37
|
-
# current_package # 'com.example.android.apis'
|
|
38
|
-
# ```
|
|
39
|
-
|
|
40
|
-
# @!method get_system_bars
|
|
41
|
-
# Get system bar's information
|
|
42
|
-
# @return [String] System bar
|
|
43
|
-
#
|
|
44
|
-
# ```ruby
|
|
45
|
-
# get_system_bars
|
|
46
|
-
# ```
|
|
47
|
-
|
|
48
|
-
# @!method get_display_density
|
|
49
|
-
# Get connected device's density.
|
|
50
|
-
# @return [Integer] The size of density
|
|
51
|
-
#
|
|
52
|
-
# ```ruby
|
|
53
|
-
# get_display_density # 320
|
|
54
|
-
# ```
|
|
55
|
-
|
|
56
|
-
# @!method is_keyboard_shown
|
|
57
|
-
# Get whether keyboard is displayed or not.
|
|
58
|
-
# @return [Bool] Return true if keyboard is shown. Return false if keyboard is hidden.
|
|
59
|
-
#
|
|
60
|
-
# ```ruby
|
|
61
|
-
# is_keyboard_shown # false
|
|
62
|
-
# ```
|
|
63
|
-
|
|
64
|
-
# @!method launch_app
|
|
65
|
-
# Start the simulator and application configured with desired capabilities
|
|
66
|
-
|
|
67
|
-
# @!method reset
|
|
68
|
-
# Reset the device, relaunching the application.
|
|
69
|
-
|
|
70
|
-
# @!method shake
|
|
71
|
-
# Cause the device to shake
|
|
72
|
-
|
|
73
|
-
# @!method toggle_flight_mode
|
|
74
|
-
# Toggle flight mode on or off
|
|
75
|
-
|
|
76
|
-
# @!method device_locked?
|
|
77
|
-
|
|
78
|
-
# @!method hide_keyboard
|
|
79
|
-
# Hide the onscreen keyboard
|
|
80
|
-
# @param [String] close_key The name of the key which closes the keyboard.
|
|
81
|
-
# Defaults to 'Done' for iOS(except for XCUITest).
|
|
82
|
-
# @param [Symbol] strategy The symbol of the strategy which closes the keyboard.
|
|
83
|
-
# XCUITest ignore this argument.
|
|
84
|
-
# Default for iOS is `:pressKey`. Default for Android is `:tapOutside`.
|
|
85
|
-
# ```ruby
|
|
86
|
-
# hide_keyboard # Close a keyboard with the 'Done' button
|
|
87
|
-
# hide_keyboard('Finished') # Close a keyboard with the 'Finished' button
|
|
88
|
-
# hide_keyboard(nil, :tapOutside) # Close a keyboard with tapping out side of keyboard
|
|
89
|
-
# ```
|
|
90
|
-
|
|
91
|
-
# @!method press_keycode
|
|
92
|
-
# Press keycode on the device.
|
|
93
|
-
# http://developer.android.com/reference/android/view/KeyEvent.html
|
|
94
|
-
# @param [integer] key The key to press.
|
|
95
|
-
# @param [String] metastate The state the metakeys should be in when pressing the key.
|
|
96
|
-
|
|
97
|
-
# @!method long_press_keycode
|
|
98
|
-
# Long press keycode on the device.
|
|
99
|
-
# http://developer.android.com/reference/android/view/KeyEvent.html
|
|
100
|
-
# @param [integer] key The key to long press.
|
|
101
|
-
# @param [String] metastate The state the metakeys should be in when long pressing the key.
|
|
102
|
-
|
|
103
|
-
# @!method push_file
|
|
104
|
-
# Place a file in a specific location on the device.
|
|
105
|
-
# @param [String] path The absolute path on the device to store data at.
|
|
106
|
-
# @param [String] data Raw file data to be sent to the device.
|
|
107
|
-
|
|
108
|
-
# @!method pull_file
|
|
109
|
-
# Retrieve a file from the device. This can retrieve an absolute path or
|
|
110
|
-
# a path relative to the installed app (iOS only).
|
|
111
|
-
# @param [String] path Either an absolute path OR, for iOS devices, a path relative to the app, as described.
|
|
112
|
-
#
|
|
113
|
-
# ```ruby
|
|
114
|
-
# pull_file '/local/data/some/path' #=> Get the file at that path
|
|
115
|
-
# pull_file 'Shenanigans.app/some/file' #=> Get 'some/file' from the install location of Shenanigans.app
|
|
116
|
-
# ```
|
|
117
|
-
|
|
118
|
-
# @!method pull_folder
|
|
119
|
-
# Retrieve a folder from the device.
|
|
120
|
-
# @param [String] path absolute path to the folder
|
|
121
|
-
#
|
|
122
|
-
# ```ruby
|
|
123
|
-
# pull_folder '/data/local/tmp' #=> Get the folder at that path
|
|
124
|
-
# ```
|
|
125
|
-
|
|
126
|
-
# @!method touch_id
|
|
127
|
-
# iOS only; Simulate Touch ID with either valid (match == true) or invalid (match == false) fingerprint.
|
|
128
|
-
# @param [Boolean] match fingerprint validity
|
|
129
|
-
# Defaults to true.
|
|
130
|
-
# ```ruby
|
|
131
|
-
# touch_id true #=> Simulate valid fingerprint
|
|
132
|
-
# touch_id false #=> Simulate invalid fingerprint
|
|
133
|
-
# ```
|
|
134
|
-
|
|
135
|
-
# @!method toggle_touch_id_enrollment
|
|
136
|
-
# iOS Simulator only: Toggle touch id enrollment on an iOS Simulator.
|
|
137
|
-
|
|
138
|
-
# @!method end_coverage
|
|
139
|
-
# Android only; Ends the test coverage and writes the results to the given path on device.
|
|
140
|
-
# @param [String] path Path on the device to write too.
|
|
141
|
-
# @param [String] intent Intent to broadcast when ending coverage.
|
|
142
|
-
|
|
143
|
-
# @!method get_settings
|
|
144
|
-
# Get appium Settings for current test session
|
|
145
|
-
|
|
146
|
-
# @!method update_settings
|
|
147
|
-
# Update appium Settings for current test session
|
|
148
|
-
# @param [Hash] settings Settings to update, keys are settings, values to value to set each setting to
|
|
149
|
-
|
|
150
|
-
# @!method start_activity
|
|
151
|
-
# Start a new activity within the current app or launch a new app and start the target activity.
|
|
152
|
-
#
|
|
153
|
-
# Android only.
|
|
154
|
-
# @option [String] The package owning the activity [required]
|
|
155
|
-
# @option [String] The target activity [required]
|
|
156
|
-
# @option opts [String] The package to start before the target package [optional]
|
|
157
|
-
# @option opts [String] The activity to start before the target activity [optional]
|
|
158
|
-
#
|
|
159
|
-
# ```ruby
|
|
160
|
-
# start_activity app_package: 'io.appium.android.apis',
|
|
161
|
-
# app_activity: '.accessibility.AccessibilityNodeProviderActivity'
|
|
162
|
-
# ```
|
|
163
|
-
|
|
164
|
-
# @!method get_network_connection
|
|
165
|
-
# Get the device network connection current status
|
|
166
|
-
# See set_network_connection method for return value
|
|
167
|
-
|
|
168
|
-
# @!method set_network_connection
|
|
169
|
-
# Set the device network connection mode
|
|
170
|
-
# @param [String] path Bit mask that represent the network mode
|
|
171
|
-
#
|
|
172
|
-
# Value (Alias) | Data | Wifi | Airplane Mode
|
|
173
|
-
# -------------------------------------------------
|
|
174
|
-
# 1 (Airplane Mode) | 0 | 0 | 1
|
|
175
|
-
# 6 (All network on) | 1 | 1 | 0
|
|
176
|
-
# 4 (Data only) | 1 | 0 | 0
|
|
177
|
-
# 2 (Wifi only) | 0 | 1 | 0
|
|
178
|
-
# 0 (None) | 0 | 0 | 0
|
|
179
|
-
#
|
|
180
|
-
|
|
181
|
-
# @!method set_immediate_value
|
|
182
|
-
# Set the value to element directly
|
|
183
|
-
# for iOS; setValue is called in XCUITest instead because XCUITest doesn't provide set value directly.
|
|
184
|
-
# https://github.com/appium/appium-xcuitest-driver/blob/793cdc7d5e84bd553e375076e1c6dc7e242c9cde/lib/commands/element.js#L123
|
|
185
|
-
#
|
|
186
|
-
# ```ruby
|
|
187
|
-
# set_immediate_value element, 'hello'
|
|
188
|
-
# ```
|
|
189
|
-
|
|
190
|
-
# @!method get_performance_data_types
|
|
191
|
-
# Get the information type of the system state which is supported to read such as
|
|
192
|
-
# cpu, memory, network, battery via adb commands.
|
|
193
|
-
# https://github.com/appium/appium-base-driver/blob/be29aec2318316d12b5c3295e924a5ba8f09b0fb/lib/mjsonwp/routes.js#L300
|
|
194
|
-
#
|
|
195
|
-
# ```ruby
|
|
196
|
-
# get_performance_data_types #=> ["cpuinfo", "batteryinfo", "networkinfo", "memoryinfo"]
|
|
197
|
-
# ```
|
|
198
|
-
|
|
199
|
-
# @!method get_performance_data
|
|
200
|
-
# Get the resource usage information of the application.
|
|
201
|
-
# https://github.com/appium/appium-base-driver/blob/be29aec2318316d12b5c3295e924a5ba8f09b0fb/lib/mjsonwp/routes.js#L303
|
|
202
|
-
# @param [String] package_name Package name
|
|
203
|
-
# @param [String] data_type Data type get with `get_performance_data_types`
|
|
204
|
-
# @param [String] data_read_timeout Command timeout. Default is 2.
|
|
205
|
-
#
|
|
206
|
-
# ```ruby
|
|
207
|
-
# get_performance_data package_name: package_name, data_type: data_type, data_read_timeout: 2
|
|
208
|
-
# ```
|
|
209
|
-
class << self
|
|
210
|
-
def extended(_mod)
|
|
211
|
-
extend_webdriver_with_forwardable
|
|
212
|
-
|
|
213
|
-
::Appium::Driver::Commands::COMMAND_NO_ARG.each_key do |method|
|
|
214
|
-
add_endpoint_method method
|
|
215
|
-
end
|
|
216
|
-
|
|
217
|
-
add_endpoint_method(:available_contexts) do
|
|
218
|
-
def available_contexts
|
|
219
|
-
# return empty array instead of nil on failure
|
|
220
|
-
execute(:available_contexts, {}) || []
|
|
221
|
-
end
|
|
222
|
-
end
|
|
223
|
-
|
|
224
|
-
add_endpoint_method(:app_strings) do
|
|
225
|
-
def app_strings(language = nil)
|
|
226
|
-
opts = language ? { language: language } : {}
|
|
227
|
-
execute :app_strings, {}, opts
|
|
228
|
-
end
|
|
229
|
-
end
|
|
230
|
-
|
|
231
|
-
add_endpoint_method(:lock) do
|
|
232
|
-
def lock(duration)
|
|
233
|
-
execute :lock, {}, seconds: duration
|
|
234
|
-
end
|
|
235
|
-
end
|
|
236
|
-
|
|
237
|
-
add_endpoint_method(:install_app) do
|
|
238
|
-
def install_app(path)
|
|
239
|
-
execute :install_app, {}, appPath: path
|
|
240
|
-
end
|
|
241
|
-
end
|
|
242
|
-
|
|
243
|
-
add_endpoint_method(:remove_app) do
|
|
244
|
-
def remove_app(id)
|
|
245
|
-
execute :remove_app, {}, appId: id
|
|
246
|
-
end
|
|
247
|
-
end
|
|
248
|
-
|
|
249
|
-
add_endpoint_method(:app_installed?) do
|
|
250
|
-
def app_installed?(app_id)
|
|
251
|
-
execute :app_installed?, {}, bundleId: app_id
|
|
252
|
-
end
|
|
253
|
-
end
|
|
254
|
-
|
|
255
|
-
add_endpoint_method(:background_app) do
|
|
256
|
-
def background_app(duration = 0)
|
|
257
|
-
execute :background_app, {}, seconds: duration
|
|
258
|
-
end
|
|
259
|
-
end
|
|
260
|
-
|
|
261
|
-
add_endpoint_method(:start_activity) do
|
|
262
|
-
def start_activity(opts)
|
|
263
|
-
raise 'opts must be a hash' unless opts.is_a? Hash
|
|
264
|
-
app_package = opts[:app_package]
|
|
265
|
-
raise 'app_package is required' unless app_package
|
|
266
|
-
app_activity = opts[:app_activity]
|
|
267
|
-
raise 'app_activity is required' unless app_activity
|
|
268
|
-
app_wait_package = opts.fetch(:app_wait_package, '')
|
|
269
|
-
app_wait_activity = opts.fetch(:app_wait_activity, '')
|
|
270
|
-
|
|
271
|
-
unknown_opts = opts.keys - [:app_package, :app_activity, :app_wait_package, :app_wait_activity]
|
|
272
|
-
raise "Unknown options #{unknown_opts}" unless unknown_opts.empty?
|
|
273
|
-
|
|
274
|
-
execute :start_activity, {}, appPackage: app_package,
|
|
275
|
-
appActivity: app_activity,
|
|
276
|
-
appWaitPackage: app_wait_package,
|
|
277
|
-
appWaitActivity: app_wait_activity
|
|
278
|
-
end
|
|
279
|
-
end
|
|
280
|
-
|
|
281
|
-
add_endpoint_method(:set_context) do
|
|
282
|
-
def set_context(context = null)
|
|
283
|
-
execute :set_context, {}, name: context
|
|
284
|
-
end
|
|
285
|
-
end
|
|
286
|
-
|
|
287
|
-
add_endpoint_method(:hide_keyboard) do
|
|
288
|
-
def hide_keyboard(close_key = nil, strategy = nil)
|
|
289
|
-
option = {}
|
|
290
|
-
|
|
291
|
-
option[:key] = close_key || 'Done' # default to Done key.
|
|
292
|
-
option[:strategy] = strategy || :pressKey # default to pressKey
|
|
293
|
-
|
|
294
|
-
execute :hide_keyboard, {}, option
|
|
295
|
-
end
|
|
296
|
-
end
|
|
297
|
-
|
|
298
|
-
add_endpoint_method(:press_keycode) do
|
|
299
|
-
def press_keycode(key, metastate = nil)
|
|
300
|
-
args = { keycode: key }
|
|
301
|
-
args[:metastate] = metastate if metastate
|
|
302
|
-
execute :press_keycode, {}, args
|
|
303
|
-
end
|
|
304
|
-
end
|
|
305
|
-
|
|
306
|
-
add_endpoint_method(:long_press_keycode) do
|
|
307
|
-
def long_press_keycode(key, metastate = nil)
|
|
308
|
-
args = { keycode: key }
|
|
309
|
-
args[:metastate] = metastate if metastate
|
|
310
|
-
execute :long_press_keycode, {}, args
|
|
311
|
-
end
|
|
312
|
-
end
|
|
313
|
-
|
|
314
|
-
add_endpoint_method(:set_immediate_value) do
|
|
315
|
-
def set_immediate_value(element, *value)
|
|
316
|
-
keys = ::Selenium::WebDriver::Keys.encode(value)
|
|
317
|
-
execute :set_immediate_value, { id: element.ref }, value: Array(keys)
|
|
318
|
-
end
|
|
319
|
-
end
|
|
320
|
-
|
|
321
|
-
add_endpoint_method(:push_file) do
|
|
322
|
-
def push_file(path, filedata)
|
|
323
|
-
encoded_data = Base64.encode64 filedata
|
|
324
|
-
execute :push_file, {}, path: path, data: encoded_data
|
|
325
|
-
end
|
|
326
|
-
end
|
|
327
|
-
|
|
328
|
-
add_endpoint_method(:pull_file) do
|
|
329
|
-
def pull_file(path)
|
|
330
|
-
data = execute :pull_file, {}, path: path
|
|
331
|
-
Base64.decode64 data
|
|
332
|
-
end
|
|
333
|
-
end
|
|
334
|
-
|
|
335
|
-
# TODO: TEST ME
|
|
336
|
-
add_endpoint_method(:pull_folder) do
|
|
337
|
-
def pull_folder(path)
|
|
338
|
-
data = execute :pull_folder, {}, path: path
|
|
339
|
-
Base64.decode64 data
|
|
340
|
-
end
|
|
341
|
-
end
|
|
342
|
-
|
|
343
|
-
# TODO: TEST ME
|
|
344
|
-
add_endpoint_method(:touch_id) do
|
|
345
|
-
def touch_id(match = true)
|
|
346
|
-
execute :touch_id, {}, match: match
|
|
347
|
-
end
|
|
348
|
-
end
|
|
349
|
-
|
|
350
|
-
# TODO: TEST ME
|
|
351
|
-
add_endpoint_method(:toggle_touch_id_enrollment) do
|
|
352
|
-
def toggle_touch_id_enrollment
|
|
353
|
-
execute :toggle_touch_id_enrollment, {}
|
|
354
|
-
end
|
|
355
|
-
end
|
|
356
|
-
|
|
357
|
-
# TODO: TEST ME
|
|
358
|
-
add_endpoint_method(:end_coverage) do
|
|
359
|
-
def end_coverage(path, intent)
|
|
360
|
-
execute :end_coverage, {}, path: path, intent: intent
|
|
361
|
-
end
|
|
362
|
-
end
|
|
363
|
-
|
|
364
|
-
add_endpoint_method(:get_settings) do
|
|
365
|
-
def get_settings
|
|
366
|
-
execute :get_settings, {}
|
|
367
|
-
end
|
|
368
|
-
end
|
|
369
|
-
|
|
370
|
-
add_endpoint_method(:update_settings) do
|
|
371
|
-
def update_settings(settings)
|
|
372
|
-
execute :update_settings, {}, settings: settings
|
|
373
|
-
end
|
|
374
|
-
end
|
|
375
|
-
|
|
376
|
-
add_endpoint_method(:set_network_connection) do
|
|
377
|
-
def set_network_connection(mode)
|
|
378
|
-
execute :set_network_connection, {}, type: mode
|
|
379
|
-
end
|
|
380
|
-
end
|
|
381
|
-
|
|
382
|
-
add_endpoint_method(:get_performance_data) do
|
|
383
|
-
def get_performance_data(package_name:, data_type:, data_read_timeout: 1000)
|
|
384
|
-
execute :get_performance_data, {}, packageName: package_name,
|
|
385
|
-
dataType: data_type,
|
|
386
|
-
dataReadTimeout: data_read_timeout
|
|
387
|
-
end
|
|
388
|
-
end
|
|
389
|
-
|
|
390
|
-
add_touch_actions
|
|
391
|
-
add_ime_actions
|
|
392
|
-
extend_search_contexts
|
|
393
|
-
end
|
|
394
|
-
|
|
395
|
-
# def extended
|
|
396
|
-
|
|
397
|
-
# @private
|
|
398
|
-
def add_endpoint_method(method)
|
|
399
|
-
block_given? ? create_bridge_command(method, &Proc.new) : create_bridge_command(method)
|
|
400
|
-
|
|
401
|
-
delegate_driver_method method
|
|
402
|
-
delegate_from_appium_driver method
|
|
403
|
-
end
|
|
404
|
-
|
|
405
|
-
# @private
|
|
406
|
-
def extend_webdriver_with_forwardable
|
|
407
|
-
return if Selenium::WebDriver::Driver.is_a? Forwardable
|
|
408
|
-
Selenium::WebDriver::Driver.class_eval do
|
|
409
|
-
extend Forwardable
|
|
410
|
-
end
|
|
411
|
-
end
|
|
412
|
-
|
|
413
|
-
# @private
|
|
414
|
-
def delegate_driver_method(method)
|
|
415
|
-
return if Selenium::WebDriver::Driver.method_defined? method
|
|
416
|
-
Selenium::WebDriver::Driver.class_eval { def_delegator :@bridge, method }
|
|
417
|
-
end
|
|
418
|
-
|
|
419
|
-
# @private
|
|
420
|
-
def delegate_from_appium_driver(method, delegation_target = :driver)
|
|
421
|
-
def_delegator delegation_target, method
|
|
422
|
-
end
|
|
423
|
-
|
|
424
|
-
# @private
|
|
425
|
-
def create_bridge_command(method)
|
|
426
|
-
Selenium::WebDriver::Remote::OSS::Bridge.class_eval do
|
|
427
|
-
block_given? ? class_eval(&Proc.new) : define_method(method) { execute method }
|
|
428
|
-
end
|
|
429
|
-
|
|
430
|
-
Selenium::WebDriver::Remote::W3C::Bridge.class_eval do
|
|
431
|
-
block_given? ? class_eval(&Proc.new) : define_method(method) { execute method }
|
|
432
|
-
end
|
|
433
|
-
end
|
|
434
|
-
|
|
435
|
-
# @!method find_element_with_appium
|
|
436
|
-
# @!method find_elements_with_appium
|
|
437
|
-
#
|
|
438
|
-
# find_element/s_with_appium with their accessibility_id
|
|
439
|
-
#
|
|
440
|
-
# ```ruby
|
|
441
|
-
# find_elements :accessibility_id, 'Animation'
|
|
442
|
-
# ```
|
|
443
|
-
def extend_search_contexts
|
|
444
|
-
Selenium::WebDriver::SearchContext.class_eval do
|
|
445
|
-
def find_element(*args)
|
|
446
|
-
how, what = extract_args(args)
|
|
447
|
-
by = _set_by_from_finders(how)
|
|
448
|
-
begin
|
|
449
|
-
bridge.find_element_by by, what.to_s, ref
|
|
450
|
-
rescue Selenium::WebDriver::Error::TimeOutError
|
|
451
|
-
raise Selenium::WebDriver::Error::NoSuchElementError
|
|
452
|
-
end
|
|
453
|
-
end
|
|
454
|
-
|
|
455
|
-
def find_elements(*args)
|
|
456
|
-
how, what = extract_args(args)
|
|
457
|
-
by = _set_by_from_finders(how)
|
|
458
|
-
begin
|
|
459
|
-
bridge.find_elements_by by, what.to_s, ref
|
|
460
|
-
rescue Selenium::WebDriver::Error::TimeOutError
|
|
461
|
-
raise Selenium::WebDriver::Error::NoSuchElementError
|
|
462
|
-
end
|
|
463
|
-
end
|
|
464
|
-
|
|
465
|
-
def _set_by_from_finders(how)
|
|
466
|
-
finders = ::Selenium::WebDriver::SearchContext::FINDERS.merge ::Appium::Driver::SearchContext::FINDERS
|
|
467
|
-
by = finders[how.to_sym]
|
|
468
|
-
raise ArgumentError, "cannot find element by #{how.inspect}" unless by
|
|
469
|
-
by
|
|
470
|
-
end
|
|
471
|
-
end
|
|
472
|
-
end
|
|
473
|
-
|
|
474
|
-
def add_touch_actions
|
|
475
|
-
add_endpoint_method(:touch_actions) do
|
|
476
|
-
def touch_actions(actions)
|
|
477
|
-
actions = { actions: [actions].flatten }
|
|
478
|
-
execute :touch_actions, {}, actions
|
|
479
|
-
end
|
|
480
|
-
end
|
|
481
|
-
|
|
482
|
-
add_endpoint_method(:multi_touch) do
|
|
483
|
-
def multi_touch(actions)
|
|
484
|
-
execute :multi_touch, {}, actions: actions
|
|
485
|
-
end
|
|
486
|
-
end
|
|
487
|
-
|
|
488
|
-
actions = Appium::TouchAction::COMPLEX_ACTIONS
|
|
489
|
-
actions.each do |method|
|
|
490
|
-
delegate_from_appium_driver(method, Appium::TouchAction)
|
|
491
|
-
end
|
|
492
|
-
|
|
493
|
-
delegate_from_appium_driver(:pinch, Appium::MultiTouch)
|
|
494
|
-
delegate_from_appium_driver(:zoom, Appium::MultiTouch)
|
|
495
|
-
end
|
|
496
|
-
|
|
497
|
-
def add_ime_actions
|
|
498
|
-
# Commands for IME are defined in the following commands.rb, but the driver have no bridge.
|
|
499
|
-
# So, appium_lib define just bridge here.
|
|
500
|
-
# https://github.com/SeleniumHQ/selenium/blob/selenium-3.0.1/rb/lib/selenium/webdriver/remote/commands.rb#L184-L192
|
|
501
|
-
|
|
502
|
-
# @!method ime_activate
|
|
503
|
-
# Make an engine that is available active.
|
|
504
|
-
#
|
|
505
|
-
# Android only.
|
|
506
|
-
# @param [String] The IME owning the activity [required]
|
|
507
|
-
#
|
|
508
|
-
# ```ruby
|
|
509
|
-
# ime_activate engine: 'com.android.inputmethod.latin/.LatinIME'
|
|
510
|
-
# ```
|
|
511
|
-
add_endpoint_method(:ime_activate) do
|
|
512
|
-
def ime_activate(ime_name)
|
|
513
|
-
execute :ime_activate, {}, engine: ime_name
|
|
514
|
-
end
|
|
515
|
-
end
|
|
516
|
-
|
|
517
|
-
# @!method ime_available_engines
|
|
518
|
-
# List all available input engines on the machine.
|
|
519
|
-
# Android only.
|
|
520
|
-
#
|
|
521
|
-
# ```ruby
|
|
522
|
-
# ime_available_engines #=> Get the list of IME installed in the target device
|
|
523
|
-
# ```
|
|
524
|
-
add_endpoint_method(:ime_available_engines) do
|
|
525
|
-
def ime_available_engines
|
|
526
|
-
execute :get_ime_available_engines
|
|
527
|
-
end
|
|
528
|
-
end
|
|
529
|
-
|
|
530
|
-
# @!method ime_active_engine
|
|
531
|
-
# Get the name of the active IME engine.
|
|
532
|
-
# Android only.
|
|
533
|
-
#
|
|
534
|
-
# ```ruby
|
|
535
|
-
# ime_active_engine #=> Get the current active IME such as 'com.android.inputmethod.latin/.LatinIME'
|
|
536
|
-
# ```
|
|
537
|
-
add_endpoint_method(:ime_active_engine) do
|
|
538
|
-
def ime_active_engine
|
|
539
|
-
execute :get_ime_active_engine
|
|
540
|
-
end
|
|
541
|
-
end
|
|
542
|
-
|
|
543
|
-
# @!method ime_activated
|
|
544
|
-
# Indicates whether IME input is active at the moment (not if it is available).
|
|
545
|
-
# Android only.
|
|
546
|
-
#
|
|
547
|
-
# ```ruby
|
|
548
|
-
# ime_activated #=> True if IME is activated
|
|
549
|
-
# ```
|
|
550
|
-
add_endpoint_method(:ime_activated) do
|
|
551
|
-
def ime_activated
|
|
552
|
-
execute :get_ime_activated
|
|
553
|
-
end
|
|
554
|
-
end
|
|
555
|
-
|
|
556
|
-
# @!method ime_deactivate
|
|
557
|
-
# De-activates the currently-active IME engine.
|
|
558
|
-
#
|
|
559
|
-
# Android only.
|
|
560
|
-
#
|
|
561
|
-
# ```ruby
|
|
562
|
-
# ime_deactivate #=> Deactivate current IME engine
|
|
563
|
-
# ```
|
|
564
|
-
add_endpoint_method(:ime_deactivate) do
|
|
565
|
-
def ime_deactivate
|
|
566
|
-
execute :ime_deactivate, {}
|
|
567
|
-
end
|
|
568
|
-
end
|
|
569
|
-
end
|
|
570
|
-
end # class << self
|
|
571
|
-
|
|
572
|
-
# @!method set_context
|
|
573
|
-
# Change the context to the given context.
|
|
574
|
-
# @param [String] The context to change to
|
|
575
|
-
#
|
|
576
|
-
# ```ruby
|
|
577
|
-
# set_context "NATIVE_APP"
|
|
578
|
-
# ```
|
|
579
|
-
|
|
580
|
-
# @!method current_context
|
|
581
|
-
# @return [String] The context currently being used.
|
|
582
|
-
|
|
583
|
-
# @!method available_contexts
|
|
584
|
-
# @return [Array<String>] All usable contexts, as an array of strings.
|
|
585
|
-
|
|
586
|
-
# Perform a block within the given context, then switch back to the starting context.
|
|
587
|
-
# @param context (String) The context to switch to for the duration of the block.
|
|
588
|
-
#
|
|
589
|
-
# ```ruby
|
|
590
|
-
# result = within_context('NATIVE_APP') do
|
|
591
|
-
# find_element :tag, "button"
|
|
592
|
-
# end # The result of `find_element :tag, "button"`
|
|
593
|
-
# ```
|
|
594
|
-
def within_context(context)
|
|
595
|
-
existing_context = current_context
|
|
596
|
-
set_context context
|
|
597
|
-
if block_given?
|
|
598
|
-
result = yield
|
|
599
|
-
set_context existing_context
|
|
600
|
-
result
|
|
601
|
-
else
|
|
602
|
-
set_context existing_context
|
|
603
|
-
end
|
|
604
|
-
end
|
|
605
|
-
|
|
606
|
-
# Change to the default context. This is equivalent to `set_context nil`.
|
|
607
|
-
def switch_to_default_context
|
|
608
|
-
set_context nil
|
|
609
|
-
end
|
|
610
|
-
end # module Device
|
|
611
|
-
end # module Appium
|