calabash 1.2.1 → 1.9.9.pre1
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/CONTRIBUTING.md +39 -0
- data/LICENSE +204 -21
- data/README.md +36 -6
- data/VERSIONING.md +16 -0
- data/bin/calabash +95 -0
- data/lib/calabash.rb +185 -1
- data/lib/calabash/android.rb +64 -0
- data/lib/calabash/android/adb.rb +277 -0
- data/lib/calabash/android/application.rb +110 -0
- data/lib/calabash/android/build.rb +12 -0
- data/lib/calabash/android/build/application.rb +13 -0
- data/lib/calabash/android/build/build_error.rb +11 -0
- data/lib/calabash/android/build/builder.rb +119 -0
- data/lib/calabash/android/build/java_keystore.rb +177 -0
- data/lib/calabash/android/build/resigner.rb +56 -0
- data/lib/calabash/android/build/test_server.rb +27 -0
- data/lib/calabash/android/console_helpers.rb +44 -0
- data/lib/calabash/android/cucumber.rb +3 -0
- data/lib/calabash/android/device.rb +965 -0
- data/lib/calabash/android/environment.rb +470 -0
- data/lib/calabash/android/gestures.rb +369 -0
- data/lib/calabash/android/interactions.rb +45 -0
- data/lib/calabash/android/lib/.irbrc +55 -0
- data/lib/calabash/android/lib/AndroidManifest.xml +51 -0
- data/lib/calabash/android/lib/TestServer.apk +0 -0
- data/lib/calabash/android/lib/calmd5/arm64-v8a/calmd5 +0 -0
- data/lib/calabash/android/lib/calmd5/arm64-v8a/calmd5-pie +0 -0
- data/lib/calabash/android/lib/calmd5/armeabi-v7a/calmd5 +0 -0
- data/lib/calabash/android/lib/calmd5/armeabi-v7a/calmd5-pie +0 -0
- data/lib/calabash/android/lib/calmd5/armeabi/calmd5 +0 -0
- data/lib/calabash/android/lib/calmd5/armeabi/calmd5-pie +0 -0
- data/lib/calabash/android/lib/calmd5/mips/calmd5 +0 -0
- data/lib/calabash/android/lib/calmd5/mips/calmd5-pie +0 -0
- data/lib/calabash/android/lib/calmd5/mips64/calmd5 +0 -0
- data/lib/calabash/android/lib/calmd5/mips64/calmd5-pie +0 -0
- data/lib/calabash/android/lib/calmd5/x86/calmd5 +0 -0
- data/lib/calabash/android/lib/calmd5/x86/calmd5-pie +0 -0
- data/lib/calabash/android/lib/calmd5/x86_64/calmd5 +0 -0
- data/lib/calabash/android/lib/calmd5/x86_64/calmd5-pie +0 -0
- data/lib/calabash/android/lib/screenshot_taker.jar +0 -0
- data/lib/calabash/android/life_cycle.rb +37 -0
- data/lib/calabash/android/orientation.rb +30 -0
- data/lib/calabash/android/physical_buttons.rb +39 -0
- data/lib/calabash/android/screenshot.rb +9 -0
- data/lib/calabash/android/scroll.rb +5 -0
- data/lib/calabash/android/server.rb +10 -0
- data/lib/calabash/android/text.rb +54 -0
- data/lib/calabash/application.rb +74 -0
- data/lib/calabash/cli.rb +12 -0
- data/lib/calabash/cli/build.rb +33 -0
- data/lib/calabash/cli/console.rb +90 -0
- data/lib/calabash/cli/generate.rb +110 -0
- data/lib/calabash/cli/helpers.rb +130 -0
- data/lib/calabash/cli/resign.rb +33 -0
- data/lib/calabash/cli/run.rb +99 -0
- data/lib/calabash/cli/setup_keystore.rb +39 -0
- data/lib/calabash/color.rb +32 -0
- data/lib/calabash/console_helpers.rb +90 -0
- data/lib/calabash/defaults.rb +56 -0
- data/lib/calabash/device.rb +401 -0
- data/lib/calabash/environment.rb +75 -0
- data/lib/calabash/gestures.rb +384 -0
- data/lib/calabash/http.rb +8 -0
- data/lib/calabash/http/error.rb +15 -0
- data/lib/calabash/http/request.rb +42 -0
- data/lib/calabash/http/retriable_client.rb +156 -0
- data/lib/calabash/interactions.rb +105 -0
- data/lib/calabash/ios.rb +37 -0
- data/lib/calabash/ios/application.rb +119 -0
- data/lib/calabash/ios/conditions.rb +79 -0
- data/lib/calabash/ios/console_helpers.rb +72 -0
- data/lib/calabash/ios/device.rb +24 -0
- data/lib/calabash/ios/device/device_implementation.rb +779 -0
- data/lib/calabash/ios/device/gestures_mixin.rb +167 -0
- data/lib/calabash/ios/device/keyboard_mixin.rb +133 -0
- data/lib/calabash/ios/device/physical_device_mixin.rb +266 -0
- data/lib/calabash/ios/device/rotation_mixin.rb +124 -0
- data/lib/calabash/ios/device/routes/backdoor_route_mixin.rb +86 -0
- data/lib/calabash/ios/device/routes/condition_route_mixin.rb +62 -0
- data/lib/calabash/ios/device/routes/error.rb +8 -0
- data/lib/calabash/ios/device/routes/handle_route_mixin.rb +102 -0
- data/lib/calabash/ios/device/routes/map_route_mixin.rb +38 -0
- data/lib/calabash/ios/device/routes/playback_route_mixin.rb +70 -0
- data/lib/calabash/ios/device/routes/response_parser.rb +48 -0
- data/lib/calabash/ios/device/routes/uia_route_mixin.rb +238 -0
- data/lib/calabash/ios/device/runtime_attributes.rb +184 -0
- data/lib/calabash/ios/device/status_bar_mixin.rb +17 -0
- data/lib/calabash/ios/device/text_mixin.rb +19 -0
- data/lib/calabash/ios/device/uia_keyboard_mixin.rb +188 -0
- data/lib/calabash/ios/device/uia_mixin.rb +12 -0
- data/lib/calabash/ios/environment.rb +41 -0
- data/lib/calabash/ios/interactions.rb +10 -0
- data/lib/calabash/ios/lib/.irbrc +55 -0
- data/lib/calabash/ios/lib/recordings/rotate_left_home_down_ipad.base64 +2 -0
- data/lib/calabash/ios/lib/recordings/rotate_left_home_down_iphone.base64 +2 -0
- data/lib/calabash/ios/lib/recordings/rotate_left_home_left_ipad.base64 +2 -0
- data/lib/calabash/ios/lib/recordings/rotate_left_home_left_iphone.base64 +2 -0
- data/lib/calabash/ios/lib/recordings/rotate_left_home_right_ipad.base64 +2 -0
- data/lib/calabash/ios/lib/recordings/rotate_left_home_right_iphone.base64 +2 -0
- data/lib/calabash/ios/lib/recordings/rotate_left_home_up_ipad.base64 +2 -0
- data/lib/calabash/ios/lib/recordings/rotate_left_home_up_iphone.base64 +2 -0
- data/lib/calabash/ios/lib/recordings/rotate_right_home_down_ipad.base64 +2 -0
- data/lib/calabash/ios/lib/recordings/rotate_right_home_down_iphone.base64 +2 -0
- data/lib/calabash/ios/lib/recordings/rotate_right_home_left_ipad.base64 +2 -0
- data/lib/calabash/ios/lib/recordings/rotate_right_home_left_iphone.base64 +2 -0
- data/lib/calabash/ios/lib/recordings/rotate_right_home_right_ipad.base64 +2 -0
- data/lib/calabash/ios/lib/recordings/rotate_right_home_right_iphone.base64 +2 -0
- data/lib/calabash/ios/lib/recordings/rotate_right_home_up_ipad.base64 +2 -0
- data/lib/calabash/ios/lib/recordings/rotate_right_home_up_iphone.base64 +2 -0
- data/lib/calabash/ios/orientation.rb +117 -0
- data/lib/calabash/ios/scroll.rb +504 -0
- data/lib/calabash/ios/server.rb +73 -0
- data/lib/calabash/ios/text.rb +248 -0
- data/lib/calabash/ios/uia.rb +24 -0
- data/lib/calabash/lib/skeleton/config/cucumber.yml +6 -0
- data/lib/calabash/lib/skeleton/features/sample.feature +5 -0
- data/lib/calabash/lib/skeleton/features/step_definitions/calabash_steps.rb +29 -0
- data/lib/calabash/lib/skeleton/features/support/env.rb +54 -0
- data/lib/calabash/lib/skeleton/features/support/hooks.rb +83 -0
- data/lib/calabash/life_cycle.rb +111 -0
- data/lib/calabash/location.rb +51 -0
- data/lib/calabash/logger.rb +87 -0
- data/lib/calabash/orientation.rb +84 -0
- data/lib/calabash/page.rb +35 -0
- data/lib/calabash/patch.rb +14 -0
- data/lib/calabash/patch/array.rb +16 -0
- data/lib/calabash/patch/run_loop.rb +90 -0
- data/lib/calabash/query.rb +160 -0
- data/lib/calabash/query_result.rb +85 -0
- data/lib/calabash/screenshot.rb +89 -0
- data/lib/calabash/server.rb +16 -0
- data/lib/calabash/text.rb +76 -0
- data/lib/calabash/utility.rb +58 -0
- data/lib/calabash/version.rb +3 -1
- data/lib/calabash/wait.rb +474 -0
- metadata +462 -24
@@ -0,0 +1,15 @@
|
|
1
|
+
module Calabash
|
2
|
+
module HTTP
|
3
|
+
|
4
|
+
# Raised when there is a problem communicating with the Calabash test
|
5
|
+
# server.
|
6
|
+
class Error < StandardError
|
7
|
+
|
8
|
+
end
|
9
|
+
|
10
|
+
# Raised when there is a problem creating an HTTP request.
|
11
|
+
class RequestError < StandardError
|
12
|
+
|
13
|
+
end
|
14
|
+
end
|
15
|
+
end
|
@@ -0,0 +1,42 @@
|
|
1
|
+
module Calabash
|
2
|
+
module HTTP
|
3
|
+
|
4
|
+
# A representation of an HTTP request that can be passed passed to the HTTP
|
5
|
+
# client as an argument for `get` or `post`.
|
6
|
+
class Request
|
7
|
+
attr_reader :route, :params
|
8
|
+
|
9
|
+
def initialize(route, params={})
|
10
|
+
@route = route
|
11
|
+
@params = params
|
12
|
+
end
|
13
|
+
|
14
|
+
# Create a new Request from `route` and `parameters`.
|
15
|
+
#
|
16
|
+
# @param [String] route The http route for the new request.
|
17
|
+
# @param [Array, Hash] parameters An Array or Hash of parameters.
|
18
|
+
# @return [Request] A new Request for `route` with `parameters`.
|
19
|
+
# @raise [RequestError] Raises an error if the parameters cannot be
|
20
|
+
# converted to JSON
|
21
|
+
def self.request(route, parameters)
|
22
|
+
Request.new(route, Request.data(parameters))
|
23
|
+
end
|
24
|
+
|
25
|
+
private
|
26
|
+
|
27
|
+
# Converts `parameters` to JSON.
|
28
|
+
#
|
29
|
+
# @param [Array, Hash] parameters An Array or Hash of parameters.
|
30
|
+
# @return [String] A JSON formatted string that represents the parameters.
|
31
|
+
# @raise [RequestError] Raises an error if the parameters cannot be
|
32
|
+
# converted to JSON
|
33
|
+
def self.data(parameters)
|
34
|
+
begin
|
35
|
+
JSON.generate(parameters)
|
36
|
+
rescue *[TypeError, JSON::GeneratorError] => e
|
37
|
+
raise RequestError, "#{e}: could not generate JSON from '#{parameters}'"
|
38
|
+
end
|
39
|
+
end
|
40
|
+
end
|
41
|
+
end
|
42
|
+
end
|
@@ -0,0 +1,156 @@
|
|
1
|
+
require 'httpclient'
|
2
|
+
|
3
|
+
module Calabash
|
4
|
+
module HTTP
|
5
|
+
|
6
|
+
# An HTTP client that retries its connection on errors and can time out.
|
7
|
+
class RetriableClient
|
8
|
+
attr_reader :client
|
9
|
+
|
10
|
+
# @!visibility private
|
11
|
+
RETRY_ON =
|
12
|
+
[
|
13
|
+
# The connection, request, or response timed out
|
14
|
+
#HTTPClient::TimeoutError,
|
15
|
+
# The proxy could not connect to the server (Android)
|
16
|
+
# or the server is not running (iOS)
|
17
|
+
HTTPClient::KeepAliveDisconnected,
|
18
|
+
# No proxy has been set up (Android)
|
19
|
+
Errno::ECONNREFUSED,
|
20
|
+
# The server sent a partial response
|
21
|
+
#Errno::ECONNRESET,
|
22
|
+
# Client sent TCP reset (RST) before server has accepted the
|
23
|
+
# connection requested by client.
|
24
|
+
Errno::ECONNABORTED,
|
25
|
+
# The foreign function call call timed out
|
26
|
+
#Errno::ETIMEDOUT
|
27
|
+
]
|
28
|
+
|
29
|
+
# @!visibility private
|
30
|
+
HEADER =
|
31
|
+
{
|
32
|
+
'Content-Type' => 'application/json;charset=utf-8'
|
33
|
+
}
|
34
|
+
|
35
|
+
# Creates a new retriable client.
|
36
|
+
#
|
37
|
+
# This initializer takes multiple options. If the option is not
|
38
|
+
# documented, it should be considered _private_. You use undocumented
|
39
|
+
# options at your own risk.
|
40
|
+
#
|
41
|
+
# @param [Calabash::Server] server The server to make the HTTP request
|
42
|
+
# on.
|
43
|
+
# @param [Hash] options Control the retry, timeout, and interval.
|
44
|
+
# @option options [Number] :retries (5) How often to retry.
|
45
|
+
# @option options [Number] :timeout (5) How long to wait for a response
|
46
|
+
# before timing out.
|
47
|
+
# @option options [Number] :interval (0.5) How long to sleep between
|
48
|
+
# retries.
|
49
|
+
def initialize(server, options = {})
|
50
|
+
@client = options[:client] || ::HTTPClient.new
|
51
|
+
@server = server
|
52
|
+
@retries = options.fetch(:retries, 5)
|
53
|
+
@timeout = options.fetch(:timeout, 5)
|
54
|
+
@interval = options.fetch(:interval, 0.5)
|
55
|
+
@logger = options[:logger] || Calabash::Logger.new
|
56
|
+
@on_error = {}
|
57
|
+
end
|
58
|
+
|
59
|
+
def on_error(type, &block)
|
60
|
+
@on_error[type] = block
|
61
|
+
end
|
62
|
+
|
63
|
+
def change_server(new_server)
|
64
|
+
@server = new_server
|
65
|
+
end
|
66
|
+
|
67
|
+
# Make an HTTP get request.
|
68
|
+
#
|
69
|
+
# This method takes multiple options. If the option is not documented,
|
70
|
+
# it should be considered _private_. You use undocumented options at
|
71
|
+
# your own risk.
|
72
|
+
#
|
73
|
+
# @param [Calabash::HTTP::Request] request The request.
|
74
|
+
# @param [Hash] options Control the retry, timeout, and interval.
|
75
|
+
# @option options [Number] :retries (5) How often to retry.
|
76
|
+
# @option options [Number] :timeout (5) How long to wait for a response
|
77
|
+
# before timing out.
|
78
|
+
# @option options [Number] :interval (0.5) How long to sleep between
|
79
|
+
# retries.
|
80
|
+
def get(request, options={})
|
81
|
+
request(request, :get, options)
|
82
|
+
end
|
83
|
+
|
84
|
+
# Make an HTTP post request.
|
85
|
+
#
|
86
|
+
# This method takes multiple options. If the option is not documented,
|
87
|
+
# it should be considered _private_. You use undocumented options at
|
88
|
+
# your own risk.
|
89
|
+
#
|
90
|
+
# @param [Calabash::HTTP::Request] request The request.
|
91
|
+
# @param [Hash] options Control the retry, timeout, and interval.
|
92
|
+
# @option options [Number] :retries (5) How often to retry.
|
93
|
+
# @option options [Number] :timeout (5) How long to wait for a response
|
94
|
+
# before timing out.
|
95
|
+
# @option options [Number] :interval (0.5) How long to sleep between
|
96
|
+
# retries.
|
97
|
+
def post(request, options={})
|
98
|
+
request(request, :post, options)
|
99
|
+
end
|
100
|
+
|
101
|
+
private
|
102
|
+
|
103
|
+
def request(request, request_method, options={})
|
104
|
+
retries = options.fetch(:retries, @retries)
|
105
|
+
timeout = options.fetch(:timeout, @timeout)
|
106
|
+
interval = options.fetch(:interval, @interval)
|
107
|
+
header = options.fetch(:header, HEADER)
|
108
|
+
|
109
|
+
@logger.log "Getting: #{@server.endpoint + request.route}"
|
110
|
+
|
111
|
+
start_time = Time.now
|
112
|
+
last_error = nil
|
113
|
+
|
114
|
+
client = @client.dup
|
115
|
+
client.receive_timeout = timeout
|
116
|
+
|
117
|
+
retries.times do |i|
|
118
|
+
first_try = i == 0
|
119
|
+
|
120
|
+
# Subtract the aggregate time we've spent thus far to make sure we're
|
121
|
+
# not exceeding the request timeout across retries.
|
122
|
+
time_diff = start_time + timeout - Time.now
|
123
|
+
|
124
|
+
if time_diff <= 0
|
125
|
+
raise HTTP::Error, 'Timeout exceeded'
|
126
|
+
end
|
127
|
+
|
128
|
+
client.receive_timeout = [time_diff, client.receive_timeout].min
|
129
|
+
|
130
|
+
begin
|
131
|
+
return client.send(request_method, @server.endpoint + request.route,
|
132
|
+
request.params, header)
|
133
|
+
rescue *RETRY_ON => e
|
134
|
+
@logger.log "Http error: #{e}"
|
135
|
+
|
136
|
+
if first_try
|
137
|
+
if @on_error[e.class]
|
138
|
+
@on_error[e.class].call(@server)
|
139
|
+
end
|
140
|
+
end
|
141
|
+
|
142
|
+
last_error = e
|
143
|
+
sleep interval
|
144
|
+
end
|
145
|
+
end
|
146
|
+
|
147
|
+
# We should raise helpful messages
|
148
|
+
if last_error.is_a?(HTTPClient::KeepAliveDisconnected)
|
149
|
+
raise HTTP::Error, "#{last_error}: It is likely your application has crashed"
|
150
|
+
end
|
151
|
+
|
152
|
+
raise HTTP::Error, last_error
|
153
|
+
end
|
154
|
+
end
|
155
|
+
end
|
156
|
+
end
|
@@ -0,0 +1,105 @@
|
|
1
|
+
module Calabash
|
2
|
+
module Interactions
|
3
|
+
# @todo Needs docs!
|
4
|
+
def query(query, *args)
|
5
|
+
Calabash::Device.default.map_route(Query.new(query), :query, *args)
|
6
|
+
end
|
7
|
+
|
8
|
+
# @todo Needs docs!
|
9
|
+
def flash(query)
|
10
|
+
Calabash::Device.default.map_route(Query.new(query), :flash)
|
11
|
+
end
|
12
|
+
|
13
|
+
# Evaluate javascript in a Web View. On iOS, an implicit return is
|
14
|
+
# inserted, on Android an explicit return is needed.
|
15
|
+
#
|
16
|
+
# @example
|
17
|
+
# # iOS
|
18
|
+
# evaluate_javascript_in("UIWebView", "2+2")
|
19
|
+
# # Android
|
20
|
+
# evaluate_javascript_in("WebView", "return 2+2"
|
21
|
+
#
|
22
|
+
# @example
|
23
|
+
# # iOS
|
24
|
+
# evaluate_javascript_in("WKWebView",
|
25
|
+
# "document.body.style.backgroundColor = 'red';")
|
26
|
+
#
|
27
|
+
# # Android
|
28
|
+
# evaluate_javascript_in("XWalkContent",
|
29
|
+
# "document.body.style.backgroundColor = 'red';")
|
30
|
+
#
|
31
|
+
# @note No error will be raised if the javascript given is invalid, or
|
32
|
+
# throws an exception.
|
33
|
+
#
|
34
|
+
# @param [String, Hash, Calabash::Query] query Query that matches the view
|
35
|
+
# @param [String] javascript The javascript to evaluate
|
36
|
+
#
|
37
|
+
# @raise ViewNotFoundError If no views are found matching `query`
|
38
|
+
def evaluate_javascript_in(query, javascript)
|
39
|
+
wait_for_view(query,
|
40
|
+
timeout: Calabash::Gestures::DEFAULT_GESTURE_WAIT_TIMEOUT)
|
41
|
+
|
42
|
+
_evaluate_javascript_in(query, javascript)
|
43
|
+
end
|
44
|
+
|
45
|
+
# Invoke a method in your application.
|
46
|
+
#
|
47
|
+
# This is an escape hatch for calling an arbitrary hook inside
|
48
|
+
# (the test build) of your app. Commonly used to "go around" the UI for
|
49
|
+
# speed purposes or reset the app to a good known state.
|
50
|
+
#
|
51
|
+
# For iOS this method calls a method on the app's AppDelegate object.
|
52
|
+
#
|
53
|
+
# For Android this method tries to invoke a method on the current Activity
|
54
|
+
# instance. If the method is not defined in the current activity, Calabash
|
55
|
+
# tries to invoke the method on the current Application instance.
|
56
|
+
#
|
57
|
+
# @note The Android implementation accepts any number of arguments, of any
|
58
|
+
# type including null (Ruby nil). The iOS implementation does not accept
|
59
|
+
# more than one argument, of the type NSString (Ruby String) or
|
60
|
+
# NSDictionary (Ruby Hash).
|
61
|
+
#
|
62
|
+
#
|
63
|
+
# ### For iOS
|
64
|
+
#
|
65
|
+
# You must create a method on you app delegate of the form:
|
66
|
+
#
|
67
|
+
# - (NSString *) calabashBackdoor:(NSString *)aIgnorable;
|
68
|
+
#
|
69
|
+
# or if you want to pass parameters
|
70
|
+
#
|
71
|
+
# - (NSString *) calabashBackdoor:(NSDictionary *)params;
|
72
|
+
#
|
73
|
+
# ### For Android
|
74
|
+
#
|
75
|
+
# You must create a public method in your current Activity or Application.
|
76
|
+
#
|
77
|
+
# public <return type> calabashBackdoor(String param1, int param2)
|
78
|
+
#
|
79
|
+
# @example
|
80
|
+
# # iOS
|
81
|
+
# backdoor('calabashBackdoor:'', '')
|
82
|
+
#
|
83
|
+
# @example
|
84
|
+
# # iOS
|
85
|
+
# backdoor('calabashBackdoor:', {example:'param'})
|
86
|
+
#
|
87
|
+
# @example
|
88
|
+
# # Android
|
89
|
+
# backdoor('calabashBackdoor', 'first argument', 2)
|
90
|
+
#
|
91
|
+
# @param [String] name The selector/method name.
|
92
|
+
# @param [Object] *arguments A comma separated list of arguments to be
|
93
|
+
# passed to the backdoor selector/method.
|
94
|
+
# @return [Object] the result of performing the selector/method with the
|
95
|
+
# arguments (serialized)
|
96
|
+
def backdoor(name, *arguments)
|
97
|
+
Device.default.backdoor(name, *arguments)
|
98
|
+
end
|
99
|
+
|
100
|
+
# @!visibility private
|
101
|
+
def _evaluate_javascript_in(query, javascript)
|
102
|
+
abstract_method!
|
103
|
+
end
|
104
|
+
end
|
105
|
+
end
|
data/lib/calabash/ios.rb
ADDED
@@ -0,0 +1,37 @@
|
|
1
|
+
module Calabash
|
2
|
+
# Contains the iOS implementations of the Calabash APIs.
|
3
|
+
module IOS
|
4
|
+
require 'calabash'
|
5
|
+
include Calabash
|
6
|
+
|
7
|
+
# @!visibility private
|
8
|
+
def self.extended(base)
|
9
|
+
Calabash.send(:extended, base)
|
10
|
+
end
|
11
|
+
|
12
|
+
# @!visibility private
|
13
|
+
def self.included(base)
|
14
|
+
Calabash.send(:included, base)
|
15
|
+
end
|
16
|
+
|
17
|
+
require 'calabash/ios/environment'
|
18
|
+
require 'calabash/ios/application'
|
19
|
+
require 'calabash/ios/device'
|
20
|
+
require 'calabash/ios/conditions'
|
21
|
+
require 'calabash/ios/interactions'
|
22
|
+
require 'calabash/ios/orientation'
|
23
|
+
require 'calabash/ios/server'
|
24
|
+
require 'calabash/ios/text'
|
25
|
+
require 'calabash/ios/console_helpers'
|
26
|
+
require 'calabash/ios/uia'
|
27
|
+
require 'calabash/ios/scroll'
|
28
|
+
|
29
|
+
include Calabash::IOS::Conditions
|
30
|
+
include Calabash::IOS::Orientation
|
31
|
+
include Calabash::IOS::Interactions
|
32
|
+
include Calabash::IOS::Text
|
33
|
+
include Calabash::IOS::UIA
|
34
|
+
include Calabash::IOS::Scroll
|
35
|
+
|
36
|
+
end
|
37
|
+
end
|
@@ -0,0 +1,119 @@
|
|
1
|
+
module Calabash
|
2
|
+
module IOS
|
3
|
+
|
4
|
+
# A class to represent an iOS application. An application can be a
|
5
|
+
# simulator bundle (.app) or a device binary (.ipa).
|
6
|
+
class Application < Calabash::Application
|
7
|
+
|
8
|
+
# The path to the application under test deduced by analysing the
|
9
|
+
# environment.
|
10
|
+
#
|
11
|
+
# You can control the default application path by setting the `CAL_APP`
|
12
|
+
# environment variable. This is the best way of ensuring Calabash
|
13
|
+
# can find your application.
|
14
|
+
#
|
15
|
+
# @todo We have a chicken and egg problem. If the device under test
|
16
|
+
# is a simulator, we have been analyzing the Xcode or Xamarin Studio
|
17
|
+
# project for the likely location of the .app. I think we still want
|
18
|
+
# to do this. The problem is that Xcode buries the .app in a
|
19
|
+
# DerivedData directory deep in the user's ~/Library/ and the correct
|
20
|
+
# directory path is very difficult to find. I overcome this problem
|
21
|
+
# with command-line build scripts that put the .app (or .ipa) in a
|
22
|
+
# directory local to my project. Others devs use Xcode Custom Build
|
23
|
+
# locations. I don't think we we want to branch here on whether or not
|
24
|
+
# the DEVICE_ID points to a simulator or physical device. This is
|
25
|
+
# wicked expensive.
|
26
|
+
def self.default_from_environment
|
27
|
+
application_path = Environment::APP_PATH
|
28
|
+
|
29
|
+
if application_path.nil?
|
30
|
+
raise 'No application path is set'
|
31
|
+
end
|
32
|
+
|
33
|
+
Application.new(application_path)
|
34
|
+
end
|
35
|
+
|
36
|
+
# Create a new Application.
|
37
|
+
#
|
38
|
+
# @param [String] application_path The path to the ipa or app.
|
39
|
+
# @param [Hash] options Optional arguments.
|
40
|
+
# @option options [Calabash::Logger] :logger An optional logger. It is
|
41
|
+
# not recommended that you set this yourself.
|
42
|
+
# @return [Calabash::IOS::Application] A new application.
|
43
|
+
# @raise [RuntimeError] If the `application_path` does not indicate a
|
44
|
+
# file that exists.
|
45
|
+
# @raise [RuntimeError] If the `application_path` does not end with .ipa
|
46
|
+
# or .app.
|
47
|
+
def initialize(application_path, options = {})
|
48
|
+
super(application_path, options)
|
49
|
+
|
50
|
+
@simulator_bundle = File.extname(path) == '.app'
|
51
|
+
@device_binary = File.extname(path) == '.ipa'
|
52
|
+
|
53
|
+
unless @simulator_bundle || @device_binary
|
54
|
+
raise "Expected #{path} to be an .ipa or .app, but found '#{File.extname(path)}'"
|
55
|
+
end
|
56
|
+
end
|
57
|
+
|
58
|
+
# Return true if this application is for an iOS Simulator.
|
59
|
+
# @return [Boolean] Is this a .app?
|
60
|
+
def simulator_bundle?
|
61
|
+
@simulator_bundle
|
62
|
+
end
|
63
|
+
|
64
|
+
# Return true if this application is for a physical iOS device.
|
65
|
+
# @return [Boolean] Is this a .ipa?
|
66
|
+
def device_binary?
|
67
|
+
@device_binary
|
68
|
+
end
|
69
|
+
|
70
|
+
# Returns the sha1 of the directory or binary of this app's path.
|
71
|
+
# @return [String] A checksum.
|
72
|
+
def sha1
|
73
|
+
RunLoop::Directory.directory_digest(path)
|
74
|
+
end
|
75
|
+
|
76
|
+
# Does this app have the same checksum as another app?
|
77
|
+
# @param [Calabash::IOS::Application] other The other app to compare to.
|
78
|
+
# @return [Boolean] Is the checksum the same for the two apps?
|
79
|
+
def same_sha1_as?(other)
|
80
|
+
sha1 == other.sha1
|
81
|
+
end
|
82
|
+
|
83
|
+
private
|
84
|
+
|
85
|
+
# @!visibility private
|
86
|
+
def run_loop_ipa
|
87
|
+
@run_loop_ipa ||= lambda do
|
88
|
+
if device_binary?
|
89
|
+
RunLoop::Ipa.new(path)
|
90
|
+
else
|
91
|
+
nil
|
92
|
+
end
|
93
|
+
end.call
|
94
|
+
end
|
95
|
+
|
96
|
+
# @!visibility private
|
97
|
+
def run_loop_app
|
98
|
+
@run_loop_app ||= lambda do
|
99
|
+
if simulator_bundle?
|
100
|
+
RunLoop::App.new(path)
|
101
|
+
else
|
102
|
+
nil
|
103
|
+
end
|
104
|
+
end.call
|
105
|
+
end
|
106
|
+
|
107
|
+
# @!visibility private
|
108
|
+
def extract_identifier
|
109
|
+
if simulator_bundle?
|
110
|
+
run_loop_app.bundle_identifier
|
111
|
+
elsif device_binary?
|
112
|
+
run_loop_ipa.bundle_identifier
|
113
|
+
else
|
114
|
+
raise "Unknown app type '#{File.extname(path)}', cannot extract bundle identifier"
|
115
|
+
end
|
116
|
+
end
|
117
|
+
end
|
118
|
+
end
|
119
|
+
end
|