Add Interaction Preconditions
This commit is contained in:
Родитель
0d7822c6dc
Коммит
0433ffe32d
|
@ -34,7 +34,7 @@
|
|||
AA1D653F1C21A9690069F90D /* FBCollectionDescriptions.m in Sources */ = {isa = PBXBuildFile; fileRef = AA1D653D1C21A9690069F90D /* FBCollectionDescriptions.m */; };
|
||||
AA1D65421C21B38D0069F90D /* FBCrashLogInfo.h in Headers */ = {isa = PBXBuildFile; fileRef = AA1D65401C21B38D0069F90D /* FBCrashLogInfo.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
AA1D65431C21B38D0069F90D /* FBCrashLogInfo.m in Sources */ = {isa = PBXBuildFile; fileRef = AA1D65411C21B38D0069F90D /* FBCrashLogInfo.m */; };
|
||||
AA1D65461C21CD2A0069F90D /* FBASLParser.h in Headers */ = {isa = PBXBuildFile; fileRef = AA1D65441C21CD2A0069F90D /* FBASLParser.h */; };
|
||||
AA1D65461C21CD2A0069F90D /* FBASLParser.h in Headers */ = {isa = PBXBuildFile; fileRef = AA1D65441C21CD2A0069F90D /* FBASLParser.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
AA1D65471C21CD2A0069F90D /* FBASLParser.m in Sources */ = {isa = PBXBuildFile; fileRef = AA1D65451C21CD2A0069F90D /* FBASLParser.m */; };
|
||||
AA3230CB1BDA387700C5BA01 /* FBSimulatorControlAssertions.m in Sources */ = {isa = PBXBuildFile; fileRef = AA3230CA1BDA387700C5BA01 /* FBSimulatorControlAssertions.m */; };
|
||||
AA5639551C060005009BAFAA /* FBSimulatorControl.h in Headers */ = {isa = PBXBuildFile; fileRef = AA5639541C05FFF5009BAFAA /* FBSimulatorControl.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
|
@ -166,6 +166,8 @@
|
|||
AACA2C381C2976B100979C45 /* FBAddVideoPolyfill.m in Sources */ = {isa = PBXBuildFile; fileRef = AACA2C361C2976B100979C45 /* FBAddVideoPolyfill.m */; };
|
||||
AAD3051F1BD4D5B10047376E /* photo0.png in Resources */ = {isa = PBXBuildFile; fileRef = AAD3051D1BD4D5B10047376E /* photo0.png */; };
|
||||
AAD305201BD4D5B10047376E /* photo1.png in Resources */ = {isa = PBXBuildFile; fileRef = AAD3051E1BD4D5B10047376E /* photo1.png */; };
|
||||
AAF2D3561C33EA3100434516 /* FBSimulatorInteraction+Lifecycle.h in Headers */ = {isa = PBXBuildFile; fileRef = AAF2D3541C33EA3100434516 /* FBSimulatorInteraction+Lifecycle.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
AAF2D3571C33EA3100434516 /* FBSimulatorInteraction+Lifecycle.m in Sources */ = {isa = PBXBuildFile; fileRef = AAF2D3551C33EA3100434516 /* FBSimulatorInteraction+Lifecycle.m */; };
|
||||
AAF8DA651C1AFF81003B519E /* FBProcessInfo+Helpers.h in Headers */ = {isa = PBXBuildFile; fileRef = AAF8DA631C1AFF81003B519E /* FBProcessInfo+Helpers.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
AAF8DA661C1AFF81003B519E /* FBProcessInfo+Helpers.m in Sources */ = {isa = PBXBuildFile; fileRef = AAF8DA641C1AFF81003B519E /* FBProcessInfo+Helpers.m */; };
|
||||
AAF8DA691C1AFFB1003B519E /* FBProcessInfo.h in Headers */ = {isa = PBXBuildFile; fileRef = AAF8DA671C1AFFB1003B519E /* FBProcessInfo.h */; settings = {ATTRIBUTES = (Public, ); }; };
|
||||
|
@ -946,6 +948,8 @@
|
|||
AACA2C361C2976B100979C45 /* FBAddVideoPolyfill.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = FBAddVideoPolyfill.m; sourceTree = "<group>"; };
|
||||
AAD3051D1BD4D5B10047376E /* photo0.png */ = {isa = PBXFileReference; lastKnownFileType = image.png; path = photo0.png; sourceTree = "<group>"; };
|
||||
AAD3051E1BD4D5B10047376E /* photo1.png */ = {isa = PBXFileReference; lastKnownFileType = image.png; path = photo1.png; sourceTree = "<group>"; };
|
||||
AAF2D3541C33EA3100434516 /* FBSimulatorInteraction+Lifecycle.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = "FBSimulatorInteraction+Lifecycle.h"; sourceTree = "<group>"; };
|
||||
AAF2D3551C33EA3100434516 /* FBSimulatorInteraction+Lifecycle.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = "FBSimulatorInteraction+Lifecycle.m"; sourceTree = "<group>"; };
|
||||
AAF8DA631C1AFF81003B519E /* FBProcessInfo+Helpers.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = "FBProcessInfo+Helpers.h"; sourceTree = "<group>"; };
|
||||
AAF8DA641C1AFF81003B519E /* FBProcessInfo+Helpers.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = "FBProcessInfo+Helpers.m"; sourceTree = "<group>"; };
|
||||
AAF8DA671C1AFFB1003B519E /* FBProcessInfo.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = FBProcessInfo.h; sourceTree = "<group>"; };
|
||||
|
@ -1727,15 +1731,19 @@
|
|||
AA9516DE1C15F54600A89CAD /* Interactions */ = {
|
||||
isa = PBXGroup;
|
||||
children = (
|
||||
AA9516DF1C15F54600A89CAD /* FBInteraction+Private.h */,
|
||||
AA9516E01C15F54600A89CAD /* FBInteraction.h */,
|
||||
AA9516E11C15F54600A89CAD /* FBInteraction.m */,
|
||||
AA9516DF1C15F54600A89CAD /* FBInteraction+Private.h */,
|
||||
AA9516F11C15F54600A89CAD /* FBSimulatorInteraction.h */,
|
||||
AA9516F21C15F54600A89CAD /* FBSimulatorInteraction.m */,
|
||||
AA9516E21C15F54600A89CAD /* FBSimulatorInteraction+Agents.h */,
|
||||
AA9516E31C15F54600A89CAD /* FBSimulatorInteraction+Agents.m */,
|
||||
AA9516E41C15F54600A89CAD /* FBSimulatorInteraction+Applications.h */,
|
||||
AA9516E51C15F54600A89CAD /* FBSimulatorInteraction+Applications.m */,
|
||||
AA9516E81C15F54600A89CAD /* FBSimulatorInteraction+Diagnostics.h */,
|
||||
AA9516E91C15F54600A89CAD /* FBSimulatorInteraction+Diagnostics.m */,
|
||||
AAF2D3541C33EA3100434516 /* FBSimulatorInteraction+Lifecycle.h */,
|
||||
AAF2D3551C33EA3100434516 /* FBSimulatorInteraction+Lifecycle.m */,
|
||||
AA9516EA1C15F54600A89CAD /* FBSimulatorInteraction+Private.h */,
|
||||
AA9516EB1C15F54600A89CAD /* FBSimulatorInteraction+Setup.h */,
|
||||
AA9516EC1C15F54600A89CAD /* FBSimulatorInteraction+Setup.m */,
|
||||
|
@ -1743,8 +1751,6 @@
|
|||
AA9516EE1C15F54600A89CAD /* FBSimulatorInteraction+Upload.m */,
|
||||
AA9516EF1C15F54600A89CAD /* FBSimulatorInteraction+Video.h */,
|
||||
AA9516F01C15F54600A89CAD /* FBSimulatorInteraction+Video.m */,
|
||||
AA9516F11C15F54600A89CAD /* FBSimulatorInteraction.h */,
|
||||
AA9516F21C15F54600A89CAD /* FBSimulatorInteraction.m */,
|
||||
);
|
||||
path = Interactions;
|
||||
sourceTree = "<group>";
|
||||
|
@ -1973,7 +1979,6 @@
|
|||
AA9517851C15F54600A89CAD /* FBSimulatorPool.h in Headers */,
|
||||
AA9517621C15F54600A89CAD /* FBInteraction+Private.h in Headers */,
|
||||
AA9517511C15F54600A89CAD /* FBSimulatorConfiguration.h in Headers */,
|
||||
AA1D65461C21CD2A0069F90D /* FBASLParser.h in Headers */,
|
||||
AA0771F11C1ADFA300E7FD52 /* FBBinaryParser.h in Headers */,
|
||||
AA9517471C15F54600A89CAD /* FBProcessLaunchConfiguration+Helpers.h in Headers */,
|
||||
AA9517BE1C15F54600A89CAD /* FBSimulatorVideoRecorder.h in Headers */,
|
||||
|
@ -2025,6 +2030,8 @@
|
|||
AA9517841C15F54600A89CAD /* FBSimulatorPool+Private.h in Headers */,
|
||||
AACA2C371C2976B100979C45 /* FBAddVideoPolyfill.h in Headers */,
|
||||
AA9517A51C15F54600A89CAD /* FBTask.h in Headers */,
|
||||
AA1D65461C21CD2A0069F90D /* FBASLParser.h in Headers */,
|
||||
AAF2D3561C33EA3100434516 /* FBSimulatorInteraction+Lifecycle.h in Headers */,
|
||||
AA95179D1C15F54600A89CAD /* FBProcessQuery.h in Headers */,
|
||||
AA9517A11C15F54600A89CAD /* FBSimulatorSession+Private.h in Headers */,
|
||||
AA9517871C15F54600A89CAD /* FBSimulatorPredicates.h in Headers */,
|
||||
|
@ -2180,6 +2187,7 @@
|
|||
AA9517A31C15F54600A89CAD /* FBSimulatorSession.m in Sources */,
|
||||
AA9517BF1C15F54600A89CAD /* FBSimulatorVideoRecorder.m in Sources */,
|
||||
AA95178F1C15F54600A89CAD /* FBSimulatorApplication.m in Sources */,
|
||||
AAF2D3571C33EA3100434516 /* FBSimulatorInteraction+Lifecycle.m in Sources */,
|
||||
AA95174F1C15F54600A89CAD /* FBSimulatorConfiguration+CoreSimulator.m in Sources */,
|
||||
AAF8DA661C1AFF81003B519E /* FBProcessInfo+Helpers.m in Sources */,
|
||||
AA9517B71C15F54600A89CAD /* FBSimDeviceWrapper.m in Sources */,
|
||||
|
|
|
@ -8,6 +8,7 @@
|
|||
*/
|
||||
|
||||
#import <FBSimulatorControl/FBAddVideoPolyfill.h>
|
||||
#import <FBSimulatorControl/FBASLParser.h>
|
||||
#import <FBSimulatorControl/FBBinaryParser.h>
|
||||
#import <FBSimulatorControl/FBCollectionDescriptions.h>
|
||||
#import <FBSimulatorControl/FBCompositeSimulatorEventSink.h>
|
||||
|
@ -47,6 +48,7 @@
|
|||
#import <FBSimulatorControl/FBSimulatorInteraction+Agents.h>
|
||||
#import <FBSimulatorControl/FBSimulatorInteraction+Applications.h>
|
||||
#import <FBSimulatorControl/FBSimulatorInteraction+Diagnostics.h>
|
||||
#import <FBSimulatorControl/FBSimulatorInteraction+Lifecycle.h>
|
||||
#import <FBSimulatorControl/FBSimulatorInteraction+Private.h>
|
||||
#import <FBSimulatorControl/FBSimulatorInteraction+Setup.h>
|
||||
#import <FBSimulatorControl/FBSimulatorInteraction+Upload.h>
|
||||
|
|
|
@ -20,6 +20,7 @@
|
|||
Chains an interaction using the provided block
|
||||
|
||||
@param block the block to perform the interaction with. Passes an NSError to return error information and the interaction for further chaining.
|
||||
@return the reciever, for chaining.
|
||||
*/
|
||||
- (instancetype)interact:(BOOL (^)(NSError **error, id interaction))block;
|
||||
|
||||
|
@ -27,11 +28,14 @@
|
|||
Fails the Interaction with the provided error.
|
||||
|
||||
@param error the error to fail the interaction with.
|
||||
@return the reciever, for chaining.
|
||||
*/
|
||||
- (instancetype)failWith:(NSError *)error;
|
||||
|
||||
/**
|
||||
Passes the interaction.
|
||||
|
||||
@return the reciever, for chaining.
|
||||
*/
|
||||
- (instancetype)succeed;
|
||||
|
||||
|
|
|
@ -33,11 +33,16 @@
|
|||
|
||||
/**
|
||||
Retries the last chained interaction by `retries`, if it fails.
|
||||
|
||||
@param retries the number of times to retry if the prior interaction fails.
|
||||
@return the reciever, for chaining.
|
||||
*/
|
||||
- (instancetype)retry:(NSUInteger)retries;
|
||||
|
||||
/**
|
||||
Ignores any failure that occurs in the last interaction if any occured.
|
||||
|
||||
@return the reciever, for chaining.
|
||||
*/
|
||||
- (instancetype)ignoreFailure;
|
||||
|
||||
|
|
|
@ -16,11 +16,17 @@
|
|||
|
||||
/**
|
||||
Launches the provided Agent with the given Configuration.
|
||||
|
||||
@param agentLaunch the Agent Launch Configuration to Launch.
|
||||
@return the reciever, for chaining.
|
||||
*/
|
||||
- (instancetype)launchAgent:(FBAgentLaunchConfiguration *)agentLaunch;
|
||||
|
||||
/**
|
||||
Launches the provided Agent.
|
||||
|
||||
@param agent the Agent Launch Configuration to Launch.
|
||||
@return the reciever, for chaining.
|
||||
*/
|
||||
- (instancetype)killAgent:(FBSimulatorBinary *)agent;
|
||||
|
||||
|
|
|
@ -32,9 +32,7 @@
|
|||
{
|
||||
NSParameterAssert(agentLaunch);
|
||||
|
||||
FBSimulator *simulator = self.simulator;
|
||||
|
||||
return [self interact:^ BOOL (NSError **error, id _) {
|
||||
return [self interactWithBootedSimulator:^ BOOL (NSError **error, FBSimulator *simulator) {
|
||||
NSError *innerError = nil;
|
||||
NSFileHandle *stdOut = nil;
|
||||
NSFileHandle *stdErr = nil;
|
||||
|
@ -66,9 +64,7 @@
|
|||
{
|
||||
NSParameterAssert(agent);
|
||||
|
||||
FBSimulator *simulator = self.simulator;
|
||||
|
||||
return [self binary:agent interact:^ BOOL (FBProcessInfo *process, NSError **error) {
|
||||
return [self binary:agent interact:^ BOOL (NSError **error, FBSimulator *simulator, FBProcessInfo *process) {
|
||||
if (!kill(process.processIdentifier, SIGKILL)) {
|
||||
return [[[FBSimulatorError describeFormat:@"SIGKILL of Agent %@ of PID %d failed", agent, process.processIdentifier] inSimulator:simulator] failBool:error];
|
||||
}
|
||||
|
|
|
@ -15,21 +15,33 @@
|
|||
|
||||
/**
|
||||
Installs the given Application.
|
||||
|
||||
@param application the Application to Install.
|
||||
@return the reciever, for chaining.
|
||||
*/
|
||||
- (instancetype)installApplication:(FBSimulatorApplication *)application;
|
||||
|
||||
/**
|
||||
Launches the Application with the given Configuration.
|
||||
|
||||
@param appLaunch the Application Launch Configuration to Launch.
|
||||
@return the reciever, for chaining.
|
||||
*/
|
||||
- (instancetype)launchApplication:(FBApplicationLaunchConfiguration *)appLaunch;
|
||||
|
||||
/**
|
||||
Unix Signals the Application.
|
||||
|
||||
@param signal the unix signo to send.
|
||||
@return the reciever, for chaining.
|
||||
*/
|
||||
- (instancetype)signal:(int)signal application:(FBSimulatorApplication *)application;
|
||||
|
||||
/**
|
||||
Kills the provided Application.
|
||||
|
||||
@param application the Application to kill.
|
||||
@return the reciever, for chaining.
|
||||
*/
|
||||
- (instancetype)killApplication:(FBSimulatorApplication *)application;
|
||||
|
||||
|
|
|
@ -32,9 +32,7 @@
|
|||
{
|
||||
NSParameterAssert(application);
|
||||
|
||||
FBSimulator *simulator = self.simulator;
|
||||
|
||||
return [self interact:^ BOOL (NSError **error, id _) {
|
||||
return [self interactWithBootedSimulator:^ BOOL (NSError **error, FBSimulator *simulator) {
|
||||
NSError *innerError = nil;
|
||||
if (![simulator.simDeviceWrapper installApplication:[NSURL fileURLWithPath:application.path] withOptions:@{@"CFBundleIdentifier" : application.bundleID} error:error]) {
|
||||
return [[[FBSimulatorError describeFormat:@"Failed to install Application %@", application] causedBy:innerError] failBool:error];
|
||||
|
@ -48,9 +46,7 @@
|
|||
{
|
||||
NSParameterAssert(appLaunch);
|
||||
|
||||
FBSimulator *simulator = self.simulator;
|
||||
|
||||
return [self interact:^ BOOL (NSError **error, id _) {
|
||||
return [self interactWithBootedSimulator:^ BOOL (NSError **error, FBSimulator *simulator) {
|
||||
NSError *innerError = nil;
|
||||
NSDictionary *installedApps = [simulator.device installedAppsWithError:&innerError];
|
||||
if (!installedApps) {
|
||||
|
@ -93,9 +89,7 @@
|
|||
{
|
||||
NSParameterAssert(application);
|
||||
|
||||
FBSimulator *simulator = self.simulator;
|
||||
|
||||
return [self binary:application.binary interact:^ BOOL (FBProcessInfo *process, NSError **error) {
|
||||
return [self binary:application.binary interact:^ BOOL (NSError **error, FBSimulator *simulator, FBProcessInfo *process) {
|
||||
[simulator.eventSink applicationDidTerminate:process expected:YES];
|
||||
int returnCode = kill(process.processIdentifier, signo);
|
||||
if (returnCode != 0) {
|
||||
|
|
|
@ -52,9 +52,7 @@ typedef id<FBTask>(^FBDiagnosticTaskFactory)(FBTaskExecutor *executor, pid_t pro
|
|||
NSParameterAssert(application);
|
||||
NSParameterAssert(name);
|
||||
|
||||
FBSimulator *simulator = self.simulator;
|
||||
|
||||
return [self binary:application.binary interact:^ BOOL (FBProcessInfo *process, NSError **error) {
|
||||
return [self binary:application.binary interact:^ BOOL (NSError **error, FBSimulator *simulator, FBProcessInfo *process) {
|
||||
id<FBTask> task = taskFactory(FBTaskExecutor.sharedInstance, process.processIdentifier);
|
||||
NSCAssert(task, @"Task should not be nil");
|
||||
|
||||
|
@ -78,9 +76,7 @@ typedef id<FBTask>(^FBDiagnosticTaskFactory)(FBTaskExecutor *executor, pid_t pro
|
|||
NSParameterAssert(application);
|
||||
NSParameterAssert(name);
|
||||
|
||||
FBSimulator *simulator = self.simulator;
|
||||
|
||||
return [self binary:application.binary interact:^ BOOL (FBProcessInfo *process, NSError **error) {
|
||||
return [self binary:application.binary interact:^ BOOL (NSError **error, FBSimulator *simulator, FBProcessInfo *process) {
|
||||
id<FBTask> task = taskFactory(FBTaskExecutor.sharedInstance, process.processIdentifier);
|
||||
NSCAssert(task, @"Task should not be nil");
|
||||
|
||||
|
|
|
@ -0,0 +1,41 @@
|
|||
/**
|
||||
* Copyright (c) 2015-present, Facebook, Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* This source code is licensed under the BSD-style license found in the
|
||||
* LICENSE file in the root directory of this source tree. An additional grant
|
||||
* of patent rights can be found in the PATENTS file in the same directory.
|
||||
*/
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
|
||||
#import <FBSimulatorControl/FBSimulatorInteraction.h>
|
||||
|
||||
/**
|
||||
Interactions for the Lifecycle of the Simulator.
|
||||
*/
|
||||
@interface FBSimulatorInteraction (Lifecycle)
|
||||
|
||||
/**
|
||||
Boots the Simulator.
|
||||
|
||||
@return the reciever, for chaining.
|
||||
*/
|
||||
- (instancetype)bootSimulator;
|
||||
|
||||
/**
|
||||
Shuts the Simulator down.
|
||||
|
||||
@return the reciever, for chaining.
|
||||
*/
|
||||
- (instancetype)shutdownSimulator;
|
||||
|
||||
/**
|
||||
Opens the provided URL on the Simulator.
|
||||
|
||||
@param url the URL to open.
|
||||
@return the reciever, for chaining.
|
||||
*/
|
||||
- (instancetype)openURL:(NSURL *)url;
|
||||
|
||||
@end
|
|
@ -0,0 +1,140 @@
|
|||
/**
|
||||
* Copyright (c) 2015-present, Facebook, Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* This source code is licensed under the BSD-style license found in the
|
||||
* LICENSE file in the root directory of this source tree. An additional grant
|
||||
* of patent rights can be found in the PATENTS file in the same directory.
|
||||
*/
|
||||
|
||||
#import "FBSimulatorInteraction+Lifecycle.h"
|
||||
|
||||
#import <CoreSimulator/SimDevice.h>
|
||||
|
||||
#import "FBSimulatorInteraction+Private.h"
|
||||
#import "FBCollectionDescriptions.h"
|
||||
#import "FBInteraction+Private.h"
|
||||
#import "FBProcessLaunchConfiguration.h"
|
||||
#import "FBProcessQuery+Simulators.h"
|
||||
#import "FBSimulator+Helpers.h"
|
||||
#import "FBSimulator.h"
|
||||
#import "FBSimulatorApplication.h"
|
||||
#import "FBSimulatorConfiguration+CoreSimulator.h"
|
||||
#import "FBSimulatorConfiguration.h"
|
||||
#import "FBSimulatorControl.h"
|
||||
#import "FBSimulatorControlConfiguration.h"
|
||||
#import "FBSimulatorControlGlobalConfiguration.h"
|
||||
#import "FBSimulatorError.h"
|
||||
#import "FBSimulatorEventSink.h"
|
||||
#import "FBSimulatorLaunchInfo.h"
|
||||
#import "FBSimulatorPool.h"
|
||||
#import "FBSimulatorSession+Private.h"
|
||||
#import "FBSimulatorTerminationStrategy.h"
|
||||
#import "FBTaskExecutor.h"
|
||||
|
||||
@implementation FBSimulatorInteraction (Lifecycle)
|
||||
|
||||
- (instancetype)bootSimulator
|
||||
{
|
||||
return [self interactWithShutdownSimulator:^ BOOL (NSError **error, FBSimulator *simulator) {
|
||||
// Construct the Arguments
|
||||
NSMutableArray *arguments = [NSMutableArray arrayWithArray:@[
|
||||
@"--args",
|
||||
@"-CurrentDeviceUDID", simulator.udid,
|
||||
@"-ConnectHardwareKeyboard", @"0"
|
||||
]];
|
||||
NSArray *scaleArguments = [simulator.configuration lastScaleCommandLineArgumentsWithError:nil];
|
||||
if (scaleArguments) {
|
||||
[arguments addObjectsFromArray:scaleArguments];
|
||||
}
|
||||
if (simulator.pool.configuration.deviceSetPath) {
|
||||
if (!FBSimulatorControlGlobalConfiguration.supportsCustomDeviceSets) {
|
||||
return [[[FBSimulatorError describe:@"Cannot use custom Device Set on current platform"] inSimulator:simulator] failBool:error];
|
||||
}
|
||||
[arguments addObjectsFromArray:@[@"-DeviceSetPath", simulator.pool.configuration.deviceSetPath]];
|
||||
}
|
||||
|
||||
// Construct and start the task.
|
||||
id<FBTask> task = [[[[[FBTaskExecutor.sharedInstance
|
||||
withLaunchPath:FBSimulatorApplication.simulatorApplication.binary.path]
|
||||
withArguments:[arguments copy]]
|
||||
withEnvironmentAdditions:@{ FBSimulatorControlSimulatorLaunchEnvironmentSimulatorUDID : simulator.udid }]
|
||||
build]
|
||||
startAsynchronously];
|
||||
|
||||
// Expect no immediate error.
|
||||
if (task.error) {
|
||||
return [[[[FBSimulatorError describe:@"Failed to Launch Simulator Process"] causedBy:task.error] inSimulator:simulator] failBool:error];
|
||||
}
|
||||
|
||||
// Expect the state of the simulator to be updated.
|
||||
BOOL didBoot = [simulator waitOnState:FBSimulatorStateBooted];
|
||||
if (!didBoot) {
|
||||
return [[[FBSimulatorError describeFormat:@"Timed out waiting for device to be Booted, got %@", simulator.device.stateString] inSimulator:simulator] failBool:error];
|
||||
}
|
||||
|
||||
// Expect the launch info for the process to exist.
|
||||
FBSimulatorLaunchInfo *launchInfo = [FBSimulatorLaunchInfo fromSimDevice:simulator.device query:simulator.processQuery];
|
||||
if (!launchInfo) {
|
||||
return [[[FBSimulatorError describe:@"Could not obtain process info for booted simulator process"] inSimulator:simulator] failBool:error];
|
||||
}
|
||||
|
||||
// Waitng for all required processes to start
|
||||
NSSet *requiredProcessNames = simulator.requiredProcessNamesToVerifyBooted;
|
||||
BOOL didStartAllRequiredProcesses = [NSRunLoop.mainRunLoop spinRunLoopWithTimeout:FBSimulatorControlGlobalConfiguration.slowTimeout untilTrue:^ BOOL {
|
||||
NSSet *runningProcessNames = [NSSet setWithArray:[launchInfo.launchedProcesses valueForKey:@"processName"]];
|
||||
return [requiredProcessNames isSubsetOfSet:runningProcessNames];
|
||||
}];
|
||||
if (!didStartAllRequiredProcesses) {
|
||||
return [[[FBSimulatorError
|
||||
describeFormat:@"Timed out waiting for all required processes %@ to start", [FBCollectionDescriptions oneLineDescriptionFromArray:requiredProcessNames.allObjects]]
|
||||
inSimulator:simulator]
|
||||
failBool:error];
|
||||
}
|
||||
|
||||
// Pass on the success to the event sink.
|
||||
[simulator.eventSink didStartWithLaunchInfo:launchInfo];
|
||||
[simulator.eventSink terminationHandleAvailable:task];
|
||||
|
||||
return YES;
|
||||
}];
|
||||
}
|
||||
|
||||
- (instancetype)shutdownSimulator
|
||||
{
|
||||
return [self interactWithBootedSimulator:^ BOOL (NSError **error, FBSimulator *simulator) {
|
||||
FBSimulatorLaunchInfo *launchInfo = simulator.launchInfo;
|
||||
if (!launchInfo) {
|
||||
return [[[FBSimulatorError describe:@"Could not shutdown simulator as there is no available launch info"] inSimulator:simulator] failBool:error];
|
||||
}
|
||||
|
||||
FBSimulatorTerminationStrategy *terminationStrategy = [FBSimulatorTerminationStrategy
|
||||
withConfiguration:simulator.pool.configuration
|
||||
processQuery:simulator.processQuery
|
||||
logger:simulator.pool.logger];
|
||||
|
||||
NSError *innerError = nil;
|
||||
if (![terminationStrategy killSimulators:@[simulator] withError:&innerError]) {
|
||||
return [[[[FBSimulatorError describe:@"Could not shutdown simulator"] inSimulator:simulator] causedBy:innerError] failBool:error];
|
||||
}
|
||||
[simulator.eventSink didTerminate:YES];
|
||||
|
||||
return YES;
|
||||
}];
|
||||
}
|
||||
|
||||
- (instancetype)openURL:(NSURL *)url
|
||||
{
|
||||
NSParameterAssert(url);
|
||||
|
||||
return [self interactWithBootedSimulator:^ BOOL (NSError **error, FBSimulator *simulator) {
|
||||
NSError *innerError = nil;
|
||||
if (![simulator.device openURL:url error:&innerError]) {
|
||||
NSString *description = [NSString stringWithFormat:@"Failed to open URL %@ on simulator %@", url, simulator];
|
||||
return [FBSimulatorError failBoolWithError:innerError description:description errorOut:error];
|
||||
}
|
||||
return YES;
|
||||
}];
|
||||
}
|
||||
|
||||
@end
|
|
@ -18,7 +18,27 @@
|
|||
|
||||
/**
|
||||
Chains an interaction on an process, for the given application.
|
||||
|
||||
@param binary the binary to interact with.
|
||||
@param block the block to execute with the process.
|
||||
@return the reciever, for chaining.
|
||||
*/
|
||||
- (instancetype)binary:(FBSimulatorBinary *)binary interact:(BOOL (^)(FBProcessInfo *process, NSError **error))block;
|
||||
- (instancetype)binary:(FBSimulatorBinary *)binary interact:(BOOL (^)(NSError **error, FBSimulator *simulator, FBProcessInfo *process))block;
|
||||
|
||||
/**
|
||||
Interact with a Shutdown Simulator. Will ensure that the Simulator is in the appropriate state.
|
||||
|
||||
@param block the block to execute with the Shutdown Simulator.
|
||||
@return the reciever, for chaining.
|
||||
*/
|
||||
- (instancetype)interactWithShutdownSimulator:(BOOL (^)(NSError **error, FBSimulator *simulator))block;
|
||||
|
||||
/**
|
||||
Interact with a Shutdown Simulator. Will ensure that the Simulator is in the appropriate state.s
|
||||
|
||||
@param block the block to execute with the Shutdown Simulator.
|
||||
@return the reciever, for chaining.
|
||||
*/
|
||||
- (instancetype)interactWithBootedSimulator:(BOOL (^)(NSError **error, FBSimulator *simulator))block;
|
||||
|
||||
@end
|
||||
|
|
|
@ -15,6 +15,7 @@
|
|||
Sets the locale for the simulator.
|
||||
|
||||
@param locale the locale to set, must not be nil.
|
||||
@return the reciever, for chaining.
|
||||
*/
|
||||
- (instancetype)setLocale:(NSLocale *)locale;
|
||||
|
||||
|
@ -22,14 +23,17 @@
|
|||
Authorizes the Location Settings for the provided application.
|
||||
|
||||
@param application the Application to authorize settings for.
|
||||
@return the reciever, for chaining.
|
||||
*/
|
||||
- (instancetype)authorizeLocationSettingsForApplication:(FBSimulatorApplication *)application;
|
||||
|
||||
/**
|
||||
Setups keyboard for simulator
|
||||
Prepares the Simulator Keyboard, prior to launch.
|
||||
1) Disables Caps Lock
|
||||
2) Disables Auto Capitalize
|
||||
3) Disables Auto Correction / QuickType
|
||||
|
||||
@return the reciever, for chaining.
|
||||
*/
|
||||
- (instancetype)setupKeyboard;
|
||||
|
||||
|
|
|
@ -23,9 +23,7 @@
|
|||
{
|
||||
NSParameterAssert(locale);
|
||||
|
||||
FBSimulator *simulator = self.simulator;
|
||||
|
||||
return [self interact:^ BOOL (NSError **error, id _) {
|
||||
return [self interactWithShutdownSimulator:^ BOOL (NSError **error, FBSimulator *simulator) {
|
||||
NSString *localeIdentifier = [locale localeIdentifier];
|
||||
NSString *languageIdentifier = [NSLocale canonicalLanguageIdentifierFromString:localeIdentifier];
|
||||
NSDictionary *preferencesDict = @{
|
||||
|
@ -47,9 +45,7 @@
|
|||
{
|
||||
NSParameterAssert(application);
|
||||
|
||||
FBSimulator *simulator = self.simulator;
|
||||
|
||||
return [self interact:^ BOOL (NSError **error, id _) {
|
||||
return [self interactWithShutdownSimulator:^ BOOL (NSError **error, FBSimulator *simulator) {
|
||||
NSString *simulatorRoot = simulator.device.dataPath;
|
||||
NSString *bundleID = application.bundleID;
|
||||
|
||||
|
@ -81,9 +77,7 @@
|
|||
|
||||
- (instancetype)setupKeyboard
|
||||
{
|
||||
FBSimulator *simulator = self.simulator;
|
||||
|
||||
return [self interact:^ BOOL (NSError **error, id _) {
|
||||
return [self interactWithShutdownSimulator:^ BOOL (NSError **error, FBSimulator *simulator) {
|
||||
NSString *simulatorRoot = simulator.device.dataPath;
|
||||
NSString *preferencesPath = [simulatorRoot stringByAppendingPathComponent:@"Library/Preferences/com.apple.Preferences.plist"];
|
||||
NSError *innerError = nil;
|
||||
|
|
|
@ -15,6 +15,7 @@
|
|||
Uploads photos to the Camera Roll of the Simulator
|
||||
|
||||
@param photoPaths photoPaths an NSArray<NSString *> of File Paths for the Photos to Upload.
|
||||
@return the reciever, for chaining.
|
||||
*/
|
||||
- (instancetype)uploadPhotos:(NSArray *)photoPaths;
|
||||
|
||||
|
@ -22,6 +23,7 @@
|
|||
Uploads videos to the Camera Roll of the Simulator
|
||||
|
||||
@param videoPaths an NSArray<NSString *> of File Paths for the Videos to Upload.
|
||||
@return the reciever, for chaining.
|
||||
*/
|
||||
- (instancetype)uploadVideos:(NSArray *)videoPaths;
|
||||
|
||||
|
|
|
@ -32,9 +32,7 @@
|
|||
return [self succeed];
|
||||
}
|
||||
|
||||
FBSimulator *simulator = self.simulator;
|
||||
|
||||
return [self interact:^ BOOL (NSError **error, id _) {
|
||||
return [self interactWithBootedSimulator:^ BOOL (NSError **error, FBSimulator *simulator) {
|
||||
if (simulator.state != FBSimulatorStateBooted) {
|
||||
return [[FBSimulatorError describeFormat:@"Simulator must be booted to upload photos, is %@", simulator.device.stateString] failBool:error];
|
||||
}
|
||||
|
@ -57,8 +55,7 @@
|
|||
return [self succeed];
|
||||
}
|
||||
|
||||
FBSimulator *simulator = self.simulator;
|
||||
return [self interact:^ BOOL (NSError **error, id _) {
|
||||
return [self interactWithBootedSimulator:^ BOOL (NSError **error, FBSimulator *simulator) {
|
||||
NSError *innerError = nil;
|
||||
BOOL success = [simulator.simDeviceWrapper addVideos:videoPaths error:&innerError];
|
||||
if (!success) {
|
||||
|
|
|
@ -15,16 +15,23 @@
|
|||
|
||||
/**
|
||||
Tiles the Simulator according to the 'tilingStrategy'.
|
||||
|
||||
@param tilingStrategy the Tiling Strategy to use.
|
||||
@return the reciever, for chaining.
|
||||
*/
|
||||
- (instancetype)tileSimulator:(id<FBSimulatorWindowTilingStrategy>)tilingStrategy;
|
||||
|
||||
/**
|
||||
Tiles the Simulator according to the occlusion other Simulators.
|
||||
|
||||
@return the reciever, for chaining.
|
||||
*/
|
||||
- (instancetype)tileSimulator;
|
||||
|
||||
/**
|
||||
Records Video of the Simulator, until the Session is terminated.
|
||||
|
||||
@return the reciever, for chaining.
|
||||
*/
|
||||
- (instancetype)recordVideo;
|
||||
|
||||
|
|
|
@ -24,9 +24,7 @@
|
|||
{
|
||||
NSParameterAssert(tilingStrategy);
|
||||
|
||||
FBSimulator *simulator = self.simulator;
|
||||
|
||||
return [self interact:^ BOOL (NSError **error, id _) {
|
||||
return [self interactWithBootedSimulator:^ BOOL (NSError **error, FBSimulator *simulator) {
|
||||
FBSimulatorWindowTiler *tiler = [FBSimulatorWindowTiler withSimulator:simulator strategy:tilingStrategy];
|
||||
NSError *innerError = nil;
|
||||
if (CGRectIsNull([tiler placeInForegroundWithError:&innerError])) {
|
||||
|
@ -43,9 +41,7 @@
|
|||
|
||||
- (instancetype)recordVideo
|
||||
{
|
||||
FBSimulator *simulator = self.simulator;
|
||||
|
||||
return [self interact:^ BOOL (NSError **error, id _) {
|
||||
return [self interactWithBootedSimulator:^ BOOL (NSError **error, FBSimulator *simulator) {
|
||||
FBSimulatorVideoRecorder *recorder = [FBSimulatorVideoRecorder forSimulator:simulator logger:nil];
|
||||
NSString *path = [simulator pathForStorage:@"video" ofExtension:@"mp4"];
|
||||
|
||||
|
|
|
@ -18,7 +18,7 @@
|
|||
@class FBSimulatorSessionLifecycle;
|
||||
|
||||
/**
|
||||
Pre-session interactions used pre-launch of a Simulator
|
||||
Interactions for FBSimulator Instances.
|
||||
*/
|
||||
@interface FBSimulatorInteraction : FBInteraction
|
||||
|
||||
|
@ -29,19 +29,4 @@
|
|||
*/
|
||||
+ (instancetype)withSimulator:(FBSimulator *)simulator;
|
||||
|
||||
/**
|
||||
Boots the Simulator.
|
||||
*/
|
||||
- (instancetype)bootSimulator;
|
||||
|
||||
/**
|
||||
Shuts the Simulator down.
|
||||
*/
|
||||
- (instancetype)shutdownSimulator;
|
||||
|
||||
/**
|
||||
Opens the provided URL on the Device
|
||||
*/
|
||||
- (instancetype)openURL:(NSURL *)url;
|
||||
|
||||
@end
|
||||
|
|
|
@ -41,125 +41,44 @@
|
|||
return interaction;
|
||||
}
|
||||
|
||||
- (instancetype)bootSimulator
|
||||
#pragma mark Private
|
||||
|
||||
- (instancetype)interactWithSimulator:(BOOL (^)(NSError **error, FBSimulator *simulator))block
|
||||
{
|
||||
FBSimulator *simulator = self.simulator;
|
||||
return [self interact:^ BOOL (NSError **error, FBSimulatorInteraction *interaction) {
|
||||
return block(error, interaction.simulator);
|
||||
}];
|
||||
}
|
||||
|
||||
return [self interact:^ BOOL (NSError **error, id _) {
|
||||
// Construct the Arguments
|
||||
NSMutableArray *arguments = [NSMutableArray arrayWithArray:@[
|
||||
@"--args",
|
||||
@"-CurrentDeviceUDID", simulator.udid,
|
||||
@"-ConnectHardwareKeyboard", @"0"
|
||||
]];
|
||||
NSArray *scaleArguments = [simulator.configuration lastScaleCommandLineArgumentsWithError:nil];
|
||||
if (scaleArguments) {
|
||||
[arguments addObjectsFromArray:scaleArguments];
|
||||
}
|
||||
if (simulator.pool.configuration.deviceSetPath) {
|
||||
if (!FBSimulatorControlGlobalConfiguration.supportsCustomDeviceSets) {
|
||||
return [[[FBSimulatorError describe:@"Cannot use custom Device Set on current platform"] inSimulator:simulator] failBool:error];
|
||||
}
|
||||
[arguments addObjectsFromArray:@[@"-DeviceSetPath", simulator.pool.configuration.deviceSetPath]];
|
||||
}
|
||||
|
||||
// Construct and start the task.
|
||||
id<FBTask> task = [[[[[FBTaskExecutor.sharedInstance
|
||||
withLaunchPath:FBSimulatorApplication.simulatorApplication.binary.path]
|
||||
withArguments:[arguments copy]]
|
||||
withEnvironmentAdditions:@{ FBSimulatorControlSimulatorLaunchEnvironmentSimulatorUDID : simulator.udid }]
|
||||
build]
|
||||
startAsynchronously];
|
||||
|
||||
// Expect no immediate error.
|
||||
if (task.error) {
|
||||
return [[[[FBSimulatorError describe:@"Failed to Launch Simulator Process"] causedBy:task.error] inSimulator:simulator] failBool:error];
|
||||
}
|
||||
|
||||
// Expect the state of the simulator to be updated.
|
||||
BOOL didBoot = [simulator waitOnState:FBSimulatorStateBooted];
|
||||
if (!didBoot) {
|
||||
return [[[FBSimulatorError describeFormat:@"Timed out waiting for device to be Booted, got %@", simulator.device.stateString] inSimulator:simulator] failBool:error];
|
||||
}
|
||||
|
||||
// Expect the launch info for the process to exist.
|
||||
FBSimulatorLaunchInfo *launchInfo = [FBSimulatorLaunchInfo fromSimDevice:simulator.device query:simulator.processQuery];
|
||||
if (!launchInfo) {
|
||||
return [[[FBSimulatorError describe:@"Could not obtain process info for booted simulator process"] inSimulator:simulator] failBool:error];
|
||||
}
|
||||
|
||||
// Waitng for all required processes to start
|
||||
NSSet *requiredProcessNames = simulator.requiredProcessNamesToVerifyBooted;
|
||||
BOOL didStartAllRequiredProcesses = [NSRunLoop.mainRunLoop spinRunLoopWithTimeout:FBSimulatorControlGlobalConfiguration.slowTimeout untilTrue:^ BOOL {
|
||||
NSSet *runningProcessNames = [NSSet setWithArray:[launchInfo.launchedProcesses valueForKey:@"processName"]];
|
||||
return [requiredProcessNames isSubsetOfSet:runningProcessNames];
|
||||
}];
|
||||
if (!didStartAllRequiredProcesses) {
|
||||
- (instancetype)interactWithSimulatorAtState:(FBSimulatorState)state block:(BOOL (^)(NSError **error, FBSimulator *simulator))block
|
||||
{
|
||||
return [self interactWithSimulator:^ BOOL (NSError **error, FBSimulator *simulator) {
|
||||
if (simulator.state != state) {
|
||||
return [[[FBSimulatorError
|
||||
describeFormat:@"Timed out waiting for all required processes %@ to start", [FBCollectionDescriptions oneLineDescriptionFromArray:requiredProcessNames.allObjects]]
|
||||
describeFormat:@"Expected Simulator %@ to be %@, but it was '%@'", simulator.udid, simulator.stateString, [FBSimulator stateStringFromSimulatorState:simulator.state]]
|
||||
inSimulator:simulator]
|
||||
failBool:error];
|
||||
}
|
||||
|
||||
// Pass on the success to the event sink.
|
||||
[simulator.eventSink didStartWithLaunchInfo:launchInfo];
|
||||
[simulator.eventSink terminationHandleAvailable:task];
|
||||
|
||||
return YES;
|
||||
return block(error, simulator);
|
||||
}];
|
||||
}
|
||||
|
||||
- (instancetype)shutdownSimulator
|
||||
- (instancetype)interactWithShutdownSimulator:(BOOL (^)(NSError **error, FBSimulator *simulator))block
|
||||
{
|
||||
FBSimulator *simulator = self.simulator;
|
||||
|
||||
return [self interact:^ BOOL (NSError **error, id _) {
|
||||
FBSimulatorLaunchInfo *launchInfo = simulator.launchInfo;
|
||||
if (!launchInfo) {
|
||||
return [[[FBSimulatorError describe:@"Could not shutdown simulator as there is no available launch info"] inSimulator:simulator] failBool:error];
|
||||
}
|
||||
|
||||
FBSimulatorTerminationStrategy *terminationStrategy = [FBSimulatorTerminationStrategy
|
||||
withConfiguration:simulator.pool.configuration
|
||||
processQuery:simulator.processQuery
|
||||
logger:simulator.pool.logger];
|
||||
|
||||
NSError *innerError = nil;
|
||||
if (![terminationStrategy killSimulators:@[simulator] withError:&innerError]) {
|
||||
return [[[[FBSimulatorError describe:@"Could not shutdown simulator"] inSimulator:simulator] causedBy:innerError] failBool:error];
|
||||
}
|
||||
[simulator.eventSink didTerminate:YES];
|
||||
|
||||
return YES;
|
||||
}];
|
||||
return [self interactWithSimulatorAtState:FBSimulatorStateShutdown block:block];
|
||||
}
|
||||
|
||||
- (instancetype)openURL:(NSURL *)url
|
||||
- (instancetype)interactWithBootedSimulator:(BOOL (^)(NSError **error, FBSimulator *simulator))block
|
||||
{
|
||||
NSParameterAssert(url);
|
||||
|
||||
FBSimulator *simulator = self.simulator;
|
||||
|
||||
return [self interact:^ BOOL (NSError **error, id _) {
|
||||
NSError *innerError = nil;
|
||||
if (![simulator.device openURL:url error:&innerError]) {
|
||||
NSString *description = [NSString stringWithFormat:@"Failed to open URL %@ on simulator %@", url, simulator];
|
||||
return [FBSimulatorError failBoolWithError:innerError description:description errorOut:error];
|
||||
}
|
||||
return YES;
|
||||
}];
|
||||
return [self interactWithSimulatorAtState:FBSimulatorStateBooted block:block];
|
||||
}
|
||||
|
||||
#pragma mark Private
|
||||
|
||||
- (instancetype)binary:(FBSimulatorBinary *)binary interact:(BOOL (^)(FBProcessInfo *process, NSError **error))block
|
||||
- (instancetype)binary:(FBSimulatorBinary *)binary interact:(BOOL (^)(NSError **error, FBSimulator *simulator, FBProcessInfo *process))block
|
||||
{
|
||||
NSParameterAssert(binary);
|
||||
NSParameterAssert(block);
|
||||
|
||||
FBSimulator *simulator = self.simulator;
|
||||
|
||||
return [self interact:^ BOOL (NSError **error, id _) {
|
||||
return [self interactWithBootedSimulator:^ BOOL (NSError **error, FBSimulator *simulator) {
|
||||
FBProcessInfo *processInfo = [[[[simulator
|
||||
launchInfo]
|
||||
launchedProcesses]
|
||||
|
@ -169,7 +88,7 @@
|
|||
if (!processInfo) {
|
||||
return [[[FBSimulatorError describeFormat:@"Could not find an active process for %@", binary] inSimulator:simulator] failBool:error];
|
||||
}
|
||||
return block(processInfo, error);
|
||||
return block(error, simulator, processInfo);
|
||||
}];
|
||||
}
|
||||
|
||||
|
|
Загрузка…
Ссылка в новой задаче