appium_lib 6.0.0 → 7.0.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/.gitignore +2 -0
- data/.rubocop.yml +28 -0
- data/.travis.yml +10 -0
- data/Rakefile +9 -1
- data/android_tests/Gemfile +1 -1
- data/android_tests/Rakefile +20 -13
- data/android_tests/lib/android/specs/android/element/alert.rb +1 -1
- data/android_tests/lib/android/specs/android/element/button.rb +2 -2
- data/android_tests/lib/android/specs/android/element/generic.rb +1 -2
- data/android_tests/lib/android/specs/android/element/text.rb +2 -3
- data/android_tests/lib/android/specs/android/element/textfield.rb +2 -2
- data/android_tests/lib/android/specs/android/helper.rb +5 -3
- data/android_tests/lib/android/specs/android/patch.rb +2 -2
- data/android_tests/lib/android/specs/common/device.rb +16 -9
- data/android_tests/lib/android/specs/common/device_touchaction.rb +5 -2
- data/android_tests/lib/android/specs/common/element/window.rb +1 -1
- data/android_tests/lib/android/specs/common/helper.rb +14 -15
- data/android_tests/lib/android/specs/common/patch.rb +11 -9
- data/android_tests/lib/android/specs/common/version.rb +3 -3
- data/android_tests/lib/android/specs/common/web_context.rb +2 -3
- data/android_tests/lib/android/specs/driver.rb +38 -29
- data/android_tests/lib/android/specs/install.rb +3 -3
- data/android_tests/lib/format.rb +6 -8
- data/android_tests/lib/run.rb +25 -17
- data/android_tests/readme.md +4 -2
- data/appium_lib.gemspec +13 -11
- data/contributing.md +1 -1
- data/docs/android_docs.md +358 -274
- data/docs/ios_docs.md +333 -270
- data/docs/migration.md +10 -0
- data/docs_gen/make_docs.rb +3 -1
- data/ios_tests/Gemfile +1 -1
- data/ios_tests/Rakefile +17 -10
- data/ios_tests/appium.txt +1 -1
- data/ios_tests/lib/common.rb +8 -4
- data/ios_tests/lib/format.rb +5 -7
- data/ios_tests/lib/ios/specs/common/element/window.rb +1 -1
- data/ios_tests/lib/ios/specs/common/helper.rb +40 -39
- data/ios_tests/lib/ios/specs/common/patch.rb +15 -11
- data/ios_tests/lib/ios/specs/common/version.rb +3 -3
- data/ios_tests/lib/ios/specs/common/web_context.rb +1 -2
- data/ios_tests/lib/ios/specs/device/device.rb +7 -7
- data/ios_tests/lib/ios/specs/device/multi_touch.rb +6 -8
- data/ios_tests/lib/ios/specs/device/touch_actions.rb +12 -12
- data/ios_tests/lib/ios/specs/driver.rb +23 -22
- data/ios_tests/lib/ios/specs/ios/element/alert.rb +6 -2
- data/ios_tests/lib/ios/specs/ios/element/button.rb +2 -2
- data/ios_tests/lib/ios/specs/ios/element/generic.rb +1 -1
- data/ios_tests/lib/ios/specs/ios/element/text.rb +4 -1
- data/ios_tests/lib/ios/specs/ios/element/textfield.rb +6 -6
- data/ios_tests/lib/ios/specs/ios/helper.rb +5 -5
- data/ios_tests/lib/ios/specs/ios/patch.rb +2 -2
- data/ios_tests/lib/run.rb +1 -1
- data/ios_tests/readme.md +3 -3
- data/ios_tests/upload/sauce_storage.rb +8 -8
- data/ios_tests/upload/upload.rb +1 -1
- data/lib/appium_lib/android/client_xpath.rb +7 -7
- data/lib/appium_lib/android/element/alert.rb +2 -2
- data/lib/appium_lib/android/element/button.rb +16 -16
- data/lib/appium_lib/android/element/generic.rb +12 -13
- data/lib/appium_lib/android/element/text.rb +5 -5
- data/lib/appium_lib/android/element/textfield.rb +5 -5
- data/lib/appium_lib/android/helper.rb +82 -52
- data/lib/appium_lib/android/mobile_methods.rb +2 -2
- data/lib/appium_lib/android/patch.rb +3 -3
- data/lib/appium_lib/common/element/window.rb +1 -1
- data/lib/appium_lib/common/helper.rb +30 -35
- data/lib/appium_lib/common/patch.rb +22 -20
- data/lib/appium_lib/common/version.rb +3 -3
- data/lib/appium_lib/common/wait.rb +9 -10
- data/lib/appium_lib/device/device.rb +39 -33
- data/lib/appium_lib/device/multi_touch.rb +5 -7
- data/lib/appium_lib/device/touch_actions.rb +14 -15
- data/lib/appium_lib/driver.rb +97 -76
- data/lib/appium_lib/ios/element/alert.rb +1 -1
- data/lib/appium_lib/ios/element/button.rb +5 -5
- data/lib/appium_lib/ios/element/generic.rb +5 -6
- data/lib/appium_lib/ios/element/text.rb +5 -5
- data/lib/appium_lib/ios/element/textfield.rb +15 -15
- data/lib/appium_lib/ios/helper.rb +103 -90
- data/lib/appium_lib/ios/mobile_methods.rb +2 -2
- data/lib/appium_lib/ios/patch.rb +4 -4
- data/lib/appium_lib/logger.rb +7 -5
- data/lib/appium_lib/rails/duplicable.rb +3 -1
- data/readme.md +7 -1
- data/release_notes.md +152 -0
- metadata +28 -54
@@ -7,11 +7,11 @@ module Appium
|
|
7
7
|
# ```ruby
|
8
8
|
# find_elements :uiautomator, 'new UiSelector().clickable(true)'
|
9
9
|
# ```
|
10
|
-
def extended(
|
10
|
+
def extended(_mod)
|
11
11
|
Selenium::WebDriver::SearchContext.class_eval do
|
12
12
|
Selenium::WebDriver::SearchContext::FINDERS[:uiautomator] = '-android uiautomator'
|
13
13
|
end
|
14
14
|
end
|
15
15
|
end # class << self
|
16
16
|
end # module Android
|
17
|
-
end # module Appium
|
17
|
+
end # module Appium
|
@@ -7,10 +7,10 @@ module Appium
|
|
7
7
|
def patch_webdriver_element
|
8
8
|
Selenium::WebDriver::Element.class_eval do
|
9
9
|
# Cross platform way of entering text into a textfield
|
10
|
-
def type
|
11
|
-
|
10
|
+
def type(text)
|
11
|
+
send_keys text
|
12
12
|
end
|
13
13
|
end
|
14
14
|
end
|
15
15
|
end # Android
|
16
|
-
end # Appium
|
16
|
+
end # Appium
|
@@ -21,11 +21,9 @@ module Appium
|
|
21
21
|
# find_element :text doesn't work so use XPath to find by text.
|
22
22
|
|
23
23
|
# Return block.call and ignore any exceptions.
|
24
|
-
def ignore
|
25
|
-
|
26
|
-
|
27
|
-
rescue Exception
|
28
|
-
end
|
24
|
+
def ignore(&block)
|
25
|
+
block.call
|
26
|
+
rescue Exception # rubocop:disable Lint/HandleExceptions, Lint/RescueException
|
29
27
|
end
|
30
28
|
|
31
29
|
# Navigate back.
|
@@ -43,7 +41,7 @@ module Appium
|
|
43
41
|
#
|
44
42
|
# @param xpath_str [String] the XPath string
|
45
43
|
# @return [Element]
|
46
|
-
def xpath
|
44
|
+
def xpath(xpath_str)
|
47
45
|
find_element :xpath, xpath_str
|
48
46
|
end
|
49
47
|
|
@@ -51,11 +49,11 @@ module Appium
|
|
51
49
|
#
|
52
50
|
# @param xpath_str [String] the XPath string
|
53
51
|
# @return [Array<Element>]
|
54
|
-
def xpaths
|
52
|
+
def xpaths(xpath_str)
|
55
53
|
find_elements :xpath, xpath_str
|
56
54
|
end
|
57
55
|
|
58
|
-
def _print_source
|
56
|
+
def _print_source(source)
|
59
57
|
opts = Nokogiri::XML::ParseOptions::NOBLANKS | Nokogiri::XML::ParseOptions::NONET
|
60
58
|
if source.start_with? '<html'
|
61
59
|
doc = Nokogiri::HTML(source) { |cfg| cfg.options = opts }
|
@@ -79,15 +77,15 @@ module Appium
|
|
79
77
|
end
|
80
78
|
|
81
79
|
# http://nokogiri.org/Nokogiri/XML/SAX/Document.html
|
82
|
-
def start_element
|
80
|
+
def start_element(name, attrs = [])
|
83
81
|
# Count only visible elements. Android is always visible
|
84
82
|
element_visible = $driver.device_is_android? ? true : Hash[attrs]['visible'] == 'true'
|
85
|
-
@result[name]
|
83
|
+
@result[name] += 1 if element_visible
|
86
84
|
end
|
87
85
|
|
88
86
|
def formatted_result
|
89
87
|
message = ''
|
90
|
-
sorted = @result.sort_by { |
|
88
|
+
sorted = @result.sort_by { |_element, count| count }.reverse
|
91
89
|
sorted.each do |element, count|
|
92
90
|
message += "#{count}x #{element}\n"
|
93
91
|
end
|
@@ -117,7 +115,7 @@ module Appium
|
|
117
115
|
# ```ruby
|
118
116
|
# px_to_window_rel x: 50, y: 150
|
119
117
|
# ```
|
120
|
-
def px_to_window_rel
|
118
|
+
def px_to_window_rel(opts = {})
|
121
119
|
w = $driver.window_size
|
122
120
|
x = opts.fetch :x, 0
|
123
121
|
y = opts.fetch :y, 0
|
@@ -136,34 +134,32 @@ module Appium
|
|
136
134
|
# Search strings.xml's values for target.
|
137
135
|
# @param target [String] the target to search for in strings.xml values
|
138
136
|
# @return [Array]
|
139
|
-
def xml_keys
|
137
|
+
def xml_keys(target)
|
140
138
|
lazy_load_strings
|
141
|
-
@strings_xml.select { |key,
|
139
|
+
@strings_xml.select { |key, _value| key.downcase.include? target.downcase }
|
142
140
|
end
|
143
141
|
|
144
142
|
# Search strings.xml's keys for target.
|
145
143
|
# @param target [String] the target to search for in strings.xml keys
|
146
144
|
# @return [Array]
|
147
|
-
def xml_values
|
145
|
+
def xml_values(target)
|
148
146
|
lazy_load_strings
|
149
|
-
@strings_xml.select { |
|
147
|
+
@strings_xml.select { |_key, value| value.downcase.include? target.downcase }
|
150
148
|
end
|
151
149
|
|
152
150
|
# Resolve id in strings.xml and return the value.
|
153
151
|
# @param id [String] the id to resolve
|
154
152
|
# @return [String]
|
155
|
-
def resolve_id
|
153
|
+
def resolve_id(id)
|
156
154
|
lazy_load_strings
|
157
155
|
@strings_xml[id]
|
158
156
|
end
|
159
157
|
|
160
158
|
class HTMLElements < Nokogiri::XML::SAX::Document
|
161
|
-
|
162
|
-
@filter
|
163
|
-
end
|
159
|
+
attr_reader :filter
|
164
160
|
|
165
161
|
# convert to string to support symbols
|
166
|
-
def filter=
|
162
|
+
def filter=(value)
|
167
163
|
# nil and false disable the filter
|
168
164
|
return @filter = false unless value
|
169
165
|
@filter = value.to_s.downcase
|
@@ -186,7 +182,7 @@ module Appium
|
|
186
182
|
attr_string = e.reduce('') do |string, attr|
|
187
183
|
attr_1 = attr[1]
|
188
184
|
attr_1 = attr_1 ? attr_1.strip : attr_1
|
189
|
-
string
|
185
|
+
string + " #{attr[0]}: #{attr_1}\n"
|
190
186
|
end
|
191
187
|
|
192
188
|
unless attr_string.nil? || attr_string.empty?
|
@@ -196,32 +192,31 @@ module Appium
|
|
196
192
|
end
|
197
193
|
end
|
198
194
|
|
199
|
-
def start_element
|
195
|
+
def start_element(name, attrs = [])
|
200
196
|
@skip_element = filter && !filter.include?(name.downcase)
|
201
|
-
|
202
|
-
|
203
|
-
|
204
|
-
|
205
|
-
|
206
|
-
end
|
197
|
+
return if @skip_element
|
198
|
+
element = { name: name }
|
199
|
+
attrs.each { |a| element[a[0]] = a[1] }
|
200
|
+
@element_stack.push element
|
201
|
+
@elements_in_order.push element
|
207
202
|
end
|
208
203
|
|
209
|
-
def end_element
|
204
|
+
def end_element(name)
|
210
205
|
return if filter && !filter.include?(name.downcase)
|
211
206
|
element_index = @element_stack.rindex { |e| e[:name] == name }
|
212
207
|
@element_stack.delete_at element_index
|
213
208
|
end
|
214
209
|
|
215
210
|
def characters(chars)
|
216
|
-
|
217
|
-
|
218
|
-
|
219
|
-
end
|
211
|
+
return if @skip_element
|
212
|
+
element = @element_stack.last
|
213
|
+
element[:text] = chars
|
220
214
|
end
|
221
215
|
end
|
222
216
|
|
223
217
|
def _no_such_element
|
224
|
-
|
218
|
+
fail Selenium::WebDriver::Error::NoSuchElementError,
|
219
|
+
'An element could not be located on the page using the given search parameters.'
|
225
220
|
end
|
226
221
|
end # module Common
|
227
222
|
end # module Appium
|
@@ -3,21 +3,21 @@ require_relative 'version'
|
|
3
3
|
module Appium
|
4
4
|
module Common
|
5
5
|
# Implement useful features for element.
|
6
|
-
class Selenium::WebDriver::Element
|
6
|
+
class Selenium::WebDriver::Element # rubocop:disable Style/ClassAndModuleChildren
|
7
7
|
# Note: For testing .text should be used over value, and name.
|
8
8
|
|
9
9
|
# Returns the value attribute
|
10
10
|
#
|
11
11
|
# Fixes NoMethodError: undefined method `value' for Selenium::WebDriver::Element
|
12
12
|
def value
|
13
|
-
|
13
|
+
attribute :value
|
14
14
|
end
|
15
15
|
|
16
16
|
# Returns the name attribute
|
17
17
|
#
|
18
18
|
# Fixes NoMethodError: undefined method `name' for Selenium::WebDriver::Element
|
19
19
|
def name
|
20
|
-
|
20
|
+
attribute :name
|
21
21
|
end
|
22
22
|
|
23
23
|
# For use with mobile tap.
|
@@ -67,8 +67,9 @@ def patch_webdriver_bridge
|
|
67
67
|
Selenium::WebDriver::Remote::Bridge.class_eval do
|
68
68
|
# Code from lib/selenium/webdriver/remote/bridge.rb
|
69
69
|
def raw_execute(command, opts = {}, command_hash = nil)
|
70
|
-
verb, path
|
71
|
-
|
70
|
+
verb, path = Selenium::WebDriver::Remote::COMMANDS[command] ||
|
71
|
+
fail(ArgumentError, "unknown command: #{command.inspect}")
|
72
|
+
path = path.dup
|
72
73
|
|
73
74
|
path[':session_id'] = @session_id if path.include?(':session_id')
|
74
75
|
|
@@ -79,18 +80,17 @@ def patch_webdriver_bridge
|
|
79
80
|
end
|
80
81
|
|
81
82
|
# convert /// into /
|
82
|
-
path.gsub!
|
83
|
+
path.gsub!(/\/+/, '/')
|
83
84
|
|
84
85
|
# change path from session/efac972c-941a-499c-803c-d7d008749/execute
|
85
86
|
# to /execute
|
86
87
|
# path may be nil, session, or not have anything after the session_id.
|
87
88
|
path_str = path
|
88
|
-
path_str = '/' + path_str unless path_str.nil? ||
|
89
|
-
|
90
|
-
path_match = path.match /.*\h{8}-?\h{4}-?\h{4}-?\h{4}-?\h{12}/
|
89
|
+
path_str = '/' + path_str unless path_str.nil? || path_str.length <= 0 || path_str[0] == '/'
|
90
|
+
path_match = path.match(/.*\h{8}-?\h{4}-?\h{4}-?\h{4}-?\h{12}/)
|
91
91
|
path_str = path.sub(path_match[0], '') unless path_match.nil?
|
92
92
|
|
93
|
-
Appium::Logger.info
|
93
|
+
Appium::Logger.info "#{verb} #{path_str}"
|
94
94
|
|
95
95
|
# must check to see if command_hash is a hash. sometimes it's not.
|
96
96
|
if command_hash.is_a?(Hash) && !command_hash.empty?
|
@@ -98,7 +98,7 @@ def patch_webdriver_bridge
|
|
98
98
|
|
99
99
|
print_command.delete :args if print_command[:args] == []
|
100
100
|
|
101
|
-
if print_command[:using]
|
101
|
+
if print_command[:using] == '-android uiautomator'
|
102
102
|
value = print_command[:value].split(';').map { |v| "#{v};" }
|
103
103
|
print_command[:value] = value.length == 1 ? value[0] : value
|
104
104
|
|
@@ -121,26 +121,28 @@ def patch_webdriver_bridge
|
|
121
121
|
end
|
122
122
|
|
123
123
|
# Print Appium's origValue error messages.
|
124
|
+
# rubocop:disable Style/ClassAndModuleChildren
|
125
|
+
# rubocop:disable Style/AndOr
|
124
126
|
class Selenium::WebDriver::Remote::Response
|
125
127
|
# @private
|
126
128
|
def error_message
|
127
129
|
val = value
|
128
130
|
|
129
131
|
case val
|
130
|
-
|
131
|
-
|
132
|
-
|
133
|
-
|
134
|
-
|
135
|
-
|
136
|
-
|
132
|
+
when Hash
|
133
|
+
msg = val['origValue'] || val['message'] or return 'unknown error'
|
134
|
+
msg << " (#{ val['class'] })" if val['class']
|
135
|
+
when String
|
136
|
+
msg = val
|
137
|
+
else
|
138
|
+
msg = "unknown error, status=#{status}: #{val.inspect}"
|
137
139
|
end
|
138
140
|
|
139
141
|
msg
|
140
142
|
end
|
141
143
|
end
|
142
144
|
|
143
|
-
class Selenium::WebDriver::Remote::Http::Common
|
145
|
+
class Selenium::WebDriver::Remote::Http::Common # rubocop:disable Style/ClassAndModuleChildren
|
144
146
|
remove_const :DEFAULT_HEADERS if defined? DEFAULT_HEADERS
|
145
147
|
DEFAULT_HEADERS = { 'Accept' => CONTENT_TYPE, 'User-Agent' => "appium/ruby_lib/#{::Appium::VERSION}" }
|
146
|
-
end
|
148
|
+
end
|
@@ -1,5 +1,5 @@
|
|
1
1
|
module Appium
|
2
2
|
# Version and Date are defined on the 'Appium' module, not 'Appium::Common'
|
3
|
-
VERSION = '
|
4
|
-
DATE = '2015-
|
5
|
-
end
|
3
|
+
VERSION = '7.0.0' unless defined? ::Appium::VERSION
|
4
|
+
DATE = '2015-05-08' unless defined? ::Appium::DATE
|
5
|
+
end
|
@@ -1,18 +1,17 @@
|
|
1
1
|
module Appium
|
2
2
|
module Common
|
3
|
-
|
4
3
|
# http://mudge.name/2011/01/26/passing-blocks-in-ruby-without-block.html
|
5
4
|
# Note that the Ruby timeout module is avoided. timeout has problems.
|
6
5
|
# https://coderwall.com/p/1novga
|
7
6
|
|
8
7
|
# Wait code from the selenium Ruby gem
|
9
8
|
# https://github.com/SeleniumHQ/selenium/blob/cf501dda3f0ed12233de51ce8170c0e8090f0c20/rb/lib/selenium/webdriver/common/wait.rb
|
10
|
-
def _generic_wait
|
9
|
+
def _generic_wait(opts = {}, &block)
|
11
10
|
valid_keys = [:timeout, :interval, :message, :ignore, :return_if_true]
|
12
11
|
invalid_keys = []
|
13
12
|
opts.keys.each { |key| invalid_keys << key unless valid_keys.include?(key) }
|
14
13
|
# [:one, :two] => :one, :two
|
15
|
-
|
14
|
+
fail "Invalid keys #{invalid_keys.to_s[1..-2]}. Valid keys are #{valid_keys.to_s[1..-2]}" unless invalid_keys.empty?
|
16
15
|
|
17
16
|
timeout = opts.fetch(:timeout, 30)
|
18
17
|
interval = opts.fetch(:interval, 0.5)
|
@@ -33,7 +32,7 @@ module Appium
|
|
33
32
|
end
|
34
33
|
rescue ::Errno::ECONNREFUSED => e
|
35
34
|
raise e
|
36
|
-
rescue *ignored => last_error
|
35
|
+
rescue *ignored => last_error # rubocop:disable Lint/HandleExceptions
|
37
36
|
# swallowed
|
38
37
|
end
|
39
38
|
|
@@ -48,13 +47,13 @@ module Appium
|
|
48
47
|
|
49
48
|
msg << " (#{last_error.message})" if last_error
|
50
49
|
|
51
|
-
|
50
|
+
fail Selenium::WebDriver::Error::TimeOutError, msg
|
52
51
|
end
|
53
52
|
|
54
53
|
# process opts before calling _generic_wait
|
55
|
-
def _process_wait_opts
|
54
|
+
def _process_wait_opts(opts)
|
56
55
|
opts = { timeout: opts } if opts.is_a?(Numeric)
|
57
|
-
|
56
|
+
fail 'opts must be a hash' unless opts.is_a? Hash
|
58
57
|
opts
|
59
58
|
end
|
60
59
|
|
@@ -73,7 +72,7 @@ module Appium
|
|
73
72
|
# @option opts [Numeric] :interval (0.5) Seconds to sleep between polls.
|
74
73
|
# @option opts [String] :message Exception message if timed out.
|
75
74
|
# @option opts [Array, Exception] :ignore Exceptions to ignore while polling (default: Exception)
|
76
|
-
def wait_true
|
75
|
+
def wait_true(opts = {}, &block)
|
77
76
|
opts = _process_wait_opts(opts).merge(return_if_true: true)
|
78
77
|
_generic_wait opts, &block
|
79
78
|
end
|
@@ -91,9 +90,9 @@ module Appium
|
|
91
90
|
# @option opts [Numeric] :interval (0.5) Seconds to sleep between polls.
|
92
91
|
# @option opts [String] :message Exception message if timed out.
|
93
92
|
# @option opts [Array, Exception] :ignore Exceptions to ignore while polling (default: Exception)
|
94
|
-
def wait
|
93
|
+
def wait(opts = {}, &block)
|
95
94
|
opts = _process_wait_opts(opts).merge(return_if_true: false)
|
96
95
|
_generic_wait opts, &block
|
97
96
|
end
|
98
97
|
end # module Common
|
99
|
-
end # module Appium
|
98
|
+
end # module Appium
|
@@ -12,11 +12,12 @@ module Appium
|
|
12
12
|
close_app: 'session/:session_id/appium/app/close',
|
13
13
|
reset: 'session/:session_id/appium/app/reset',
|
14
14
|
toggle_airplane_mode: 'session/:session_id/appium/device/toggle_airplane_mode',
|
15
|
+
device_locked?: 'session/:session_id/appium/device/is_locked'
|
15
16
|
},
|
16
17
|
get: {
|
17
18
|
current_activity: 'session/:session_id/appium/device/current_activity',
|
18
19
|
current_context: 'session/:session_id/context',
|
19
|
-
get_network_connection: 'session/:session_id/network_connection'
|
20
|
+
get_network_connection: 'session/:session_id/network_connection'
|
20
21
|
}
|
21
22
|
}
|
22
23
|
|
@@ -34,7 +35,7 @@ module Appium
|
|
34
35
|
# @!method current_activity
|
35
36
|
|
36
37
|
# @!method launch_app
|
37
|
-
# Start the simulator and
|
38
|
+
# Start the simulator and application configured with desired capabilities
|
38
39
|
|
39
40
|
# @!method reset
|
40
41
|
# Reset the device, relaunching the application.
|
@@ -43,7 +44,9 @@ module Appium
|
|
43
44
|
# Cause the device to shake
|
44
45
|
|
45
46
|
# @!method toggle_flight_mode
|
46
|
-
#
|
47
|
+
# Toggle flight mode on or off
|
48
|
+
|
49
|
+
# @!method device_locked?
|
47
50
|
|
48
51
|
# @!method hide_keyboard
|
49
52
|
# Hide the onscreen keyboard
|
@@ -101,7 +104,7 @@ module Appium
|
|
101
104
|
# Update appium Settings for current test session
|
102
105
|
# @param settings (hash) Settings to update, keys are settings, values to value to set each setting to
|
103
106
|
class << self
|
104
|
-
def extended(
|
107
|
+
def extended(_mod)
|
105
108
|
extend_webdriver_with_forwardable
|
106
109
|
|
107
110
|
NoArgMethods.each_pair do |verb, pair|
|
@@ -116,7 +119,7 @@ module Appium
|
|
116
119
|
end
|
117
120
|
|
118
121
|
add_endpoint_method(:app_strings, 'session/:session_id/appium/app/strings') do
|
119
|
-
def app_strings
|
122
|
+
def app_strings(language = nil)
|
120
123
|
opts = language ? { language: language } : {}
|
121
124
|
execute :app_strings, {}, opts
|
122
125
|
end
|
@@ -124,31 +127,31 @@ module Appium
|
|
124
127
|
|
125
128
|
add_endpoint_method(:lock, 'session/:session_id/appium/device/lock') do
|
126
129
|
def lock(duration)
|
127
|
-
execute :lock, {}, :
|
130
|
+
execute :lock, {}, seconds: duration
|
128
131
|
end
|
129
132
|
end
|
130
133
|
|
131
134
|
add_endpoint_method(:install_app, 'session/:session_id/appium/device/install_app') do
|
132
135
|
def install_app(path)
|
133
|
-
execute :install_app, {}, :
|
136
|
+
execute :install_app, {}, appPath: path
|
134
137
|
end
|
135
138
|
end
|
136
139
|
|
137
140
|
add_endpoint_method(:remove_app, 'session/:session_id/appium/device/remove_app') do
|
138
141
|
def remove_app(id)
|
139
|
-
execute :remove_app, {}, :
|
142
|
+
execute :remove_app, {}, appId: id
|
140
143
|
end
|
141
144
|
end
|
142
145
|
|
143
|
-
add_endpoint_method(:
|
144
|
-
def
|
145
|
-
execute :
|
146
|
+
add_endpoint_method(:app_installed?, 'session/:session_id/appium/device/app_installed') do
|
147
|
+
def app_installed?(app_id)
|
148
|
+
execute :app_installed?, {}, bundleId: app_id
|
146
149
|
end
|
147
150
|
end
|
148
151
|
|
149
152
|
add_endpoint_method(:background_app, 'session/:session_id/appium/app/background') do
|
150
153
|
def background_app(duration)
|
151
|
-
execute :background_app, {}, :
|
154
|
+
execute :background_app, {}, seconds: duration
|
152
155
|
end
|
153
156
|
end
|
154
157
|
|
@@ -162,37 +165,40 @@ module Appium
|
|
162
165
|
# @param [String] The activity to start before the target activity [optional]
|
163
166
|
#
|
164
167
|
# ```ruby
|
165
|
-
# start_activity app_package: 'io.appium.android.apis',
|
168
|
+
# start_activity app_package: 'io.appium.android.apis',
|
169
|
+
# app_activity: '.accessibility.AccessibilityNodeProviderActivity'
|
166
170
|
# ```
|
167
171
|
add_endpoint_method(:start_activity, 'session/:session_id/appium/device/start_activity') do
|
168
172
|
def start_activity(opts)
|
169
|
-
|
173
|
+
fail 'opts must be a hash' unless opts.is_a? Hash
|
170
174
|
app_package = opts[:app_package]
|
171
|
-
|
175
|
+
fail 'app_package is required' unless app_package
|
172
176
|
app_activity = opts[:app_activity]
|
173
|
-
|
177
|
+
fail 'app_activity is required' unless opts[:app_activity]
|
174
178
|
app_wait_package = opts.fetch(:app_wait_package, '')
|
175
179
|
app_wait_activity = opts.fetch(:app_wait_activity, '')
|
176
180
|
|
177
181
|
unknown_opts = opts.keys - [:app_package, :app_activity, :app_wait_package, :app_wait_activity]
|
178
|
-
|
182
|
+
fail "Unknown options #{unknown_opts}" unless unknown_opts.empty?
|
179
183
|
|
180
|
-
execute :start_activity, {},
|
181
|
-
|
184
|
+
execute :start_activity, {}, appPackage: app_package,
|
185
|
+
appActivity: app_activity,
|
186
|
+
appWaitPackage: app_wait_package,
|
187
|
+
appWaitActivity: app_wait_activity
|
182
188
|
end
|
183
189
|
end
|
184
190
|
|
185
191
|
add_endpoint_method(:set_context, 'session/:session_id/context') do
|
186
|
-
def set_context(context=null)
|
187
|
-
execute :set_context, {}, :
|
192
|
+
def set_context(context = null)
|
193
|
+
execute :set_context, {}, name: context
|
188
194
|
end
|
189
195
|
end
|
190
196
|
|
191
197
|
add_endpoint_method(:hide_keyboard, 'session/:session_id/appium/device/hide_keyboard') do
|
192
|
-
def hide_keyboard(close_key=nil)
|
198
|
+
def hide_keyboard(close_key = nil)
|
193
199
|
# Android can only tapOutside.
|
194
200
|
if $driver.device_is_android?
|
195
|
-
|
201
|
+
return execute :hide_keyboard, {}, strategy: :tapOutside
|
196
202
|
end
|
197
203
|
|
198
204
|
close_key ||= 'Done' # default to Done key.
|
@@ -201,7 +207,7 @@ module Appium
|
|
201
207
|
end
|
202
208
|
|
203
209
|
add_endpoint_method(:press_keycode, 'session/:session_id/appium/device/press_keycode') do
|
204
|
-
def press_keycode(key, metastate=nil)
|
210
|
+
def press_keycode(key, metastate = nil)
|
205
211
|
args = { keycode: key }
|
206
212
|
args[:metastate] = metastate if metastate
|
207
213
|
execute :press_keycode, {}, args
|
@@ -209,17 +215,17 @@ module Appium
|
|
209
215
|
end
|
210
216
|
|
211
217
|
add_endpoint_method(:long_press_keycode, 'session/:session_id/appium/device/long_press_keycode') do
|
212
|
-
def long_press_keycode(key, metastate=nil)
|
218
|
+
def long_press_keycode(key, metastate = nil)
|
213
219
|
args = { keycode: key }
|
214
220
|
args[:metastate] = metastate if metastate
|
215
221
|
execute :long_press_keycode, {}, args
|
216
222
|
end
|
217
223
|
end
|
218
224
|
|
219
|
-
# TODO TEST ME
|
225
|
+
# TODO: TEST ME
|
220
226
|
add_endpoint_method(:set_immediate_value, 'session/:session_id/appium/element/:id/value') do
|
221
227
|
def set_immediate_value(element, value)
|
222
|
-
execute :set_immediate_value, { :
|
228
|
+
execute :set_immediate_value, { id: element.ref }, value: value
|
223
229
|
end
|
224
230
|
end
|
225
231
|
|
@@ -237,7 +243,7 @@ module Appium
|
|
237
243
|
end
|
238
244
|
end
|
239
245
|
|
240
|
-
# TODO TEST ME
|
246
|
+
# TODO: TEST ME
|
241
247
|
add_endpoint_method(:pull_folder, 'session/:session_id/appium/device/pull_folder') do
|
242
248
|
def pull_folder(path)
|
243
249
|
data = execute :pull_folder, {}, path: path
|
@@ -245,7 +251,7 @@ module Appium
|
|
245
251
|
end
|
246
252
|
end
|
247
253
|
|
248
|
-
# TODO TEST ME
|
254
|
+
# TODO: TEST ME
|
249
255
|
add_endpoint_method(:end_coverage, 'session/:session_id/appium/app/end_test_coverage') do
|
250
256
|
def end_coverage(path, intent)
|
251
257
|
execute :end_coverage, {}, path: path, intent: intent
|
@@ -292,7 +298,7 @@ module Appium
|
|
292
298
|
# def extended
|
293
299
|
|
294
300
|
# @private
|
295
|
-
def add_endpoint_method(method, path, verb
|
301
|
+
def add_endpoint_method(method, path, verb = :post)
|
296
302
|
if block_given?
|
297
303
|
# &Proc.new with no args passes the passed_in block
|
298
304
|
# Because creating Procs from blocks is slow
|
@@ -307,7 +313,7 @@ module Appium
|
|
307
313
|
|
308
314
|
# @private
|
309
315
|
def extend_webdriver_with_forwardable
|
310
|
-
return if Selenium::WebDriver::Driver.
|
316
|
+
return if Selenium::WebDriver::Driver.is_a? Forwardable
|
311
317
|
Selenium::WebDriver::Driver.class_eval do
|
312
318
|
extend Forwardable
|
313
319
|
end
|
@@ -320,7 +326,7 @@ module Appium
|
|
320
326
|
end
|
321
327
|
|
322
328
|
# @private
|
323
|
-
def delegate_from_appium_driver(method, delegation_target
|
329
|
+
def delegate_from_appium_driver(method, delegation_target = :driver)
|
324
330
|
def_delegator delegation_target, method
|
325
331
|
end
|
326
332
|
|
@@ -329,7 +335,7 @@ module Appium
|
|
329
335
|
Selenium::WebDriver::Remote::Bridge.class_eval do
|
330
336
|
command method, verb, path
|
331
337
|
if block_given?
|
332
|
-
class_eval
|
338
|
+
class_eval(&Proc.new)
|
333
339
|
else
|
334
340
|
define_method(method) { execute method }
|
335
341
|
end
|