run_loop 2.1.2 → 2.1.3
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/lib/run_loop.rb +7 -0
- data/lib/run_loop/abstract.rb +18 -0
- data/lib/run_loop/core.rb +30 -1
- data/lib/run_loop/core_simulator.rb +5 -1
- data/lib/run_loop/detect_aut/detect.rb +8 -2
- data/lib/run_loop/detect_aut/xcode.rb +6 -2
- data/lib/run_loop/device.rb +9 -2
- data/lib/run_loop/device_agent/app/CBX-Runner.app.zip +0 -0
- data/lib/run_loop/device_agent/bin/xctestctl +0 -0
- data/lib/run_loop/device_agent/cbxrunner.rb +155 -0
- data/lib/run_loop/device_agent/frameworks.rb +64 -0
- data/lib/run_loop/device_agent/frameworks/Frameworks.zip +0 -0
- data/lib/run_loop/device_agent/ipa/CBX-Runner.app.zip +0 -0
- data/lib/run_loop/device_agent/launcher.rb +51 -0
- data/lib/run_loop/device_agent/xcodebuild.rb +91 -0
- data/lib/run_loop/device_agent/xctestctl.rb +109 -0
- data/lib/run_loop/dylib_injector.rb +10 -1
- data/lib/run_loop/environment.rb +66 -0
- data/lib/run_loop/host_cache.rb +7 -2
- data/lib/run_loop/physical_device/{ideviceinstaller.rb → life_cycle.rb} +86 -39
- data/lib/run_loop/sim_control.rb +8 -3
- data/lib/run_loop/version.rb +1 -1
- data/lib/run_loop/xcuitest.rb +134 -116
- data/scripts/lib/log.js +1 -1
- data/scripts/lib/on_alert.js +102 -17
- data/vendor-licenses/FBSimulatorControl.LICENSE +30 -0
- data/vendor-licenses/xctestctl.LICENSE +32 -0
- metadata +15 -3
data/lib/run_loop/sim_control.rb
CHANGED
@@ -294,7 +294,11 @@ module RunLoop
|
|
294
294
|
end
|
295
295
|
else
|
296
296
|
possible = XCODE_5_SDKS.map do |sdk|
|
297
|
-
File.
|
297
|
+
File.join(RunLoop::Environment.user_home_directory,
|
298
|
+
"Library",
|
299
|
+
"Application Support",
|
300
|
+
"iPhone Simulator",
|
301
|
+
sdk)
|
298
302
|
end
|
299
303
|
|
300
304
|
dirs = (possible + existing).uniq
|
@@ -646,10 +650,11 @@ module RunLoop
|
|
646
650
|
# The absolute path to the iPhone Simulator Application Support directory.
|
647
651
|
# @return [String] absolute path
|
648
652
|
def sim_app_support_dir
|
653
|
+
home_dir = RunLoop::Environment.user_home_directory
|
649
654
|
if xcode_version_gte_6?
|
650
|
-
File.
|
655
|
+
File.join(home_dir, "Library", "Developer", "CoreSimulator", "Devices")
|
651
656
|
else
|
652
|
-
File.
|
657
|
+
File.join(home_dir, "Library", "Application Support", "iPhone Simulator")
|
653
658
|
end
|
654
659
|
end
|
655
660
|
|
data/lib/run_loop/version.rb
CHANGED
data/lib/run_loop/xcuitest.rb
CHANGED
@@ -3,6 +3,9 @@ module RunLoop
|
|
3
3
|
# @!visibility private
|
4
4
|
class XCUITest
|
5
5
|
|
6
|
+
require "run_loop/shell"
|
7
|
+
include RunLoop::Shell
|
8
|
+
|
6
9
|
class HTTPError < RuntimeError; end
|
7
10
|
|
8
11
|
# @!visibility private
|
@@ -38,59 +41,64 @@ module RunLoop
|
|
38
41
|
core_sim.install
|
39
42
|
end
|
40
43
|
|
41
|
-
|
44
|
+
cbx_launcher = XCUITest.detect_cbx_launcher(options, device)
|
45
|
+
|
46
|
+
xcuitest = RunLoop::XCUITest.new(bundle_id, device, cbx_launcher)
|
42
47
|
xcuitest.launch
|
43
48
|
xcuitest
|
44
49
|
end
|
45
50
|
|
46
51
|
# @!visibility private
|
47
|
-
|
48
|
-
|
49
|
-
|
50
|
-
|
52
|
+
#
|
53
|
+
# @param [RunLoop::Device] device the device under test
|
54
|
+
def self.default_cbx_launcher(device)
|
55
|
+
RunLoop::DeviceAgent::XCTestctl.new(device)
|
56
|
+
end
|
57
|
+
|
58
|
+
# @!visibility private
|
59
|
+
# @param [Hash] options the options passed by the user
|
60
|
+
# @param [RunLoop::Device] device the device under test
|
61
|
+
def self.detect_cbx_launcher(options, device)
|
62
|
+
value = options[:cbx_launcher]
|
63
|
+
if value
|
64
|
+
if value == :xcodebuild
|
65
|
+
RunLoop::DeviceAgent::Xcodebuild.new(device)
|
66
|
+
elsif value == :xctestctl
|
67
|
+
RunLoop::DeviceAgent::XCTestctl.new(device)
|
68
|
+
else
|
69
|
+
raise(ArgumentError,
|
70
|
+
"Expected :cbx_launcher => #{value} to be :xcodebuild or :xctestctl")
|
71
|
+
end
|
72
|
+
else
|
73
|
+
XCUITest.default_cbx_launcher(device)
|
74
|
+
end
|
51
75
|
end
|
52
76
|
|
77
|
+
attr_reader :bundle_id, :device, :cbx_launcher
|
78
|
+
|
53
79
|
# @!visibility private
|
54
80
|
#
|
55
81
|
# The app with `bundle_id` needs to be installed.
|
56
82
|
#
|
57
83
|
# @param [String] bundle_id The identifier of the app under test.
|
58
84
|
# @param [RunLoop::Device] device The device device.
|
59
|
-
def initialize(bundle_id, device)
|
85
|
+
def initialize(bundle_id, device, cbx_launcher)
|
60
86
|
@bundle_id = bundle_id
|
61
87
|
@device = device
|
88
|
+
@cbx_launcher = cbx_launcher
|
62
89
|
end
|
63
90
|
|
91
|
+
# @!visibility private
|
64
92
|
def to_s
|
65
|
-
"#<XCUITest #{url} : #{bundle_id} : #{device}>"
|
93
|
+
"#<XCUITest #{url} : #{bundle_id} : #{device} : #{cbx_launcher}>"
|
66
94
|
end
|
67
95
|
|
96
|
+
# @!visibility private
|
68
97
|
def inspect
|
69
98
|
to_s
|
70
99
|
end
|
71
100
|
|
72
101
|
# @!visibility private
|
73
|
-
def bundle_id
|
74
|
-
@bundle_id
|
75
|
-
end
|
76
|
-
|
77
|
-
# @!visibility private
|
78
|
-
def device
|
79
|
-
@device
|
80
|
-
end
|
81
|
-
|
82
|
-
# @!visibility private
|
83
|
-
def workspace
|
84
|
-
@workspace ||= lambda do
|
85
|
-
path = RunLoop::Environment.send(:cbxws)
|
86
|
-
if path
|
87
|
-
path
|
88
|
-
else
|
89
|
-
raise "TODO: figure out how to distribute the CBX-Runner"
|
90
|
-
end
|
91
|
-
end.call
|
92
|
-
end
|
93
|
-
|
94
102
|
def launch
|
95
103
|
start = Time.now
|
96
104
|
launch_cbx_runner
|
@@ -123,6 +131,15 @@ module RunLoop
|
|
123
131
|
launch_aut(bundle_id)
|
124
132
|
end
|
125
133
|
|
134
|
+
# @!visibility private
|
135
|
+
def runtime
|
136
|
+
options = http_options
|
137
|
+
request = request("device")
|
138
|
+
client = client(options)
|
139
|
+
response = client.get(request)
|
140
|
+
expect_200_response(response)
|
141
|
+
end
|
142
|
+
|
126
143
|
# @!visibility private
|
127
144
|
def query(mark)
|
128
145
|
options = http_options
|
@@ -134,23 +151,50 @@ module RunLoop
|
|
134
151
|
end
|
135
152
|
|
136
153
|
# @!visibility private
|
137
|
-
def
|
154
|
+
def query_for_coordinate(mark)
|
138
155
|
body = query(mark)
|
139
|
-
|
156
|
+
coordinate_from_query_result(body)
|
140
157
|
end
|
141
158
|
|
142
159
|
# @!visibility private
|
143
|
-
def
|
144
|
-
|
145
|
-
|
146
|
-
|
160
|
+
def tap_mark(mark)
|
161
|
+
coordinate = query_for_coordinate(mark)
|
162
|
+
tap_coordinate(coordinate[:x], coordinate[:y])
|
163
|
+
end
|
164
|
+
|
165
|
+
# @!visibility private
|
166
|
+
def tap_coordinate(x, y, options)
|
167
|
+
make_coordinate_gesture_request("touch", x, y)
|
168
|
+
end
|
169
|
+
|
170
|
+
# @!visibility private
|
171
|
+
def double_tap(x, y)
|
172
|
+
make_coordinate_gesture_request("double_tap", x, y)
|
173
|
+
end
|
174
|
+
|
175
|
+
# @!visibiity private
|
176
|
+
def coordinate_gesture_parameters(name, x, y, options={})
|
177
|
+
{
|
178
|
+
:gesture => name,
|
147
179
|
:specifiers => {
|
148
|
-
:coordinate =>
|
180
|
+
:coordinate => [x, y]
|
149
181
|
},
|
150
|
-
:options =>
|
182
|
+
:options => options
|
151
183
|
}
|
152
|
-
|
153
|
-
|
184
|
+
end
|
185
|
+
|
186
|
+
# @!visibility private
|
187
|
+
def coordinate_gesture_request(name, x, y, gesture_options={})
|
188
|
+
parameters = coordinate_gesture_parameters(name, x, y, gesture_options)
|
189
|
+
request("gesture", parameters)
|
190
|
+
end
|
191
|
+
|
192
|
+
# @!visibility private
|
193
|
+
def make_coordinate_gesture_request(name, x, y, options={})
|
194
|
+
gesture_options = options.fetch(:gesture_options, {})
|
195
|
+
http_options = options.fetch(:http_options, http_options())
|
196
|
+
request = coordinate_gesture_request(name, x, y, gesture_options)
|
197
|
+
client = client(http_options)
|
154
198
|
response = client.post(request)
|
155
199
|
expect_200_response(response)
|
156
200
|
end
|
@@ -162,7 +206,7 @@ module RunLoop
|
|
162
206
|
:orientation => orientation
|
163
207
|
}
|
164
208
|
request = request("rotate_home_button_to", parameters)
|
165
|
-
client(http_options)
|
209
|
+
client = client(http_options)
|
166
210
|
response = client.post(request)
|
167
211
|
json = expect_200_response(response)
|
168
212
|
sleep(sleep_for)
|
@@ -179,23 +223,46 @@ module RunLoop
|
|
179
223
|
:options => options
|
180
224
|
}
|
181
225
|
|
226
|
+
RunLoop.log_debug(%Q[
|
227
|
+
Sending request to perform '#{gesture}' with:
|
228
|
+
|
229
|
+
#{JSON.pretty_generate(parameters)}
|
230
|
+
|
231
|
+
])
|
182
232
|
request = request("gesture", parameters)
|
183
|
-
client(http_options)
|
233
|
+
client = client(http_options)
|
184
234
|
response = client.post(request)
|
185
235
|
expect_200_response(response)
|
186
236
|
end
|
187
237
|
|
188
238
|
# @!visibility private
|
189
|
-
def
|
190
|
-
|
239
|
+
def coordinate_from_query_result(hash)
|
240
|
+
matches = hash["result"]
|
241
|
+
|
242
|
+
if matches.nil? || matches.empty?
|
243
|
+
raise "Expected #{hash} to contain some results"
|
244
|
+
end
|
245
|
+
|
246
|
+
rect = matches.first["rect"]
|
191
247
|
h = rect["height"]
|
192
248
|
w = rect["width"]
|
193
249
|
x = rect["x"]
|
194
250
|
y = rect["y"]
|
195
251
|
|
196
|
-
touchx = x + (
|
197
|
-
touchy = y + (
|
198
|
-
|
252
|
+
touchx = x + (w/2.0)
|
253
|
+
touchy = y + (h/2.0)
|
254
|
+
|
255
|
+
new_rect = rect.dup
|
256
|
+
new_rect[:center_x] = touchx
|
257
|
+
new_rect[:center_y] = touchy
|
258
|
+
|
259
|
+
RunLoop.log_debug(%Q[Rect from query:
|
260
|
+
|
261
|
+
#{JSON.pretty_generate(new_rect)}
|
262
|
+
|
263
|
+
])
|
264
|
+
{:x => touchx,
|
265
|
+
:y => touchy}
|
199
266
|
end
|
200
267
|
|
201
268
|
private
|
@@ -223,7 +290,7 @@ module RunLoop
|
|
223
290
|
:undef => :replace, # Replace anything not defined in ASCII
|
224
291
|
:replace => "" # Use a blank for those replacements
|
225
292
|
}
|
226
|
-
encoded = device_name.encode(Encoding.find("ASCII"), encoding_options)
|
293
|
+
encoded = device_name.encode(::Encoding.find("ASCII"), encoding_options)
|
227
294
|
"http://#{encoded}.local:27753/"
|
228
295
|
end
|
229
296
|
end
|
@@ -296,14 +363,6 @@ module RunLoop
|
|
296
363
|
response = client.post(request)
|
297
364
|
body = response.body
|
298
365
|
RunLoop.log_debug("CBX-Runner says, \"#{body}\"")
|
299
|
-
5.times do
|
300
|
-
begin
|
301
|
-
health
|
302
|
-
sleep(1.0)
|
303
|
-
rescue => _
|
304
|
-
break
|
305
|
-
end
|
306
|
-
end
|
307
366
|
body
|
308
367
|
rescue => e
|
309
368
|
RunLoop.log_debug("CBX-Runner shutdown error: #{e}")
|
@@ -323,65 +382,22 @@ module RunLoop
|
|
323
382
|
body
|
324
383
|
end
|
325
384
|
|
326
|
-
# @!visibility private
|
327
|
-
def xcodebuild
|
328
|
-
env = {
|
329
|
-
"COMMAND_LINE_BUILD" => "1"
|
330
|
-
}
|
331
|
-
|
332
|
-
args = [
|
333
|
-
"xcrun",
|
334
|
-
"xcodebuild",
|
335
|
-
"-scheme", "CBXAppStub",
|
336
|
-
"-workspace", workspace,
|
337
|
-
"-config", "Debug",
|
338
|
-
"-destination",
|
339
|
-
"id=#{device.udid}",
|
340
|
-
"clean",
|
341
|
-
"test"
|
342
|
-
]
|
343
|
-
|
344
|
-
log_file = XCUITest.xcodebuild_log_file
|
345
|
-
|
346
|
-
options = {
|
347
|
-
:out => log_file,
|
348
|
-
:err => log_file
|
349
|
-
}
|
350
|
-
|
351
|
-
command = "#{env.map.each { |k, v| "#{k}=#{v}" }.join(" ")} #{args.join(" ")}"
|
352
|
-
RunLoop.log_unix_cmd("#{command} >& #{log_file}")
|
353
|
-
|
354
|
-
pid = Process.spawn(env, *args, options)
|
355
|
-
Process.detach(pid)
|
356
|
-
pid
|
357
|
-
end
|
358
|
-
|
359
385
|
# @!visibility private
|
360
386
|
def launch_cbx_runner
|
361
|
-
# Fail fast if CBXWS is not defined.
|
362
|
-
# WIP - we will distribute the workspace somehow.
|
363
|
-
workspace
|
364
|
-
|
365
387
|
shutdown
|
366
388
|
|
367
|
-
|
368
|
-
|
369
|
-
|
370
|
-
|
371
|
-
# quits the simulator
|
372
|
-
sim = CoreSimulator.new(device, "")
|
373
|
-
sim.launch_simulator
|
374
|
-
else
|
375
|
-
# anything special about physical devices?
|
376
|
-
end
|
389
|
+
options = {:log_cmd => true}
|
390
|
+
exec(["pkill", "xctestctl"], options)
|
391
|
+
exec(["pkill", "testmanagerd"], options)
|
392
|
+
exec(["pkill", "xcodebuild"], options)
|
377
393
|
|
378
394
|
start = Time.now
|
379
|
-
|
380
|
-
|
395
|
+
RunLoop.log_debug("Waiting for CBX-Runner to launch...")
|
396
|
+
pid = cbx_launcher.launch
|
381
397
|
health
|
398
|
+
RunLoop.log_debug("Took #{Time.now - start} launch and respond to /health")
|
382
399
|
|
383
|
-
|
384
|
-
pid.to_i
|
400
|
+
pid
|
385
401
|
end
|
386
402
|
|
387
403
|
# @!visibility private
|
@@ -423,26 +439,28 @@ Something went wrong.
|
|
423
439
|
# @!visibility private
|
424
440
|
def expect_200_response(response)
|
425
441
|
body = response_body_to_hash(response)
|
426
|
-
|
442
|
+
if response.status_code < 300 && !body["error"]
|
443
|
+
return body
|
444
|
+
end
|
427
445
|
|
428
|
-
|
429
|
-
|
446
|
+
if response.status_code > 300
|
447
|
+
raise RunLoop::XCUITest::HTTPError,
|
448
|
+
%Q[Expected status code < 300, found #{response.status_code}.
|
430
449
|
|
431
450
|
Server replied with:
|
432
451
|
|
433
452
|
#{body}
|
453
|
+
|
434
454
|
]
|
435
|
-
|
455
|
+
else
|
456
|
+
raise RunLoop::XCUITest::HTTPError,
|
457
|
+
%Q[Expected JSON response with no error, but found
|
436
458
|
|
437
|
-
|
438
|
-
def self.dot_dir
|
439
|
-
path = File.join(RunLoop::DotDir.directory, "xcuitest")
|
459
|
+
#{body["error"]}
|
440
460
|
|
441
|
-
|
442
|
-
FileUtils.mkdir_p(path)
|
443
|
-
end
|
461
|
+
]
|
444
462
|
|
445
|
-
|
463
|
+
end
|
446
464
|
end
|
447
465
|
|
448
466
|
# @!visibility private
|
data/scripts/lib/log.js
CHANGED
@@ -17,7 +17,7 @@ var Log = (function () {
|
|
17
17
|
|
18
18
|
return {
|
19
19
|
result: function (status, data) {
|
20
|
-
log_json({"status": status, "value": data, "index":_actualIndex})
|
20
|
+
log_json({"status": status, "value": data, "index":_actualIndex});
|
21
21
|
},
|
22
22
|
output: function (msg) {
|
23
23
|
log_json({"output": msg,"last_index":_actualIndex});
|
data/scripts/lib/on_alert.js
CHANGED
@@ -5,9 +5,9 @@ function findAlertTitle(alert) {
|
|
5
5
|
var title = alert.name();
|
6
6
|
var staticTexts;
|
7
7
|
|
8
|
-
if (title
|
8
|
+
if (title === null) {
|
9
9
|
staticTexts = alert.staticTexts();
|
10
|
-
if (staticTexts
|
10
|
+
if (staticTexts !== null && staticTexts.length > 0) {
|
11
11
|
|
12
12
|
title = staticText[0].name();
|
13
13
|
}
|
@@ -49,31 +49,85 @@ function englishLocalizations() {
|
|
49
49
|
|
50
50
|
function danishLocalizations() {
|
51
51
|
return [
|
52
|
-
// Location
|
53
52
|
["Tillad", /bruge din lokalitet, når du bruger appen/],
|
54
53
|
["Tillad", /også når du ikke bruger appen/],
|
55
|
-
["OK", /vil bruge din aktuelle placering/]
|
54
|
+
["OK", /vil bruge din aktuelle placering/],
|
55
|
+
["OK", /vil bruge dine kontakter/],
|
56
|
+
["OK", /vil bruge mikrofonen/],
|
57
|
+
["OK", /vil bruge din kalender/],
|
58
|
+
["OK", /vil bruge dine påmindelser/],
|
59
|
+
["OK", /vil bruge dine fotos/],
|
60
|
+
["OK", /ønsker adgang til Twitter-konti/],
|
61
|
+
["OK", /vil bruge din fysiske aktivitet og din træningsaktivitet/],
|
62
|
+
["OK", /vil bruge kameraet/],
|
63
|
+
["OK", /vil gerne sende dig meddelelser/]
|
56
64
|
];
|
57
65
|
}
|
58
66
|
|
59
|
-
function
|
67
|
+
function euSpanishLocalizations() {
|
68
|
+
return [
|
69
|
+
["Permitir", /acceder a tu ubicación mientras utilizas la aplicación/],
|
70
|
+
["Permitir", /acceder a tu ubicación aunque no estés utilizando la aplicación/],
|
71
|
+
["OK", /quiere acceder a tus contactos/],
|
72
|
+
["OK", /quiere acceder a tu calendario/],
|
73
|
+
["OK", /quiere acceder a tus recordatorios/],
|
74
|
+
["OK", /quiere acceder a tus fotos/],
|
75
|
+
["OK", /quiere obtener acceso a cuentas Twitter/],
|
76
|
+
["OK", /quiere acceder al micrófono/],
|
77
|
+
["OK", /desea acceder a tu actividad física y deportiva/],
|
78
|
+
["OK", /quiere acceder a la cámara/],
|
79
|
+
["OK", /quiere enviarte notificaciones/]
|
80
|
+
];
|
81
|
+
}
|
82
|
+
|
83
|
+
function es419SpanishLocalizations() {
|
60
84
|
return [
|
61
|
-
|
62
|
-
["
|
85
|
+
["Permitir", /acceda a tu ubicación mientras la app está en uso/],
|
86
|
+
["Permitir", /acceda a tu ubicación incluso cuando la app no está en uso/],
|
87
|
+
["OK", /quiere acceder a tu condición y actividad física/]
|
63
88
|
];
|
64
89
|
}
|
65
90
|
|
91
|
+
function spanishLocalizations() {
|
92
|
+
return [].concat(
|
93
|
+
euSpanishLocalizations(),
|
94
|
+
es419SpanishLocalizations()
|
95
|
+
);
|
96
|
+
}
|
97
|
+
|
66
98
|
function germanLocalizations() {
|
67
99
|
return [
|
68
|
-
|
69
|
-
["
|
100
|
+
["Ja", /Darf (?:.)+ Ihren aktuellen Ort verwenden/],
|
101
|
+
["Erlauben", /auf Ihren Standort zugreifen, wenn Sie die App benutzen/],
|
102
|
+
["Erlauben", /auch auf Ihren Standort zugreifen, wenn Sie die App nicht benutzen/],
|
103
|
+
["Erlauben", /auf Ihren Standort zugreifen, selbst wenn Sie die App nicht benutzen/],
|
104
|
+
["Ja", /auf Ihre Kontakte zugreifen/],
|
105
|
+
["Ja", /auf Ihren Kalender zugreifen/],
|
106
|
+
["Ja", /auf Ihre Erinnerungen zugreifen/],
|
107
|
+
["Ja", /auf Ihre Fotos zugreifen/],
|
108
|
+
["Erlauben", /möchte auf Twitter-Accounts zugreifen/],
|
109
|
+
["Ja", /auf das Mikrofon zugreifen/],
|
110
|
+
["Ja", /möchte auf Ihre Bewegungs- und Fitnessdaten zugreifen/],
|
111
|
+
["Ja", /auf Ihre Kamera zugreifen/],
|
112
|
+
["OK", /Ihnen Mitteilungen senden/]
|
70
113
|
];
|
71
114
|
}
|
72
115
|
|
73
116
|
function dutchLocalizations() {
|
74
117
|
return [
|
75
|
-
|
76
|
-
["
|
118
|
+
["Sta toe", /tot uw locatie toestaan terwijl u de app gebruikt/],
|
119
|
+
["Sta toe", /toegang tot uw locatie toestaan terwijl u de app gebruikt/],
|
120
|
+
["Sta toe", /ook toegang tot uw locatie toestaan, zelfs als u de app niet gebruikt/],
|
121
|
+
["Sta toe", /toegang tot uw locatie toestaan, zelfs als u de app niet gebruikt/],
|
122
|
+
["OK", /wil toegang tot uw contacten/],
|
123
|
+
["OK", /wil toegang tot uw agenda/],
|
124
|
+
["OK", /wil toegang tot uw herinneringen/],
|
125
|
+
["OK", /wil toegang tot uw foto's/],
|
126
|
+
["OK", /wil toegang tot Twitter-accounts/],
|
127
|
+
["OK", /wil toegang tot de microfoon/],
|
128
|
+
["OK", /wil toegang tot uw bewegings- en fitnessactiviteit/],
|
129
|
+
["OK", /wil toegang tot de camera/],
|
130
|
+
["OK", /wil u berichten sturen/]
|
77
131
|
];
|
78
132
|
}
|
79
133
|
|
@@ -89,13 +143,15 @@ function frenchLocalizations() {
|
|
89
143
|
["OK", /vous envoyer des notifications/],
|
90
144
|
["Autoriser", /à accéder à vos données de localisation lorsque vous utilisez l’app/],
|
91
145
|
["Autoriser", /à accéder à vos données de localisation même lorsque vous n’utilisez pas l’app/],
|
146
|
+
["Autoriser", /à accéder aussi à vos données de localisation lorsque vous n’utilisez pas l’app/],
|
92
147
|
["OK", /souhaite accéder à vos contacts/],
|
93
148
|
["OK", /souhaite accéder à votre calendrier/],
|
94
149
|
["OK", /souhaite accéder à vos rappels/],
|
95
150
|
["OK", /souhaite accéder à vos mouvements et vos activités physiques/],
|
96
151
|
["OK", /souhaite accéder à vos photos/],
|
97
152
|
["OK", /souhaite accéder à l’appareil photo/],
|
98
|
-
["OK", /souhaite accéder aux comptes Twitter/]
|
153
|
+
["OK", /souhaite accéder aux comptes Twitter/],
|
154
|
+
["OK", /souhaite accéder au micro/]
|
99
155
|
];
|
100
156
|
}
|
101
157
|
|
@@ -117,13 +173,42 @@ function isPrivacyAlert(alert) {
|
|
117
173
|
|
118
174
|
var title = findAlertTitle(alert);
|
119
175
|
|
120
|
-
// Comment this out
|
121
|
-
Log.output({"
|
176
|
+
// Comment this out when capturing new regexes. See the comment below.
|
177
|
+
Log.output({"alert":title});
|
122
178
|
|
123
179
|
// When debugging or trying to capture the regexes for a new
|
124
|
-
// localization, uncomment
|
125
|
-
//
|
126
|
-
//
|
180
|
+
// localization, uncomment the logging below.
|
181
|
+
//
|
182
|
+
// Notes:
|
183
|
+
// * Microphone alerts only appear on physical devices.
|
184
|
+
// * You have to click through the Health alert; it is completely blocking -
|
185
|
+
// tests will not proceed.
|
186
|
+
// * Generating bluetooth alerts is NYI.
|
187
|
+
// * In general, there will be a different alert on device for using location
|
188
|
+
// in background mode.
|
189
|
+
// * Alerts vary by iOS.
|
190
|
+
// * To reset notifications on devices:
|
191
|
+
// General > Settings > Reset > Reset Location + Privacy
|
192
|
+
// - These are the last table rows
|
193
|
+
// - APNS permissions are reset once a day.
|
194
|
+
// * On devices, set the device language in Settings.
|
195
|
+
//
|
196
|
+
// Use the Permission.app.
|
197
|
+
//
|
198
|
+
// * Alert text is printed at the end of every test.
|
199
|
+
// * Alert text is written to a file in Permissions/tmp.
|
200
|
+
//
|
201
|
+
// Examples:
|
202
|
+
//
|
203
|
+
// # Simulator running Mexican Spanish
|
204
|
+
// $ APP_LANG="es-MX" APP_LOCALE="es_MX" be cucumber -t @supported
|
205
|
+
//
|
206
|
+
// # Device running Dutch
|
207
|
+
// $ APP_LANG="nl" APP_LOCALE="nl" be cucumber -t @supported -p macmini
|
208
|
+
|
209
|
+
// This is very slow, so only do this if you are trying to capture regexes.
|
210
|
+
//var buttonNames = findAlertButtonNames(alert);
|
211
|
+
//Log.output({"alert":{"title":title, "buttons":buttonNames, "capture":"YES"}});
|
127
212
|
|
128
213
|
var answer;
|
129
214
|
var expression;
|