├── README.md
└── XCTestWD-master
├── .gitignore
├── .jshintignore
├── .jshintrc
├── .npmignore
├── .travis.yml
├── CONTRIBUTING.md
├── Cartfile
├── LICENSE
├── Makefile
├── README.md
├── XCTestWD
├── XCTestWD-Info.plist
├── XCTestWD.xcodeproj
│ ├── project.pbxproj
│ └── xcshareddata
│ │ └── xcschemes
│ │ ├── XCTestWD.xcscheme
│ │ ├── XCTestWDAggregation.xcscheme
│ │ ├── XCTestWDUITests.xcscheme
│ │ └── XCTestWDUnitTest.xcscheme
├── XCTestWD
│ ├── Info.plist
│ ├── PrivateHeaders
│ │ ├── CDStructures.h
│ │ ├── Macaca
│ │ │ ├── NSPredicate+XCTestWD.h
│ │ │ ├── NSPredicate+XCTestWD.m
│ │ │ ├── XCTestWDApplication.h
│ │ │ ├── XCTestWDApplication.m
│ │ │ ├── XCTestWDImplementationFailureHoldingProxy.h
│ │ │ └── XCTestWDImplementationFailureHoldingProxy.m
│ │ ├── XCAXClient_iOS.h
│ │ ├── XCDebugLogDelegate-Protocol.h
│ │ ├── XCElementSnapshot.h
│ │ ├── XCRuntimeUtils.h
│ │ ├── XCRuntimeUtils.m
│ │ ├── XCTRunnerDaemonSession.h
│ │ ├── XCTestCase.h
│ │ ├── XCTestDaemonsProxy.h
│ │ ├── XCTestDaemonsProxy.m
│ │ ├── XCTestDriver.h
│ │ ├── XCTestDriverInterface-Protocol.h
│ │ ├── XCTestManager_IDEInterface-Protocol.h
│ │ ├── XCTestManager_ManagerInterface-Protocol.h
│ │ ├── XCTestManager_TestsInterface-Protocol.h
│ │ ├── XCTestPrivateSymbols.h
│ │ ├── XCTestPrivateSymbols.m
│ │ ├── XCUIApplication.h
│ │ ├── XCUICoordinate.h
│ │ ├── XCUIElement.h
│ │ ├── XCUIElementQuery.h
│ │ └── _XCTestCaseImplementation.h
│ ├── Server
│ │ ├── Controllers
│ │ │ ├── Monkey.swift
│ │ │ ├── MonkeyUIAutomation.swift
│ │ │ ├── MonkeyXCTest.swift
│ │ │ ├── MonkeyXCTestPrivate.swift
│ │ │ ├── Random.swift
│ │ │ ├── XCTestWDActionsController.swift
│ │ │ ├── XCTestWDAlertController.swift
│ │ │ ├── XCTestWDContextController.swift
│ │ │ ├── XCTestWDElementController.swift
│ │ │ ├── XCTestWDExecuteController.swift
│ │ │ ├── XCTestWDKeysController.swift
│ │ │ ├── XCTestWDMonkeyController.swift
│ │ │ ├── XCTestWDScreenshotController.swift
│ │ │ ├── XCTestWDSessionController.swift
│ │ │ ├── XCTestWDSourceController.swift
│ │ │ ├── XCTestWDStatusController.swift
│ │ │ ├── XCTestWDTimeoutController.swift
│ │ │ ├── XCTestWDTitleController.swift
│ │ │ ├── XCTestWDUrlController.swift
│ │ │ └── XCTestWDWindowController.swift
│ │ ├── Modules
│ │ │ ├── Extensions
│ │ │ │ ├── XCTestWDFindElementUtils.swift
│ │ │ │ ├── XCTestWDMathUtils.swift
│ │ │ │ └── XCTestWDXPath.swift
│ │ │ ├── Utils
│ │ │ │ ├── XCTestWDAccessibility.swift
│ │ │ │ └── XCTestWDApplicationTree.swift
│ │ │ ├── XCTestWDAlert.swift
│ │ │ ├── XCTestWDErrors.swift
│ │ │ ├── XCTestWDReponse.swift
│ │ │ ├── XCTestWDSession.swift
│ │ │ ├── XCTestWDStatus.swift
│ │ │ └── XCUIElementTypeTransformer.swift
│ │ ├── XCTestWDController.swift
│ │ ├── XCTestWDDispatch.swift
│ │ ├── XCTestWDFailureProofTestCase.swift
│ │ ├── XCTestWDMonkey.swift
│ │ └── XCTestWDServer.swift
│ └── XCTestWD.h
├── XCTestWDUITests
│ ├── Info.plist
│ └── XCTestWDRunner.swift
├── XCTestWDUnitTest
│ ├── ControllerTests
│ │ ├── XCTestWDScreenShotControllerTest.swift
│ │ ├── XCTestWDSourceControllerTests.swift
│ │ ├── XCTestWDTitleControllerTests.swift
│ │ ├── XCTestWDUrlControllerTests.swift
│ │ └── XCTestWDWindowControllerTests.swift
│ ├── Info.plist
│ ├── XCTestWDSessionTest.swift
│ └── XCTestWDUnitTestBase.swift
├── curlTests.sh
└── libxml2
│ └── libxml2-fuzi.h
├── index.html
├── index.js
├── lib
├── helper.js
├── logger.js
├── proxy.js
├── xctest-client.js
└── xctestwd.js
├── package.json
├── scripts
├── aggregate.sh
├── install.js
└── integration-testing.sh
└── test
├── mocha.opts
└── xctest.test.js
/README.md:
--------------------------------------------------------------------------------
1 | # FastMonkey
2 |
3 | > A Swift implementation of Monkey TEST(Non-Stub) for iOS that runs on Simulator/iOS devices.
4 |
5 | 1.0.0.1002 支持
6 | 1. 非插桩monkey点击事件
7 | 2. app后台或退出检测
8 | 3. 基于控件点击事件
9 | 4. 自定义业务序列事件
10 |
11 |
12 | - homepage : https://testerhome.com/topics/9524
13 |
14 | ## 1. Requirements
15 |
16 | - XCode version 8.3.0 and above.
17 | - iOS version 9.0 and above.
18 |
19 | ## 2. Starting
20 |
21 | FastMonkey can be either started with XCode IDE or via simple xcodebuild command line.
22 |
23 | ### 2.1. Using Xcode
24 |
25 | Download the project and open the XCode project, checkout the scheme `XCTestWDUITests` and run the test case `XCTextWDRunner`
26 |
27 | ### 2.2. Using XcodeBuild
28 |
29 | Open the terminal, go to the directory where contains `XCTestWD.xcodeproj` file and execute the following command:
30 |
31 | ``` bash
32 | #
33 | #Change the port number to override the default port
34 | #
35 | $ xcodebuild -project XCTestWD.xcodeproj \
36 | -scheme XCTestWDUITests \
37 | -destination 'platform=iOS Simulator,name=iPhone 6' \
38 | XCTESTWD_PORT=8001 \
39 | clean test
40 | ```
41 |
42 | To execute Monkey for iOS device, run the following command:
43 |
44 | ``` bash
45 | #
46 | #Change the port number to override the default port
47 | #Specify the device name
48 | #
49 | $ iproxy 8001 8001
50 |
51 | $ xcodebuild -project XCTestWD.xcodeproj -scheme XCTestWDUITests -destination 'platform=iOS,name=(your device name)' XCTESTWD_PORT=8001 clean test
52 | #
53 | # Now server is started and listening in 8001
54 | # To start Monkey run:
55 |
56 | $curl -X POST -H "Content-Type:application/json" -d "{\"desiredCapabilities\":{\"deviceName\":\"xxxx\",\"platformName\":\"iOS\", \"bundleId\":\"com.PandaTV.Live-iPhone\",\"autoAcceptAlerts\":\"false\"}}" http://127.0.0.1:8001/wd/hub/monkey
57 |
58 |
59 | ```
60 |
--------------------------------------------------------------------------------
/XCTestWD-master/.gitignore:
--------------------------------------------------------------------------------
1 | # Xcode
2 | .DS_Store
3 | build/
4 | *.pbxuser
5 | !default.pbxuser
6 | *.mode1v3
7 | !default.mode1v3
8 | *.mode2v3
9 | !default.mode2v3
10 | *.perspectivev3
11 | !default.perspectivev3
12 | *.xcworkspace
13 | !default.xcworkspace
14 | xcuserdata
15 | profile
16 | *.moved-aside
17 | DerivedData
18 | .idea/
19 | # Normal
20 | .project
21 | .settings
22 | node_modules/
23 | logs/
24 | Carthage/
25 | Cartfile.resolved
26 | UserInterfaceState.xcuserstate
27 | .*.sw[a-z]
28 | .sw?
29 | *.un~
30 | .DS_Store
31 | node_modules
32 | npm-debug.log
33 | .idea/*
34 | Thumbs.db
35 | coverage/
36 | .project
37 | logs/
38 | *.un~
39 |
--------------------------------------------------------------------------------
/XCTestWD-master/.jshintignore:
--------------------------------------------------------------------------------
1 | .git/
2 | node_modules/
3 | coverage/
4 | build/
5 | assets/
6 | dist/
7 | XCTestWD/
8 |
--------------------------------------------------------------------------------
/XCTestWD-master/.jshintrc:
--------------------------------------------------------------------------------
1 | {
2 | "indent": 2,
3 | "latedef": "nofunc",
4 | "newcap": true,
5 | "curly": true,
6 | "eqeqeq": true,
7 | "eqnull": true,
8 | "strict": true,
9 | "undef": true,
10 | "unused": true,
11 | "laxcomma": false,
12 | "asi": false,
13 | "boss": false,
14 | "expr": true,
15 | "sub": true,
16 | "quotmark": "single",
17 | "loopfunc": false,
18 | "lastsemic": true,
19 | "funcscope": false,
20 | "esnext": true,
21 | "noyield": true,
22 | "browser": true,
23 | "nonstandard": true,
24 | "devel": true,
25 | "node": true,
26 | "mocha": true,
27 | "validthis": true,
28 | "globals": {
29 | "define": false
30 | }
31 | }
32 |
--------------------------------------------------------------------------------
/XCTestWD-master/.npmignore:
--------------------------------------------------------------------------------
1 | # Xcode
2 | .DS_Store
3 | *.pbxuser
4 | !default.pbxuser
5 | *.mode1v3
6 | !default.mode1v3
7 | *.mode2v3
8 | !default.mode2v3
9 | *.perspectivev3
10 | !default.perspectivev3
11 | *.xcworkspace
12 | !default.xcworkspace
13 | xcuserdata
14 | profile
15 | *.moved-aside
16 | DerivedData
17 | .idea/
18 | # Normal
19 | .project
20 | .settings
21 | node_modules/
22 | logs/
23 | Cartfile.resolved
24 | UserInterfaceState.xcuserstate
25 | Cartfile
26 | XCTestWD/build
27 | *.un~
28 | coverage.html
29 | lib-cov/
30 | node_modules
31 | .travis.yml
32 | .drone.yml
33 | examples/
34 | Makefile
35 | .jshintrc
36 | .jshintignore
37 | coverage/
38 | logs/
39 |
--------------------------------------------------------------------------------
/XCTestWD-master/.travis.yml:
--------------------------------------------------------------------------------
1 | language: objective-c
2 | osx_image: xcode8.3
3 | script:
4 | - make build
5 |
--------------------------------------------------------------------------------
/XCTestWD-master/CONTRIBUTING.md:
--------------------------------------------------------------------------------
1 | # Contributing to XCTestWD
2 |
3 | We love pull requests from everyone.
4 |
5 | ## Link Global To Local
6 |
7 | ```bash
8 | $ cd path/to/macaca-ios
9 | $ npm link path/to/XCTestWD
10 | # now project XCTestWD is linked to macaca-ios
11 | ```
12 |
13 | ## Run with XCode
14 |
15 | ```bash
16 | $ open ./XCTestWD/XCTestWD.xcodeproj
17 | # run test(command + u) in XCTestWDUITests schema
18 | # ./XCTestWD/curlTests.sh is some useful restful testing scripts
19 | ```
20 |
--------------------------------------------------------------------------------
/XCTestWD-master/Cartfile:
--------------------------------------------------------------------------------
1 | github "httpswift/swifter" == 1.4.3
2 | github "SwiftyJSON/SwiftyJSON"
3 | github "cezheng/Fuzi" ~> 2.1.0
4 | github "tadija/AEXML" == 4.2.2
5 | github "CocoaLumberjack/CocoaLumberjack"
6 | github "Quick/Nimble"
7 |
--------------------------------------------------------------------------------
/XCTestWD-master/LICENSE:
--------------------------------------------------------------------------------
1 | MIT LICENSE
2 |
3 | Copyright (c) 2017 Alibaba Group Holding Limited and other contributors.
4 |
5 | Permission is hereby granted, free of charge, to any person obtaining
6 | a copy of this software and associated documentation files (the
7 | "Software"), to deal in the Software without restriction, including
8 | without limitation the rights to use, copy, modify, merge, publish,
9 | distribute, sublicense, and/or sell copies of the Software, and to
10 | permit persons to whom the Software is furnished to do so, subject to
11 | the following conditions:
12 |
13 | The above copyright notice and this permission notice shall be
14 | included in all copies or substantial portions of the Software.
15 |
16 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
17 | EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
18 | MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
19 | NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
20 | LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
21 | OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
22 | WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
23 |
--------------------------------------------------------------------------------
/XCTestWD-master/Makefile:
--------------------------------------------------------------------------------
1 | install:
2 | carthage update --platform iOS --verbose
3 | .PHONY: coverage
4 |
--------------------------------------------------------------------------------
/XCTestWD-master/README.md:
--------------------------------------------------------------------------------
1 | # XCTestWD
2 |
3 | [![NPM version][npm-image]][npm-url]
4 | [![node version][node-image]][node-url]
5 | [![npm download][download-image]][download-url]
6 | [](https://circleci.com/gh/macacajs/XCTestWD)
7 |
8 | [npm-image]: https://img.shields.io/npm/v/xctestwd.svg?style=flat-square
9 | [npm-url]: https://npmjs.org/package/xctestwd
10 | [node-image]: https://img.shields.io/badge/node.js-%3E=_8-green.svg?style=flat-square
11 | [node-url]: http://nodejs.org/download/
12 | [download-image]: https://img.shields.io/npm/dm/xctestwd.svg?style=flat-square
13 | [download-url]: https://npmjs.org/package/xctestwd
14 |
15 | > Swift implementation of WebDriver server for iOS that runs on Simulator/iOS devices.
16 |
17 | ## 1. Requirements
18 |
19 | - XCode version 9.0 and above.
20 | - iOS version 11.0 and above. (there is significant change on XCUITest interfaces and system private headers, hence we decide to support newest OS version only)
21 |
22 | ## 2. Starting XCTestWD
23 |
24 | XCTestWD can be either started with XCode IDE or via simple xcodebuild command line. By default, the webdriver agent occupies port `8001`. You can override the default port in XCode by searching `XCTESTWD_PORT` under project build settings. Alternatively, it can also be overrided when you execute command line method as specified in `2.2. Using Xcodebuild`
25 |
26 | ### 2.1. Using Xcode
27 |
28 | Download the project and open the XCode project, checkout the scheme `XCTestWDUITests` and run the test case `XCTextWDRunner`
29 |
30 | ### 2.2. Using XcodeBuild
31 |
32 | Open the terminal, go to the directory where contains `XCTestWD.xcodeproj` file and execute the following command:
33 |
34 | ```bash
35 | #
36 | # Change the port number to override the default port
37 | #
38 | $ xcodebuild -project XCTestWD.xcodeproj \
39 | -scheme XCTestWDUITests \
40 | -destination 'platform=iOS Simulator,name=iPhone 6' \
41 | XCTESTWD_PORT=8001 \
42 | clean test
43 | ```
44 |
45 | To execute for iOS device, run the following command:
46 |
47 | ```bash
48 | #
49 | # Change the port number to override the default port
50 | # Specify the device name
51 | #
52 | $ xcodebuild -project XCTestWD.xcodeproj \
53 | -scheme XCTestWDUITests \
54 | -destination 'platform=iOS,name=(your device name)' \
55 | XCTESTWD_PORT=8001 \
56 | clean test
57 | ```
58 | **Note:** For versions above wxtestwd 2.0.0, please install ideviceinstaller for supporting real device testing
59 |
60 |
61 | ## 3. Element Types
62 |
63 | In the current protocol, element strings for each `XCUIElementType` are generated based on the existing mapping in [reference/xctest/xcuielementtype](https://developer.apple.com/reference/xctest/xcuielementtype)
64 |
65 |
66 | ## 4. Common Issues
67 |
68 | ### 4.1 Socket hangup error
69 |
70 | Socket Hangup Error happens in the following two scenarios:
71 | - **Case 1**
72 | Issue:
73 | When you have some existing XCTestWD instances running and creating new ones.
74 | Solution:
75 | verify whether ideviceinstaller and xcrun is properly working on your device and simulator.
76 | Hint:
77 | https://github.com/libimobiledevice/ideviceinstaller/issues/48
78 |
79 | - **Case 2**
80 | Issue:
81 | When you have started the XCTestWD instance properly but fails in middle of a testing process.
82 | Solution:
83 | See the Macaca Service log to checkout which command leads the error. With detailed and comprehensive log information, please submit an issue to us.
84 | Optional:
85 | If you cannot get anything from macaca server log, open the XCTestWD in your node installation path and attatch for debugging on process 'XCTRunnerUITests-Runner'.
86 |
87 | **Additional Info**
88 | `The project path is at`
89 | ```
90 | cd "$(npm root -g)/macaca-ios/node_modules/xctestwd"
91 | ```
92 |
93 | `Set up the linebreak for swift error and exceptions:`
94 |
95 |
96 | `Run your command regularly, once the driver has been initialized, attach the process:`
97 |
98 |
99 | ### 4.2 Swift modules fails to compile
100 |
101 | Check carthage installation
102 |
103 | ### 4.3 Debug info
104 |
105 | Now XCTestWD supports gathering debug log into log files which is stored in "Your-App-Sandbox-Root"/Documents/Logs dir. For real devices, you can connect to itunes and choose backup for `XCTestWDUITests` and get the debug log. For iOS simulators, the log file is in your computer's simulator app directory like:
106 |
107 | ```
108 | "/Users/${user-name}/Library/Developer/CoreSimulator/Devices \
109 | /${device-id}/data/Containers/Data/Application/${app-id}/Documents/Logs"
110 | ```
111 |
112 | You can use `xcrun simctl list` to get the id of the booted device.
113 |
114 |
115 |
116 | ## Contributors
117 |
118 | |[
SamuelZhaoY](https://github.com/SamuelZhaoY)
|[
xudafeng](https://github.com/xudafeng)
|[
holy-lousie](https://github.com/holy-lousie)
|[
adudurant](https://github.com/adudurant)
|[
Chan-Chun](https://github.com/Chan-Chun)
|[
gurisxie](https://github.com/gurisxie)
119 | | :---: | :---: | :---: | :---: | :---: | :---: |
120 | |[
fengguochao](https://github.com/fengguochao)
|[
butterflyingdog](https://github.com/butterflyingdog)
121 |
122 | This project follows the git-contributor [spec](https://github.com/xudafeng/git-contributor), auto upated at `Mon Aug 13 2018 13:47:20 GMT+0800`.
123 |
124 |
125 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD-Info.plist:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | CFBundleDevelopmentRegion
6 | $(DEVELOPMENT_LANGUAGE)
7 | CFBundleExecutable
8 | $(EXECUTABLE_NAME)
9 | CFBundleIdentifier
10 | $(PRODUCT_BUNDLE_IDENTIFIER)
11 | CFBundleInfoDictionaryVersion
12 | 6.0
13 | CFBundleName
14 | $(PRODUCT_NAME)
15 | CFBundlePackageType
16 | FMWK
17 | CFBundleShortVersionString
18 | 1.0
19 | CFBundleVersion
20 | $(CURRENT_PROJECT_VERSION)
21 | NSPrincipalClass
22 |
23 |
24 |
25 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD.xcodeproj/xcshareddata/xcschemes/XCTestWD.xcscheme:
--------------------------------------------------------------------------------
1 |
2 |
5 |
8 |
9 |
15 |
21 |
22 |
23 |
24 |
25 |
31 |
32 |
33 |
34 |
35 |
36 |
47 |
48 |
54 |
55 |
56 |
57 |
58 |
59 |
65 |
66 |
72 |
73 |
74 |
75 |
77 |
78 |
81 |
82 |
83 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD.xcodeproj/xcshareddata/xcschemes/XCTestWDAggregation.xcscheme:
--------------------------------------------------------------------------------
1 |
2 |
5 |
8 |
9 |
15 |
21 |
22 |
23 |
24 |
25 |
31 |
32 |
33 |
34 |
35 |
36 |
47 |
48 |
54 |
55 |
56 |
57 |
58 |
59 |
65 |
66 |
72 |
73 |
74 |
75 |
77 |
78 |
81 |
82 |
83 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD.xcodeproj/xcshareddata/xcschemes/XCTestWDUITests.xcscheme:
--------------------------------------------------------------------------------
1 |
2 |
5 |
8 |
9 |
15 |
21 |
22 |
23 |
24 |
25 |
30 |
31 |
33 |
39 |
40 |
41 |
42 |
43 |
49 |
50 |
51 |
52 |
53 |
54 |
64 |
65 |
71 |
72 |
73 |
74 |
75 |
76 |
82 |
83 |
89 |
90 |
91 |
92 |
94 |
95 |
98 |
99 |
100 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD.xcodeproj/xcshareddata/xcschemes/XCTestWDUnitTest.xcscheme:
--------------------------------------------------------------------------------
1 |
2 |
5 |
8 |
9 |
15 |
16 |
18 |
24 |
25 |
26 |
27 |
28 |
29 |
30 |
41 |
42 |
43 |
44 |
50 |
51 |
53 |
54 |
57 |
58 |
59 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/Info.plist:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | CFBundleDevelopmentRegion
6 | $(DEVELOPMENT_LANGUAGE)
7 | CFBundleExecutable
8 | $(EXECUTABLE_NAME)
9 | CFBundleIdentifier
10 | $(PRODUCT_BUNDLE_IDENTIFIER)
11 | CFBundleInfoDictionaryVersion
12 | 6.0
13 | CFBundleName
14 | $(PRODUCT_NAME)
15 | CFBundlePackageType
16 | FMWK
17 | CFBundleShortVersionString
18 | 1.0
19 | CFBundleVersion
20 | $(CURRENT_PROJECT_VERSION)
21 | NSPrincipalClass
22 |
23 |
24 |
25 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/PrivateHeaders/CDStructures.h:
--------------------------------------------------------------------------------
1 | //
2 | // Generated by class-dump 3.5 (64 bit).
3 | //
4 | // class-dump is Copyright (C) 1997-1998, 2000-2001, 2004-2013 by Steve Nygard.
5 | //
6 |
7 | #pragma mark Blocks
8 |
9 | typedef void (^CDUnknownBlockType)(void); // return type and parameters are unknown
10 |
11 | typedef struct {
12 | unsigned int _field1;
13 | unsigned int _field2;
14 | unsigned int _field3;
15 | unsigned int _field4;
16 | unsigned int _field5;
17 | unsigned int _field6;
18 | unsigned int _field7;
19 | } CDStruct_a561fd19;
20 |
21 | typedef struct {
22 | unsigned short _field1;
23 | unsigned short _field2;
24 | unsigned short _field3[1];
25 | } CDStruct_27a325c0;
26 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/PrivateHeaders/Macaca/NSPredicate+XCTestWD.h:
--------------------------------------------------------------------------------
1 | //
2 | // NSPredicate+XCTestWD.h
3 | // XCTestWD
4 | //
5 | // Created by SamuelZhaoY on 18/8/18.
6 | // Copyright © 2018 XCTestWD. All rights reserved.
7 | //
8 |
9 | #import
10 |
11 | @interface NSPredicate (XCTestWD)
12 |
13 | // utility method for providing xctestwd predicates
14 | + (instancetype)xctestWDPredicateWithFormat:(NSString *)predicateFormat;
15 |
16 | + (instancetype)xctestWDformatSearchPredicate:(NSPredicate *)input;
17 |
18 | @end
19 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/PrivateHeaders/Macaca/NSPredicate+XCTestWD.m:
--------------------------------------------------------------------------------
1 | //
2 | // NSPredicate+XCTestWD.m
3 | // XCTestWD
4 | //
5 | // Created by SamuelZhaoY on 18/8/18.
6 | // Copyright © 2018 XCTestWD. All rights reserved.
7 | //
8 |
9 | #import "NSPredicate+XCTestWD.h"
10 |
11 | @implementation NSPredicate(XCTestWD)
12 |
13 | + (instancetype)xctestWDPredicateWithFormat:(NSString *)predicateFormat
14 | {
15 | NSPredicate *predicate = [NSPredicate predicateWithFormat:predicateFormat arguments:nil];
16 | NSPredicate *hackPredicate = [NSPredicate predicateWithFormat:self.forceResolvePredicateString];
17 | return [NSCompoundPredicate andPredicateWithSubpredicates:@[predicate, hackPredicate]];
18 | }
19 |
20 | + (NSString *)forceResolvePredicateString
21 | {
22 | return @"1 == 1 or identifier == 0 or frame == 0 or value == 0 or title == 0 or label == 0 or elementType == 0 or enabled == 0 or placeholderValue == 0";
23 | }
24 |
25 | + (instancetype)xctestWDPredicateWithPredicate:(NSPredicate *)original comparisonModifier:(NSPredicate *(^)(NSComparisonPredicate *))comparisonModifier
26 | {
27 | if ([original isKindOfClass:NSCompoundPredicate.class]) {
28 | NSCompoundPredicate *compPred = (NSCompoundPredicate *)original;
29 | NSMutableArray *predicates = [NSMutableArray array];
30 | for (NSPredicate *predicate in [compPred subpredicates]) {
31 | if ([predicate.predicateFormat.lowercaseString isEqualToString:NSPredicate.forceResolvePredicateString.lowercaseString]) {
32 | // Do not translete this predicate
33 | [predicates addObject:predicate];
34 | continue;
35 | }
36 | NSPredicate *newPredicate = [self.class xctestWDPredicateWithPredicate:predicate comparisonModifier:comparisonModifier];
37 | if (nil != newPredicate) {
38 | [predicates addObject:newPredicate];
39 | }
40 | }
41 | return [[NSCompoundPredicate alloc] initWithType:compPred.compoundPredicateType
42 | subpredicates:predicates];
43 | }
44 | if ([original isKindOfClass:NSComparisonPredicate.class]) {
45 | return comparisonModifier((NSComparisonPredicate *)original);
46 | }
47 | return original;
48 | }
49 |
50 | + (instancetype)xctestWDformatSearchPredicate:(NSPredicate *)input
51 | {
52 | return [self.class xctestWDPredicateWithPredicate:input comparisonModifier:^NSPredicate *(NSComparisonPredicate *cp) {
53 | return [NSComparisonPredicate predicateWithLeftExpression:[cp leftExpression]
54 | rightExpression:[cp rightExpression]
55 | modifier:cp.comparisonPredicateModifier
56 | type:cp.predicateOperatorType
57 | options:cp.options];
58 | }];
59 | }
60 |
61 | @end
62 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/PrivateHeaders/Macaca/XCTestWDApplication.h:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestWDApplication.h
3 | // XCTestWDUITests
4 | //
5 | // Created by zhaoy on 24/9/17.
6 | // Copyright © 2017 XCTestWD. All rights reserved.
7 | //
8 |
9 | #import
10 | #import "XCUIApplication.h"
11 |
12 | @interface XCTestWDApplication : NSObject
13 |
14 | + (XCUIApplication*)activeApplication;
15 |
16 | + (XCUIApplication*)createByPID:(pid_t)pid;
17 |
18 | @end
19 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/PrivateHeaders/Macaca/XCTestWDApplication.m:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestWDApplication.m
3 | // XCTestWDUITests
4 | //
5 | // Created by zhaoy on 24/9/17.
6 | // Copyright © 2017 XCTestWD. All rights reserved.
7 | //
8 |
9 | #import "XCTestWDApplication.h"
10 | #import "XCUIApplication.h"
11 | #import "XCAXClient_iOS.h"
12 |
13 | @implementation XCTestWDApplication
14 |
15 | + (XCUIApplication*)activeApplication
16 | {
17 | id activeApplicationElement = ((NSArray*)[[XCAXClient_iOS sharedClient] activeApplications]).lastObject;
18 |
19 | if (!activeApplicationElement) {
20 | activeApplicationElement = ((XCAXClient_iOS*)[XCAXClient_iOS sharedClient]).systemApplication;
21 | }
22 |
23 | XCUIApplication* application = [XCTestWDApplication createByPID:[[activeApplicationElement valueForKey:@"processIdentifier"] intValue]];
24 |
25 | if (application.state != XCUIApplicationStateRunningForeground) {
26 | application = [[XCUIApplication alloc] initPrivateWithPath:nil bundleID:@"com.apple.springboard"];
27 | }
28 |
29 | [application query];
30 | return application;
31 | }
32 |
33 | + (XCUIApplication*)createByPID:(pid_t)pid
34 | {
35 | if ([XCUIApplication respondsToSelector:@selector(appWithPID:)]) {
36 | return [XCUIApplication appWithPID:pid];
37 | }
38 |
39 | return [XCUIApplication applicationWithPID:pid];
40 | }
41 |
42 | @end
43 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/PrivateHeaders/Macaca/XCTestWDImplementationFailureHoldingProxy.h:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestWDImplementationFailureHoldingProxy.h
3 | // XCTestWD
4 | //
5 | // Created by SamuelZhaoY on 3/10/18.
6 | // Copyright © 2018 XCTestWD. All rights reserved.
7 | //
8 |
9 | #import
10 |
11 | NS_ASSUME_NONNULL_BEGIN
12 |
13 | @class _XCTestCaseImplementation;
14 | /**
15 | Class that can be used to proxy existing _XCTestCaseImplementation and
16 | prevent currently running test from being terminated on any XCTest failure
17 | */
18 | @interface XCTestWDImplementationFailureHoldingProxy : NSObject
19 |
20 | /**
21 | Constructor for given existing _XCTestCaseImplementation instance
22 | */
23 | + (_XCTestCaseImplementation *)proxyWithXCTestCaseImplementation:(_XCTestCaseImplementation *)internalImplementation;
24 |
25 | @end
26 |
27 | NS_ASSUME_NONNULL_END
28 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/PrivateHeaders/Macaca/XCTestWDImplementationFailureHoldingProxy.m:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestWDImplementationFailureHoldingProxy.m
3 | // XCTestWD
4 | //
5 | // Created by SamuelZhaoY on 3/10/18.
6 | // Copyright © 2018 XCTestWD. All rights reserved.
7 | //
8 |
9 | #import "XCTestWDImplementationFailureHoldingProxy.h"
10 | #import "_XCTestCaseImplementation.h"
11 |
12 | @interface XCTestWDImplementationFailureHoldingProxy()
13 |
14 | @property (nonatomic, strong) _XCTestCaseImplementation *internalImplementation;
15 |
16 | @end
17 |
18 | @implementation XCTestWDImplementationFailureHoldingProxy
19 |
20 | + (_XCTestCaseImplementation *)proxyWithXCTestCaseImplementation:(_XCTestCaseImplementation *)internalImplementation
21 | {
22 | XCTestWDImplementationFailureHoldingProxy *proxy = [super alloc];
23 | proxy.internalImplementation = internalImplementation;
24 | return (_XCTestCaseImplementation *)proxy;
25 | }
26 |
27 | - (id)forwardingTargetForSelector:(SEL)aSelector
28 | {
29 | return self.internalImplementation;
30 | }
31 |
32 | // This will prevent test from quiting on app crash or any other test failure
33 | - (BOOL)shouldHaltWhenReceivesControl
34 | {
35 | return NO;
36 | }
37 |
38 | @end
39 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/PrivateHeaders/XCAXClient_iOS.h:
--------------------------------------------------------------------------------
1 | //
2 | // Generated by class-dump 3.5 (64 bit).
3 | //
4 | // class-dump is Copyright (C) 1997-1998, 2000-2001, 2004-2013 by Steve Nygard.
5 | //
6 |
7 | #import "CDStructures.h"
8 | #import
9 |
10 | @class NSMutableDictionary;
11 | @class XCAccessibilityElement;
12 |
13 | @interface XCAXClient_iOS : NSObject
14 | {
15 | NSMutableDictionary *_userTestingNotificationHandlers;
16 | NSMutableDictionary *_cacheAccessibilityLoadedValuesForPIDs;
17 | unsigned long long *_alertNotificationCounter;
18 | }
19 | @property double AXTimeout;
20 |
21 | + (id)sharedClient;
22 | - (BOOL)_setAXTimeout:(double)arg1 error:(id *)arg2;
23 | - (NSData *)screenshotData;
24 | - (BOOL)performAction:(int)arg1 onElement:(id)arg2 value:(id)arg3 error:(id *)arg4;
25 | - (id)parameterizedAttributeForElement:(id)arg1 attribute:(id)arg2 parameter:(id)arg3;
26 | - (BOOL)setAttribute:(id)arg1 value:(id)arg2 element:(id)arg3 outError:(id *)arg4;
27 | - (id)attributesForElement:(id)arg1 attributes:(id)arg2;
28 | - (id)attributesForElementSnapshot:(id)arg1 attributeList:(id)arg2;
29 | - (id)snapshotForApplication:(id)arg1 attributeList:(id)arg2 parameters:(id)arg3;
30 | - (id)defaultParameters;
31 | - (id)defaultAttributes;
32 | - (void)notifyWhenViewControllerViewDidDisappearReply:(CDUnknownBlockType)arg1;
33 | - (void)notifyWhenViewControllerViewDidAppearReply:(CDUnknownBlockType)arg1;
34 | - (void)notifyWhenNoAnimationsAreActiveForApplication:(id)arg1 reply:(CDUnknownBlockType)arg2;
35 | - (void)notifyWhenEventLoopIsIdleForApplication:(id)arg1 reply:(CDUnknownBlockType)arg2;
36 | - (id)interruptingUIElementAffectingSnapshot:(id)arg1;
37 | - (void)handleAccessibilityNotification:(int)arg1 withPayload:(id)arg2;
38 | - (void)notifyOnNextOccurrenceOfUserTestingEvent:(id)arg1 handler:(CDUnknownBlockType)arg2;
39 | - (void)handleUserTestingNotification:(id)arg1;
40 | - (id)elementAtPoint:(CGPoint)arg1 error:(id *)arg2;
41 | - (BOOL)cachedAccessibilityLoadedValueForPID:(int)arg1;
42 | - (id)activeApplications;
43 | - (id)systemApplication;
44 | - (BOOL)enableFauxCollectionViewCells:(id *)arg1;
45 | - (BOOL)loadAccessibility:(id *)arg1;
46 | - (BOOL)_registerForAXNotification:(int)arg1 error:(id *)arg2;
47 | - (BOOL)_loadAccessibility:(id *)arg1;
48 | - (id)init;
49 |
50 | @end
51 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/PrivateHeaders/XCDebugLogDelegate-Protocol.h:
--------------------------------------------------------------------------------
1 | //
2 | // Generated by class-dump 3.5 (64 bit).
3 | //
4 | // class-dump is Copyright (C) 1997-1998, 2000-2001, 2004-2013 by Steve Nygard.
5 | //
6 |
7 | @class NSString;
8 |
9 | @protocol XCDebugLogDelegate
10 | - (void)logDebugMessage:(NSString *)arg1;
11 | @end
12 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/PrivateHeaders/XCElementSnapshot.h:
--------------------------------------------------------------------------------
1 | //
2 | // Generated by class-dump 3.5 (64 bit).
3 | //
4 | // class-dump is Copyright (C) 1997-1998, 2000-2001, 2004-2013 by Steve Nygard.
5 | //
6 |
7 | #import "CDStructures.h"
8 |
9 | #import
10 |
11 | @class NSArray, NSDictionary, NSString, XCAccessibilityElement, XCUIApplication;
12 |
13 | @interface XCElementSnapshot : NSObject
14 | {
15 | NSString *_identifier;
16 | id _value;
17 | NSString *_placeholderValue;
18 | BOOL _enabled;
19 | BOOL _selected;
20 | BOOL _isMainWindow;
21 | BOOL _hasKeyboardFocus;
22 | BOOL _hasFocus;
23 | XCUIApplication *_application;
24 | unsigned long long _generation;
25 | NSString *_title;
26 | NSString *_label;
27 | unsigned long long _elementType;
28 | long long _horizontalSizeClass;
29 | long long _verticalSizeClass;
30 | XCAccessibilityElement *_accessibilityElement;
31 | XCAccessibilityElement *_parentAccessibilityElement;
32 | XCElementSnapshot *_parent;
33 | NSArray *_children;
34 | unsigned long long _traits;
35 | NSArray *_userTestingAttributes;
36 | NSDictionary *_additionalAttributes;
37 | struct CGRect _frame;
38 | }
39 | @property BOOL hasFocus; // @synthesize hasFocus=_hasFocus;
40 | @property BOOL hasKeyboardFocus; // @synthesize hasKeyboardFocus=_hasKeyboardFocus;
41 | @property(copy) NSDictionary *additionalAttributes; // @synthesize additionalAttributes=_additionalAttributes;
42 | @property(copy) NSArray *userTestingAttributes; // @synthesize userTestingAttributes=_userTestingAttributes;
43 | @property unsigned long long traits; // @synthesize traits=_traits;
44 | @property BOOL isMainWindow; // @synthesize isMainWindow=_isMainWindow;
45 | @property(copy) NSArray *children; // @synthesize children=_children;
46 | @property XCElementSnapshot *parent; // @synthesize parent=_parent;
47 | @property(retain) XCAccessibilityElement *parentAccessibilityElement; // @synthesize parentAccessibilityElement=_parentAccessibilityElement;
48 | @property(retain) XCAccessibilityElement *accessibilityElement; // @synthesize accessibilityElement=_accessibilityElement;
49 | @property(readonly) NSArray *suggestedHitpoints;
50 | @property(readonly) struct CGRect visibleFrame;
51 | @property(readonly) XCElementSnapshot *scrollView;
52 | @property(readonly, copy) NSString *truncatedValueString;
53 | @property(readonly) long long depth;
54 | @property(readonly, copy) XCElementSnapshot *pathFromRoot;
55 | @property(readonly) BOOL isTopLevelTouchBarElement;
56 | @property(readonly) BOOL isTouchBarElement;
57 | @property(readonly, copy) NSString *sparseTreeDescription;
58 | @property(readonly, copy) NSString *compactDescription;
59 | @property(readonly, copy) NSString *pathDescription;
60 | @property(readonly) NSString *recursiveDescriptionIncludingAccessibilityElement;
61 | @property(readonly) NSString *recursiveDescription;
62 | @property(readonly, copy) NSArray *identifiers;
63 | @property(nonatomic) unsigned long long generation; // @synthesize generation=_generation;
64 | @property(nonatomic) XCUIApplication *application; // @synthesize application=_application;
65 | @property(readonly) struct CGPoint hitPointForScrolling;
66 | @property(readonly) struct CGPoint hitPoint;
67 |
68 | - (id)_uniquelyIdentifyingObjectiveCCode;
69 | - (id)_uniquelyIdentifyingSwiftCode;
70 | - (BOOL)_isAncestorOfElement:(id)arg1;
71 | - (BOOL)_isDescendantOfElement:(id)arg1;
72 | - (id)rootElement;
73 | - (BOOL)_frameFuzzyMatchesElement:(id)arg1;
74 | - (BOOL)_fuzzyMatchesElement:(id)arg1;
75 | - (BOOL)_matchesElement:(id)arg1;
76 | - (BOOL)matchesTreeWithRoot:(id)arg1;
77 | - (void)mergeTreeWithSnapshot:(id)arg1;
78 | - (id)_childMatchingElement:(id)arg1;
79 | - (NSArray *)_allDescendants;
80 | - (BOOL)hasDescendantMatchingFilter:(CDUnknownBlockType)arg1;
81 | - (NSArray *)descendantsByFilteringWithBlock:(BOOL(^)(XCElementSnapshot *snapshot))block;
82 | - (id)elementSnapshotMatchingAccessibilityElement:(id)arg1;
83 | - (void)enumerateDescendantsUsingBlock:(void(^)(XCElementSnapshot *snapshot))block;
84 | - (id)recursiveDescriptionWithIndent:(id)arg1 includeAccessibilityElement:(BOOL)arg2;
85 | - (id)init;
86 | - (struct CGPoint)hostingAndOrientationTransformedPoint:(struct CGPoint)arg1;
87 | - (struct CGPoint)_transformPoint:(struct CGPoint)arg1 windowContextID:(id)arg2 windowDisplayID:(id)arg3;
88 | - (id)hitTest:(struct CGPoint)arg1;
89 |
90 | @end
91 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/PrivateHeaders/XCRuntimeUtils.h:
--------------------------------------------------------------------------------
1 | /**
2 | * Copyright (c) 2015-present, Facebook, Inc.
3 | * All rights reserved.
4 | *
5 | * This source code is licensed under the BSD-style license found in the
6 | * LICENSE file in the root directory of this source tree. An additional grant
7 | * of patent rights can be found in the PATENTS file in the same directory.
8 | */
9 |
10 | #import
11 |
12 | NS_ASSUME_NONNULL_BEGIN
13 |
14 | /**
15 | Returns array of classes that conforms to given protocol
16 | */
17 | NSArray *FBClassesThatConformsToProtocol(Protocol *protocol);
18 |
19 | /**
20 | Method used to retrieve pointer for given symbol 'name' from given 'binary'
21 |
22 | @param binary path to binary we want to retrieve symbols pointer from
23 | @param name name of the symbol
24 | @return pointer to symbol
25 | */
26 | void *FBRetrieveSymbolFromBinary(const char *binary, const char *name);
27 |
28 | NS_ASSUME_NONNULL_END
29 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/PrivateHeaders/XCRuntimeUtils.m:
--------------------------------------------------------------------------------
1 | /**
2 | * Copyright (c) 2015-present, Facebook, Inc.
3 | * All rights reserved.
4 | *
5 | * This source code is licensed under the BSD-style license found in the
6 | * LICENSE file in the root directory of this source tree. An additional grant
7 | * of patent rights can be found in the PATENTS file in the same directory.
8 | */
9 |
10 | #import "XCRuntimeUtils.h"
11 | #import
12 | #include
13 | #import
14 |
15 | NSUInteger const ddLogLevel = DDLogLevelDebug;
16 |
17 | NSArray *FBClassesThatConformsToProtocol(Protocol *protocol)
18 | {
19 | Class *classes = NULL;
20 | NSMutableArray *collection = [NSMutableArray array];
21 | int numClasses = objc_getClassList(NULL, 0);
22 | if (numClasses == 0 ) {
23 | return @[];
24 | }
25 |
26 | classes = (__unsafe_unretained Class*)malloc(sizeof(Class) * numClasses);
27 | numClasses = objc_getClassList(classes, numClasses);
28 | for (int index = 0; index < numClasses; index++) {
29 | Class aClass = classes[index];
30 | if (class_conformsToProtocol(aClass, protocol)) {
31 | [collection addObject:aClass];
32 | }
33 | }
34 |
35 | free(classes);
36 | return collection.copy;
37 | }
38 |
39 | void *FBRetrieveSymbolFromBinary(const char *binary, const char *name)
40 | {
41 | void *handle = dlopen(binary, RTLD_LAZY);
42 | NSCAssert(handle, @"%s could not be opened", binary);
43 | void *pointer = dlsym(handle, name);
44 | NSCAssert(pointer, @"%s could not be located", name);
45 | return pointer;
46 | }
47 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/PrivateHeaders/XCTRunnerDaemonSession.h:
--------------------------------------------------------------------------------
1 | //
2 | // Generated by class-dump 3.5 (64 bit).
3 | //
4 | // class-dump is Copyright (C) 1997-1998, 2000-2001, 2004-2013 by Steve Nygard.
5 | //
6 |
7 | #import "XCTestManager_TestsInterface-Protocol.h"
8 | #import "CDStructures.h"
9 | #import
10 |
11 | @class NSMutableDictionary, NSXPCConnection;
12 | @protocol XCTUIApplicationMonitor, XCTAXClient;
13 |
14 | // iOS since 10.3
15 | @interface XCTRunnerDaemonSession : NSObject
16 | {
17 | NSObject *_queue;
18 | id _applicationMonitor;
19 | id _accessibilityClient;
20 | NSXPCConnection *_connection;
21 | unsigned long long _daemonProtocolVersion;
22 | NSMutableDictionary *_invalidationHandlers;
23 | }
24 | @property(retain) NSObject *queue; // @synthesize queue=_queue;
25 | @property id accessibilityClient; // @synthesize accessibilityClient=_accessibilityClient;
26 | @property id applicationMonitor; // @synthesize applicationMonitor=_applicationMonitor;
27 | @property(retain) NSMutableDictionary *invalidationHandlers; // @synthesize invalidationHandlers=_invalidationHandlers;
28 | @property(retain) NSXPCConnection *connection; // @synthesize connection=_connection;
29 | @property(readonly) BOOL useLegacyEventCoordinateTransformationPath;
30 | @property unsigned long long daemonProtocolVersion;
31 | @property(readonly) id daemonProxy;
32 |
33 | + (instancetype)sharedSession;
34 |
35 | - (void)injectVoiceRecognitionAudioInputPaths:(id)arg1 completion:(CDUnknownBlockType)arg2;
36 | - (void)injectAssistantRecognitionStrings:(id)arg1 completion:(CDUnknownBlockType)arg2;
37 | - (void)startSiriUIRequestWithAudioFileURL:(id)arg1 completion:(CDUnknownBlockType)arg2;
38 | - (void)startSiriUIRequestWithText:(id)arg1 completion:(CDUnknownBlockType)arg2;
39 | - (void)requestDTServiceHubConnectionWithReply:(CDUnknownBlockType)arg1;
40 | - (void)enableFauxCollectionViewCells:(CDUnknownBlockType)arg1;
41 | - (void)loadAccessibilityWithTimeout:(double)arg1 reply:(CDUnknownBlockType)arg2;
42 | - (void)setAXTimeout:(double)arg1 reply:(CDUnknownBlockType)arg2;
43 | - (void)requestScreenshotWithReply:(CDUnknownBlockType)arg1;
44 | - (void)sendString:(id)arg1 maximumFrequency:(unsigned long long)arg2 completion:(CDUnknownBlockType)arg3;
45 | - (void)updateDeviceOrientation:(long long)arg1 completion:(CDUnknownBlockType)arg2;
46 | - (void)performDeviceEvent:(id)arg1 completion:(CDUnknownBlockType)arg2;
47 | - (void)synthesizeEvent:(id)arg1 completion:(CDUnknownBlockType)arg2;
48 | - (void)requestElementAtPoint:(CGPoint)arg1 reply:(CDUnknownBlockType)arg2;
49 | - (void)fetchParameterizedAttributeForElement:(id)arg1 attribute:(id)arg2 parameter:(id)arg3 reply:(CDUnknownBlockType)arg4;
50 | - (void)setAttribute:(id)arg1 value:(id)arg2 element:(id)arg3 reply:(CDUnknownBlockType)arg4;
51 | - (void)fetchAttributesForElement:(id)arg1 attributes:(id)arg2 reply:(CDUnknownBlockType)arg3;
52 | - (void)snapshotForElement:(id)arg1 attributes:(id)arg2 parameters:(id)arg3 reply:(CDUnknownBlockType)arg4;
53 | - (void)terminateApplicationWithBundleID:(id)arg1 completion:(CDUnknownBlockType)arg2;
54 | - (void)performAccessibilityAction:(int)arg1 onElement:(id)arg2 value:(id)arg3 reply:(CDUnknownBlockType)arg4;
55 | - (void)unregisterForAccessibilityNotification:(int)arg1 registrationToken:(id)arg2 reply:(CDUnknownBlockType)arg3;
56 | - (void)registerForAccessibilityNotification:(int)arg1 reply:(CDUnknownBlockType)arg2;
57 | - (void)launchApplicationWithBundleID:(id)arg1 arguments:(id)arg2 environment:(id)arg3 completion:(CDUnknownBlockType)arg4;
58 | - (void)startMonitoringApplicationWithBundleID:(id)arg1;
59 | - (void)requestBackgroundAssertionForPID:(int)arg1 reply:(CDUnknownBlockType)arg2;
60 | - (void)requestAutomationSessionForTestTargetWithPID:(int)arg1 reply:(CDUnknownBlockType)arg2;
61 | - (void)requestIDEConnectionSocketForSessionIdentifier:(id)arg1 reply:(CDUnknownBlockType)arg2;
62 | - (void)_XCT_receivedAccessibilityNotification:(int)arg1 withPayload:(id)arg2;
63 | - (void)_XCT_applicationWithBundleID:(id)arg1 didUpdatePID:(int)arg2 andState:(unsigned long long)arg3;
64 | - (void)unregisterInvalidationHandlerWithToken:(id)arg1;
65 | - (id)registerInvalidationHandler:(CDUnknownBlockType)arg1;
66 | - (void)_reportInvalidation;
67 | - (id)initWithConnection:(id)arg1;
68 |
69 | @end
70 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/PrivateHeaders/XCTestCase.h:
--------------------------------------------------------------------------------
1 | //
2 | // Generated by class-dump 3.5 (64 bit).
3 | //
4 | // class-dump is Copyright (C) 1997-1998, 2000-2001, 2004-2013 by Steve Nygard.
5 | //
6 |
7 | #import
8 |
9 | #import "CDStructures.h"
10 |
11 | @class NSInvocation, XCTestCaseRun, XCTestContext, _XCTestCaseImplementation;
12 |
13 | @interface XCTestCase()
14 | {
15 | id _internalImplementation;
16 | }
17 | @property(retain) _XCTestCaseImplementation *internalImplementation; // @synthesize internalImplementation=_internalImplementation;
18 | @property(readonly) XCTestContext *testContext;
19 | @property(readonly) unsigned long long activityRecordStackDepth;
20 | @property(nonatomic) BOOL shouldHaltWhenReceivesControl;
21 | @property(retain) XCTestCaseRun *testCaseRun;
22 |
23 | + (id)_baselineDictionary;
24 | + (BOOL)_treatMissingBaselinesAsTestFailures;
25 | + (id)knownMemoryMetrics;
26 | + (id)measurementFormatter;
27 | + (BOOL)_reportPerformanceFailuresForLargeImprovements;
28 | + (BOOL)_enableSymbolication;
29 |
30 | + (BOOL)isInheritingTestCases;
31 | + (id)_testStartActvityDateFormatter;
32 | + (id)testCaseWithSelector:(SEL)arg1;
33 |
34 |
35 | + (void)tearDown;
36 | + (void)setUp;
37 | + (id)defaultTestSuite;
38 | + (id)allTestMethodInvocations;
39 | + (void)_allTestMethodInvocations:(id)arg1;
40 | + (id)testMethodInvocations;
41 | + (id)allSubclasses;
42 | - (void)startActivityWithTitle:(id)arg1 block:(CDUnknownBlockType)arg2;
43 | - (void)registerDefaultMetrics;
44 | - (id)baselinesDictionaryForTest;
45 | - (void)_logAndReportPerformanceMetrics:(id)arg1 perfMetricResultsForIDs:(id)arg2 withBaselinesForTest:(id)arg3;
46 | - (void)_logAndReportPerformanceMetrics:(id)arg1 perfMetricResultsForIDs:(id)arg2 withBaselinesForTest:(id)arg3 defaultBaselinesForPerfMetricID:(id)arg4;
47 | - (void)registerMetricID:(id)arg1 name:(id)arg2 unitString:(id)arg3;
48 | - (void)registerMetricID:(id)arg1 name:(id)arg2 unit:(id)arg3;
49 | - (void)reportMetric:(id)arg1 reportFailures:(BOOL)arg2;
50 | - (void)reportMeasurements:(id)arg1 forMetricID:(id)arg2 reportFailures:(BOOL)arg3;
51 | - (void)_recordValues:(id)arg1 forPerformanceMetricID:(id)arg2 name:(id)arg3 unitsOfMeasurement:(id)arg4 baselineName:(id)arg5 baselineAverage:(id)arg6 maxPercentRegression:(id)arg7 maxPercentRelativeStandardDeviation:(id)arg8 maxRegression:(id)arg9 maxStandardDeviation:(id)arg10 file:(id)arg11 line:(unsigned long long)arg12;
52 | - (id)_symbolicationRecordForTestCodeInAddressStack:(id)arg1;
53 | - (void)measureBlock:(CDUnknownBlockType)arg1;
54 | - (void)stopMeasuring;
55 | - (void)startMeasuring;
56 | - (BOOL)_isMeasuringMetrics;
57 | - (BOOL)_didStopMeasuring;
58 | - (BOOL)_didStartMeasuring;
59 | - (BOOL)_didMeasureMetrics;
60 | - (id)_perfMetricsForID;
61 | - (void)_logMemoryGraphDataFromFilePath:(id)arg1 withTitle:(id)arg2;
62 | - (void)_logMemoryGraphData:(id)arg1 withTitle:(id)arg2;
63 | - (unsigned long long)numberOfTestIterationsForTestWithSelector:(SEL)arg1;
64 | - (void)afterTestIteration:(unsigned long long)arg1 selector:(SEL)arg2;
65 | - (void)beforeTestIteration:(unsigned long long)arg1 selector:(SEL)arg2;
66 | - (void)tearDownTestWithSelector:(SEL)arg1;
67 | - (void)setUpTestWithSelector:(SEL)arg1;
68 | - (void)performTest:(id)arg1;
69 | - (void)invokeTest;
70 | - (Class)testRunClass;
71 | - (Class)_requiredTestRunBaseClass;
72 | - (void)_recordUnexpectedFailureWithDescription:(id)arg1 error:(id)arg2;
73 | - (void)_recordUnexpectedFailureWithDescription:(id)arg1 exception:(id)arg2;
74 | - (void)_enqueueFailureWithDescription:(NSString *)description inFile:(NSString *)filePath atLine:(NSUInteger)lineNumber expected:(BOOL)expected;
75 | - (void)_dequeueFailures;
76 | - (void)_interruptTest;
77 | - (BOOL)isEqual:(id)arg1;
78 | - (id)nameForLegacyLogging;
79 | - (id)name;
80 | - (id)languageAgnosticTestMethodName;
81 | - (unsigned long long)testCaseCount;
82 | - (id)initWithSelector:(SEL)arg1;
83 | - (id)init;
84 | - (void)waiter:(id)arg1 didFulfillInvertedExpectation:(id)arg2;
85 | - (void)waiter:(id)arg1 fulfillmentDidViolateOrderingConstraintsForExpectation:(id)arg2 requiredExpectation:(id)arg3;
86 | - (void)waiter:(id)arg1 didTimeoutWithUnfulfilledExpectations:(id)arg2;
87 | - (id)expectationForPredicate:(id)arg1 evaluatedWithObject:(id)arg2 handler:(CDUnknownBlockType)arg3;
88 | - (id)expectationForNotification:(id)arg1 object:(id)arg2 handler:(CDUnknownBlockType)arg3;
89 | - (id)keyValueObservingExpectationForObject:(id)arg1 keyPath:(id)arg2 handler:(CDUnknownBlockType)arg3;
90 | - (id)keyValueObservingExpectationForObject:(id)arg1 keyPath:(id)arg2 expectedValue:(id)arg3;
91 | - (void)_addExpectation:(id)arg1;
92 | - (void)waitForExpectations:(id)arg1 timeout:(double)arg2 enforceOrder:(BOOL)arg3;
93 | - (void)waitForExpectations:(id)arg1 timeout:(double)arg2;
94 | - (void)waitForExpectationsWithTimeout:(double)arg1 handler:(CDUnknownBlockType)arg2;
95 | - (void)_waitForExpectations:(id)arg1 timeout:(double)arg2 enforceOrder:(BOOL)arg3 handler:(CDUnknownBlockType)arg4;
96 | - (id)expectationWithDescription:(id)arg1;
97 | - (id)_expectationForDarwinNotification:(id)arg1;
98 | - (void)nestedWaiter:(id)arg1 wasInterruptedByTimedOutWaiter:(id)arg2;
99 |
100 | @end
101 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/PrivateHeaders/XCTestDaemonsProxy.h:
--------------------------------------------------------------------------------
1 |
2 | #import
3 |
4 | @protocol XCTestManager_ManagerInterface;
5 |
6 | /**
7 | Temporary class used to abstract interactions with TestManager daemon between Xcode 8.2.1 and Xcode 8.3-beta
8 | */
9 | @interface XCTestDaemonsProxy : NSObject
10 |
11 | + (id)testRunnerProxy;
12 |
13 | @end
14 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/PrivateHeaders/XCTestDaemonsProxy.m:
--------------------------------------------------------------------------------
1 |
2 | #import "XCTestDaemonsProxy.h"
3 | #import "XCTestDriver.h"
4 | #import "XCTRunnerDaemonSession.h"
5 | #import
6 |
7 | @implementation XCTestDaemonsProxy
8 |
9 | + (id)testRunnerProxy
10 | {
11 | static id proxy = nil;
12 | static dispatch_once_t onceToken;
13 | dispatch_once(&onceToken, ^{
14 | if ([[XCTestDriver sharedTestDriver] respondsToSelector:@selector(managerProxy)]) {
15 | proxy = [XCTestDriver sharedTestDriver].managerProxy;
16 | return;
17 | }
18 | Class runnerClass = objc_lookUpClass("XCTRunnerDaemonSession");
19 | proxy = ((XCTRunnerDaemonSession *)[runnerClass sharedSession]).daemonProxy;
20 | });
21 | NSAssert(proxy != NULL, @"Could not determin testRunnerProxy", proxy);
22 | return proxy;
23 | }
24 |
25 | @end
26 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/PrivateHeaders/XCTestDriver.h:
--------------------------------------------------------------------------------
1 | //
2 | // Generated by class-dump 3.5 (64 bit).
3 | //
4 | // class-dump is Copyright (C) 1997-1998, 2000-2001, 2004-2013 by Steve Nygard.
5 | //
6 |
7 | #import "CDStructures.h"
8 | #import "XCDebugLogDelegate-Protocol.h"
9 | #import "XCTestDriverInterface-Protocol.h"
10 | #import "XCTestManager_TestsInterface-Protocol.h"
11 | #import "XCTestManager_IDEInterface-Protocol.h"
12 | #import "XCTestManager_ManagerInterface-Protocol.h"
13 |
14 | @class DTXConnection, NSMutableArray, NSString, NSUUID, NSXPCConnection, XCTestConfiguration, XCTestSuite;
15 |
16 | @interface XCTestDriver : NSObject
17 | {
18 | XCTestConfiguration *_testConfiguration;
19 | NSObject *_queue;
20 | NSMutableArray *_debugMessageBuffer;
21 | int _debugMessageBufferOverflow;
22 | }
23 | @property int debugMessageBufferOverflow; // @synthesize debugMessageBufferOverflow=_debugMessageBufferOverflow;
24 | @property(retain) NSMutableArray *debugMessageBuffer; // @synthesize debugMessageBuffer=_debugMessageBuffer;
25 | @property(retain) NSObject *queue; // @synthesize queue=_queue;
26 | @property(readonly) XCTestConfiguration *testConfiguration; // @synthesize testConfiguration=_testConfiguration;
27 |
28 | + (instancetype)sharedTestDriver;
29 |
30 | - (void)runTestConfiguration:(id)arg1 completionHandler:(CDUnknownBlockType)arg2;
31 | - (void)runTestSuite:(id)arg1 completionHandler:(CDUnknownBlockType)arg2;
32 | - (void)reportStallOnMainThreadInTestCase:(id)arg1 method:(id)arg2 file:(id)arg3 line:(unsigned long long)arg4;
33 | - (BOOL)runTestsAndReturnError:(id *)arg1;
34 | - (id)_readyIDESession:(id *)arg1;
35 | - (int)_connectedSocketForIDESession:(id *)arg1;
36 | - (void)logDebugMessage:(id)arg1;
37 | - (id)initWithTestConfiguration:(id)arg1;
38 |
39 | // Removed with iOS 10.3
40 | @property(readonly) id managerProxy;
41 |
42 | @end
43 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/PrivateHeaders/XCTestDriverInterface-Protocol.h:
--------------------------------------------------------------------------------
1 | //
2 | // Generated by class-dump 3.5 (64 bit).
3 | //
4 | // class-dump is Copyright (C) 1997-1998, 2000-2001, 2004-2013 by Steve Nygard.
5 | //
6 |
7 | @class NSNumber;
8 |
9 | @protocol XCTestDriverInterface
10 | - (id)_IDE_processWithToken:(NSNumber *)arg1 exitedWithStatus:(NSNumber *)arg2;
11 | - (id)_IDE_stopTrackingProcessWithToken:(NSNumber *)arg1;
12 | - (id)_IDE_processWithBundleID:(NSString *)arg1 path:(NSString *)arg2 pid:(NSNumber *)arg3 crashedUnderSymbol:(NSString *)arg4;
13 | - (id)_IDE_startExecutingTestPlanWithProtocolVersion:(NSNumber *)arg1;
14 | @end
15 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/PrivateHeaders/XCTestManager_IDEInterface-Protocol.h:
--------------------------------------------------------------------------------
1 | //
2 | // Generated by class-dump 3.5 (64 bit).
3 | //
4 | // class-dump is Copyright (C) 1997-1998, 2000-2001, 2004-2013 by Steve Nygard.
5 | //
6 |
7 | @class NSArray, NSDictionary, NSNumber, NSString, XCAccessibilityElement, XCActivityRecord, XCElementSnapshot;
8 |
9 | @protocol XCTestManager_IDEInterface
10 | - (id)_XCT_handleCrashReportData:(NSData *)arg1 fromFileWithName:(NSString *)arg2;
11 | - (id)_XCT_nativeFocusItemDidChangeAtTime:(NSNumber *)arg1 parameterSnapshot:(XCElementSnapshot *)arg2 applicationSnapshot:(XCElementSnapshot *)arg3;
12 | - (id)_XCT_recordedEventNames:(NSArray *)arg1 timestamp:(NSNumber *)arg2 duration:(NSNumber *)arg3 startLocation:(NSDictionary *)arg4 startElementSnapshot:(XCElementSnapshot *)arg5 startApplicationSnapshot:(XCElementSnapshot *)arg6 endLocation:(NSDictionary *)arg7 endElementSnapshot:(XCElementSnapshot *)arg8 endApplicationSnapshot:(XCElementSnapshot *)arg9;
13 | - (id)_XCT_testCase:(NSString *)arg1 method:(NSString *)arg2 didFinishActivity:(XCActivityRecord *)arg3;
14 | - (id)_XCT_testCase:(NSString *)arg1 method:(NSString *)arg2 willStartActivity:(XCActivityRecord *)arg3;
15 | - (id)_XCT_recordedOrientationChange:(NSString *)arg1;
16 | - (id)_XCT_recordedFirstResponderChangedWithApplicationSnapshot:(XCElementSnapshot *)arg1;
17 | - (id)_XCT_exchangeCurrentProtocolVersion:(NSNumber *)arg1 minimumVersion:(NSNumber *)arg2;
18 | - (id)_XCT_recordedKeyEventsWithApplicationSnapshot:(XCElementSnapshot *)arg1 characters:(NSString *)arg2 charactersIgnoringModifiers:(NSString *)arg3 modifierFlags:(NSNumber *)arg4;
19 | - (id)_XCT_logDebugMessage:(NSString *)arg1;
20 | - (id)_XCT_logMessage:(NSString *)arg1;
21 | - (id)_XCT_testMethod:(NSString *)arg1 ofClass:(NSString *)arg2 didMeasureMetric:(NSDictionary *)arg3 file:(NSString *)arg4 line:(NSNumber *)arg5;
22 | - (id)_XCT_testCase:(NSString *)arg1 method:(NSString *)arg2 didStallOnMainThreadInFile:(NSString *)arg3 line:(NSNumber *)arg4;
23 | - (id)_XCT_testCaseDidFinishForTestClass:(NSString *)arg1 method:(NSString *)arg2 withStatus:(NSString *)arg3 duration:(NSNumber *)arg4;
24 | - (id)_XCT_testCaseDidFailForTestClass:(NSString *)arg1 method:(NSString *)arg2 withMessage:(NSString *)arg3 file:(NSString *)arg4 line:(NSNumber *)arg5;
25 | - (id)_XCT_testCaseDidStartForTestClass:(NSString *)arg1 method:(NSString *)arg2;
26 | - (id)_XCT_testSuite:(NSString *)arg1 didFinishAt:(NSString *)arg2 runCount:(NSNumber *)arg3 withFailures:(NSNumber *)arg4 unexpected:(NSNumber *)arg5 testDuration:(NSNumber *)arg6 totalDuration:(NSNumber *)arg7;
27 | - (id)_XCT_testSuite:(NSString *)arg1 didStartAt:(NSString *)arg2;
28 | - (id)_XCT_initializationForUITestingDidFailWithError:(NSError *)arg1;
29 | - (id)_XCT_didBeginInitializingForUITesting;
30 | - (id)_XCT_didFinishExecutingTestPlan;
31 | - (id)_XCT_didBeginExecutingTestPlan;
32 | - (id)_XCT_testBundleReadyWithProtocolVersion:(NSNumber *)arg1 minimumVersion:(NSNumber *)arg2;
33 | - (id)_XCT_getProgressForLaunch:(id)arg1;
34 | - (id)_XCT_terminateProcess:(id)arg1;
35 | - (id)_XCT_launchProcessWithPath:(NSString *)arg1 bundleID:(NSString *)arg2 arguments:(NSArray *)arg3 environmentVariables:(NSDictionary *)arg4;
36 | @end
37 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/PrivateHeaders/XCTestManager_ManagerInterface-Protocol.h:
--------------------------------------------------------------------------------
1 | //
2 | // Generated by class-dump 3.5 (64 bit).
3 | //
4 | // class-dump is Copyright (C) 1997-1998, 2000-2001, 2004-2013 by Steve Nygard.
5 | //
6 |
7 | #import
8 |
9 | @class NSArray, NSDictionary, NSNumber, NSString, NSUUID, XCAccessibilityElement, XCDeviceEvent, XCSynthesizedEventRecord, XCTouchGesture, NSXPCListenerEndpoint;
10 |
11 | @protocol XCTestManager_ManagerInterface
12 | - (void)_XCT_loadAccessibilityWithTimeout:(double)arg1 reply:(void (^)(BOOL, NSError *))arg2;
13 | - (void)_XCT_injectVoiceRecognitionAudioInputPaths:(NSArray *)arg1 completion:(void (^)(BOOL, NSError *))arg2;
14 | - (void)_XCT_injectAssistantRecognitionStrings:(NSArray *)arg1 completion:(void (^)(BOOL, NSError *))arg2;
15 | - (void)_XCT_startSiriUIRequestWithAudioFileURL:(NSURL *)arg1 completion:(void (^)(BOOL, NSError *))arg2;
16 | - (void)_XCT_startSiriUIRequestWithText:(NSString *)arg1 completion:(void (^)(BOOL, NSError *))arg2;
17 | - (void)_XCT_requestDTServiceHubConnectionWithReply:(void (^)(NSXPCListenerEndpoint *, NSError *))arg1;
18 | - (void)_XCT_enableFauxCollectionViewCells:(void (^)(BOOL, NSError *))arg1;
19 | - (void)_XCT_setAXTimeout:(double)arg1 reply:(void (^)(int))arg2;
20 | - (void)_XCT_requestScreenshotWithReply:(void (^)(NSData *, NSError *))arg1;
21 | - (void)_XCT_sendString:(NSString *)arg1 maximumFrequency:(NSUInteger)arg2 completion:(void (^)(NSError *))arg3;
22 | - (void)_XCT_updateDeviceOrientation:(long long)arg1 completion:(void (^)(NSError *))arg2;
23 | - (void)_XCT_performDeviceEvent:(XCDeviceEvent *)arg1 completion:(void (^)(NSError *))arg2;
24 | - (void)_XCT_synthesizeEvent:(XCSynthesizedEventRecord *)arg1 completion:(void (^)(NSError *))arg2;
25 | - (void)_XCT_requestElementAtPoint:(CGPoint)arg1 reply:(void (^)(XCAccessibilityElement *, NSError *))arg2;
26 | - (void)_XCT_fetchParameterizedAttributeForElement:(XCAccessibilityElement *)arg1 attributes:(NSNumber *)arg2 parameter:(id)arg3 reply:(void (^)(id, NSError *))arg4;
27 | - (void)_XCT_setAttribute:(NSNumber *)arg1 value:(id)arg2 element:(XCAccessibilityElement *)arg3 reply:(void (^)(BOOL, NSError *))arg4;
28 | - (void)_XCT_fetchAttributesForElement:(XCAccessibilityElement *)arg1 attributes:(NSArray *)arg2 reply:(void (^)(NSDictionary *, NSError *))arg3;
29 | - (void)_XCT_snapshotForElement:(XCAccessibilityElement *)arg1 attributes:(NSArray *)arg2 parameters:(NSDictionary *)arg3 reply:(void (^)(XCElementSnapshot *, NSError *))arg4;
30 | - (void)_XCT_terminateApplicationWithBundleID:(NSString *)arg1 completion:(void (^)(NSError *))arg2;
31 | - (void)_XCT_performAccessibilityAction:(int)arg1 onElement:(XCAccessibilityElement *)arg2 withValue:(id)arg3 reply:(void (^)(NSError *))arg4;
32 | - (void)_XCT_unregisterForAccessibilityNotification:(int)arg1 withRegistrationToken:(NSNumber *)arg2 reply:(void (^)(NSError *))arg3;
33 | - (void)_XCT_registerForAccessibilityNotification:(int)arg1 reply:(void (^)(NSNumber *, NSError *))arg2;
34 | - (void)_XCT_launchApplicationWithBundleID:(NSString *)arg1 arguments:(NSArray *)arg2 environment:(NSDictionary *)arg3 completion:(void (^)(NSError *))arg4;
35 | - (void)_XCT_startMonitoringApplicationWithBundleID:(NSString *)arg1;
36 | - (void)_XCT_requestBackgroundAssertionForPID:(int)arg1 reply:(void (^)(BOOL))arg2;
37 | - (void)_XCT_requestBackgroundAssertionWithReply:(void (^)(void))arg1;
38 | - (void)_XCT_registerTarget;
39 | - (void)_XCT_requestEndpointForTestTargetWithPID:(int)arg1 preferredBackendPath:(NSString *)arg2 reply:(void (^)(NSXPCListenerEndpoint *, NSError *))arg3;
40 | - (void)_XCT_requestSocketForSessionIdentifier:(NSUUID *)arg1 reply:(void (^)(NSFileHandle *))arg2;
41 | - (void)_XCT_exchangeProtocolVersion:(unsigned long long)arg1 reply:(void (^)(unsigned long long))arg2;
42 | @end
43 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/PrivateHeaders/XCTestManager_TestsInterface-Protocol.h:
--------------------------------------------------------------------------------
1 | //
2 | // Generated by class-dump 3.5 (64 bit).
3 | //
4 | // class-dump is Copyright (C) 1997-1998, 2000-2001, 2004-2013 by Steve Nygard.
5 | //
6 |
7 | @class NSData, NSString;
8 |
9 | @protocol XCTestManager_TestsInterface
10 | - (void)_XCT_receivedAccessibilityNotification:(int)arg1 withPayload:(NSData *)arg2;
11 | - (void)_XCT_applicationWithBundleID:(NSString *)arg1 didUpdatePID:(int)arg2 andState:(unsigned long long)arg3;
12 | @end
13 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/PrivateHeaders/XCTestPrivateSymbols.h:
--------------------------------------------------------------------------------
1 | /**
2 | * Copyright (c) 2015-present, Facebook, Inc.
3 | * All rights reserved.
4 | *
5 | * This source code is licensed under the BSD-style license found in the
6 | * LICENSE file in the root directory of this source tree. An additional grant
7 | * of patent rights can be found in the PATENTS file in the same directory.
8 | */
9 |
10 | #import
11 |
12 | @protocol XCDebugLogDelegate;
13 |
14 | /*! Accessibility identifier for is visible attribute */
15 | extern NSNumber *XCAXAIsVisibleAttribute;
16 |
17 | /*! Accessibility identifier for is accessible attribute */
18 | extern NSNumber *XCAXAIsElementAttribute;
19 |
20 | /*! Getter for XCTest logger */
21 | extern id (*XCDebugLogger)(void);
22 |
23 | /*! Setter for XCTest logger */
24 | extern void (*XCSetDebugLogger)(id );
25 |
26 | /**
27 | Method used to retrieve pointer for given symbol 'name' from given 'binary'
28 |
29 | @param name name of the symbol
30 | @return pointer to symbol
31 | */
32 | void *RetrieveXCTestSymbol(const char *name);
33 |
34 | /*! Static constructor that will retrieve XCTest private symbols */
35 | __attribute__((constructor)) void LoadXCTestSymbols(void);
36 |
37 | int portNumber(void);
38 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/PrivateHeaders/XCTestPrivateSymbols.m:
--------------------------------------------------------------------------------
1 | /**
2 | * Copyright (c) 2015-present, Facebook, Inc.
3 | * All rights reserved.
4 | *
5 | * This source code is licensed under the BSD-style license found in the
6 | * LICENSE file in the root directory of this source tree. An additional grant
7 | * of patent rights can be found in the PATENTS file in the same directory.
8 | */
9 |
10 | #import "XCTestPrivateSymbols.h"
11 |
12 | #import "XCRuntimeUtils.h"
13 |
14 | NSNumber *XCAXAIsVisibleAttribute;
15 | NSNumber *XCAXAIsElementAttribute;
16 |
17 | void (*XCSetDebugLogger)(id );
18 | id (*XCDebugLogger)(void);
19 |
20 | __attribute__((constructor)) void LoadXCTestSymbols(void)
21 | {
22 | NSString *XC_kAXXCAttributeIsVisible = *(NSString*__autoreleasing*)RetrieveXCTestSymbol("XC_kAXXCAttributeIsVisible");
23 | NSString *XC_kAXXCAttributeIsElement = *(NSString*__autoreleasing*)RetrieveXCTestSymbol("XC_kAXXCAttributeIsElement");
24 |
25 | NSArray *(*XCAXAccessibilityAttributesForStringAttributes)(NSArray *list) =
26 | (NSArray *(*)(NSArray *))RetrieveXCTestSymbol("XCAXAccessibilityAttributesForStringAttributes");
27 |
28 | XCSetDebugLogger = (void (*)(id ))RetrieveXCTestSymbol("XCSetDebugLogger");
29 | XCDebugLogger = (id(*)(void))RetrieveXCTestSymbol("XCDebugLogger");
30 |
31 | NSArray *accessibilityAttributes = XCAXAccessibilityAttributesForStringAttributes(@[XC_kAXXCAttributeIsVisible, XC_kAXXCAttributeIsElement]);
32 | XCAXAIsVisibleAttribute = accessibilityAttributes[0];
33 | XCAXAIsElementAttribute = accessibilityAttributes[1];
34 |
35 | NSCAssert(XCAXAIsVisibleAttribute != nil , @"Failed to retrieve FB_XCAXAIsVisibleAttribute", XCAXAIsVisibleAttribute);
36 | NSCAssert(XCAXAIsElementAttribute != nil , @"Failed to retrieve FB_XCAXAIsElementAttribute", XCAXAIsElementAttribute);
37 | }
38 |
39 | void *RetrieveXCTestSymbol(const char *name)
40 | {
41 | Class XCTestClass = NSClassFromString(@"XCTestCase");
42 | NSCAssert(XCTestClass != nil, @"XCTest should be already linked", XCTestClass);
43 | NSString *XCTestBinary = [NSBundle bundleForClass:XCTestClass].executablePath;
44 | const char *binaryPath = XCTestBinary.UTF8String;
45 | NSCAssert(binaryPath != nil, @"XCTest binary path should not be nil", binaryPath);
46 | return FBRetrieveSymbolFromBinary(binaryPath, name);
47 | }
48 |
49 | int portNumber()
50 | {
51 | return XCTESTWD_PORT;
52 | }
53 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/PrivateHeaders/XCUIApplication.h:
--------------------------------------------------------------------------------
1 | //
2 | // Generated by class-dump 3.5 (64 bit).
3 | //
4 | // class-dump is Copyright (C) 1997-1998, 2000-2001, 2004-2013 by Steve Nygard.
5 | //
6 |
7 | #import
8 |
9 | @class NSArray, NSDictionary, NSString, XCAccessibilityElement, XCApplicationQuery, XCUIApplicationImpl;
10 |
11 | @interface XCUIApplication ()
12 | {
13 | BOOL _ancillary;
14 | BOOL _doesNotHandleUIInterruptions;
15 | BOOL _idleAnimationWaitEnabled;
16 | XCUIElement *_keyboard;
17 | NSArray *_launchArguments;
18 | NSDictionary *_launchEnvironment;
19 | XCUIApplicationImpl *_applicationImpl;
20 | XCApplicationQuery *_applicationQuery;
21 | unsigned long long _generation;
22 | }
23 | @property unsigned long long generation; // @synthesize generation=_generation;
24 | @property(retain) XCApplicationQuery *applicationQuery; // @synthesize applicationQuery=_applicationQuery;
25 | @property(retain) XCUIApplicationImpl *applicationImpl; // @synthesize applicationQuery=_applicationQuery;
26 | @property(readonly, copy) NSString *bundleID; // @synthesize bundleID=_bundleID;
27 | @property(readonly, copy) NSString *path; // @synthesize path=_path;
28 | @property BOOL ancillary; // @synthesize ancillary=_ancillary;
29 | @property(readonly) XCUIElement *keyboard; // @synthesize keyboard=_keyboard;
30 |
31 | @property(getter=isIdleAnimationWaitEnabled) BOOL idleAnimationWaitEnabled; // @synthesize idleAnimationWaitEnabled=_idleAnimationWaitEnabled;
32 | @property(nonatomic) BOOL doesNotHandleUIInterruptions; // @synthesize doesNotHandleUIInterruptions=_doesNotHandleUIInterruptions;
33 | @property(readonly) BOOL fauxCollectionViewCellsEnabled;
34 | @property(readonly, nonatomic) UIInterfaceOrientation interfaceOrientation; //TODO tvos
35 | @property(readonly, nonatomic) BOOL running;
36 | @property(nonatomic) pid_t processID; // @synthesize processID=_processID;
37 | @property XCUIApplicationState state; // @synthesize state=_state; // @synthesize state=_state;
38 | @property(readonly) XCAccessibilityElement *accessibilityElement;
39 |
40 | + (instancetype)appWithPID:(pid_t)processID;
41 | + (instancetype)applicationWithPID:(pid_t)processID;
42 |
43 | - (void)dismissKeyboard;
44 | - (BOOL)setFauxCollectionViewCellsEnabled:(BOOL)arg1 error:(id *)arg2;
45 | - (void)_waitForViewControllerViewDidDisappearWithTimeout:(double)arg1;
46 | - (void)_waitForQuiescence;
47 | - (void)terminate;
48 | - (void)_launchUsingXcode:(BOOL)arg1;
49 | - (void)launch;
50 | - (id)application;
51 | - (id)description;
52 | - (id)lastSnapshot;
53 | - (id)query;
54 | - (void)clearQuery;
55 | - (void)resolveHandleUIInterruption:(BOOL)arg1;
56 | - (id)initPrivateWithPath:(id)arg1 bundleID:(id)arg2;
57 | - (id)init;
58 |
59 | @end
60 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/PrivateHeaders/XCUICoordinate.h:
--------------------------------------------------------------------------------
1 | //
2 | // Generated by class-dump 3.5 (64 bit).
3 | //
4 | // class-dump is Copyright (C) 1997-1998, 2000-2001, 2004-2013 by Steve Nygard.
5 | //
6 |
7 | #import
8 | #import
9 |
10 | @class XCUIElement;
11 |
12 | #if !TARGET_OS_TV
13 | @interface XCUICoordinate ()
14 | {
15 | XCUIElement *_element;
16 | XCUICoordinate *_coordinate;
17 | CGVector _normalizedOffset;
18 | CGVector _pointsOffset;
19 | }
20 |
21 | @property(readonly) CGVector pointsOffset; // @synthesize pointsOffset=_pointsOffset;
22 | @property(readonly) CGVector normalizedOffset; // @synthesize normalizedOffset=_normalizedOffset;
23 | @property(readonly) XCUICoordinate *coordinate; // @synthesize coordinate=_coordinate;
24 | @property(readonly) XCUIElement *element; // @synthesize element=_element;
25 |
26 | - (id)initWithCoordinate:(id)arg1 pointsOffset:(CGVector)arg2;
27 | - (id)initWithElement:(id)arg1 normalizedOffset:(CGVector)arg2;
28 | - (id)init;
29 |
30 | - (void)pressForDuration:(double)arg1 thenDragToCoordinate:(id)arg2;
31 | - (void)pressForDuration:(double)arg1;
32 | - (void)doubleTap;
33 | - (void)tap;
34 |
35 | @end
36 | #endif
37 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/PrivateHeaders/XCUIElement.h:
--------------------------------------------------------------------------------
1 | //
2 | // Generated by class-dump 3.5 (64 bit).
3 | //
4 | // class-dump is Copyright (C) 1997-1998, 2000-2001, 2004-2013 by Steve Nygard.
5 | //
6 |
7 | #import
8 |
9 | @class NSString, XCElementSnapshot, XCUIApplication, XCUICoordinate, XCUIElementQuery;
10 |
11 | @interface XCUIElement ()
12 | {
13 | BOOL _safeQueryResolutionEnabled;
14 | XCUIElementQuery *_query;
15 | XCElementSnapshot *_lastSnapshot;
16 | }
17 |
18 | @property BOOL safeQueryResolutionEnabled; // @synthesize safeQueryResolutionEnabled=_safeQueryResolutionEnabled;
19 | @property(retain) XCElementSnapshot *lastSnapshot; // @synthesize lastSnapshot=_lastSnapshot;
20 | @property(readonly) XCUIElementQuery *query; // @synthesize query=_query;
21 | @property(readonly, nonatomic) UIInterfaceOrientation interfaceOrientation;
22 | @property(readonly, copy) XCUICoordinate *hitPointCoordinate;
23 | @property(readonly) BOOL isTopLevelTouchBarElement;
24 | @property(readonly) BOOL isTouchBarElement;
25 | @property(readonly) BOOL hasKeyboardFocus;
26 | @property(readonly, nonatomic) XCUIApplication *application;
27 |
28 | - (id)initWithElementQuery:(id)arg1;
29 |
30 | - (unsigned long long)traits;
31 | - (void)resolveHandleUIInterruption:(BOOL)arg1;
32 | - (void)resolve;
33 | - (BOOL)_waitForExistenceWithTimeout:(double)arg1;
34 | - (BOOL)evaluatePredicateForExpectation:(id)arg1 debugMessage:(id *)arg2;
35 | - (void)_swipe:(unsigned long long)arg1;
36 | - (void)_tapWithNumberOfTaps:(unsigned long long)arg1 numberOfTouches:(unsigned long long)arg2 activityTitle:(id)arg3;
37 | - (id)_highestNonWindowAncestorOfElement:(id)arg1 notSharedWithElement:(id)arg2;
38 | - (id)_pointsInFrame:(CGRect)arg1 numberOfTouches:(unsigned long long)arg2;
39 | - (CGPoint)_hitPointByAttemptingToScrollToVisibleSnapshot:(id)arg1;
40 | - (void)forcePress;
41 |
42 | @end
43 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/PrivateHeaders/XCUIElementQuery.h:
--------------------------------------------------------------------------------
1 | //
2 | // Generated by class-dump 3.5 (64 bit).
3 | //
4 | // class-dump is Copyright (C) 1997-1998, 2000-2001, 2004-2013 by Steve Nygard.
5 | //
6 |
7 | #import "CDStructures.h"
8 | #import
9 |
10 | @class NSArray, NSOrderedSet, NSString, XCUIApplication, XCUIElement;
11 |
12 | @interface XCUIElementQuery ()
13 | {
14 | BOOL _changesScope;
15 | NSString *_queryDescription;
16 | XCUIElementQuery *_inputQuery;
17 | CDUnknownBlockType _filter;
18 | unsigned long long _expressedType;
19 | NSArray *_expressedIdentifiers;
20 | NSOrderedSet *_lastInput;
21 | NSOrderedSet *_lastOutput;
22 | }
23 |
24 | @property(copy) NSOrderedSet *lastOutput; // @synthesize lastOutput=_lastOutput;
25 | @property(copy) NSOrderedSet *lastInput; // @synthesize lastInput=_lastInput;
26 | @property(copy) NSArray *expressedIdentifiers; // @synthesize expressedIdentifiers=_expressedIdentifiers;
27 | @property unsigned long long expressedType; // @synthesize expressedType=_expressedType;
28 | @property BOOL changesScope; // @synthesize changesScope=_changesScope;
29 | @property(readonly, copy) CDUnknownBlockType filter; // @synthesize filter=_filter;
30 | @property(readonly) XCUIElementQuery *inputQuery; // @synthesize inputQuery=_inputQuery;
31 | @property(readonly, copy) NSString *queryDescription; // @synthesize queryDescription=_queryDescription;
32 | @property(readonly, copy) NSString *elementDescription;
33 | @property(readonly) XCUIApplication *application;
34 |
35 | - (id)matchingSnapshotsWithError:(id *)arg1;
36 | - (id)matchingSnapshotsHandleUIInterruption:(BOOL)arg1 withError:(id *)arg2;
37 | - (id)_elementMatchingAccessibilityElementOfSnapshot:(id)arg1;
38 |
39 | - (id)_containingPredicate:(id)arg1 queryDescription:(id)arg2;
40 | - (id)_predicateWithType:(unsigned long long)arg1 identifier:(id)arg2;
41 | - (id)_queryWithPredicate:(id)arg1;
42 | - (id)sorted:(CDUnknownBlockType)arg1;
43 | - (id)descending:(unsigned long long)arg1;
44 | - (id)ascending:(unsigned long long)arg1;
45 | - (id)filter:(CDUnknownBlockType)arg1;
46 | - (id)_debugInfoWithIndent:(id *)arg1;
47 | - (id)_derivedExpressedIdentifiers;
48 | - (unsigned long long)_derivedExpressedType;
49 | - (id)initWithInputQuery:(id)arg1 queryDescription:(id)arg2 filter:(CDUnknownBlockType)arg3;
50 |
51 | @end
52 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/PrivateHeaders/_XCTestCaseImplementation.h:
--------------------------------------------------------------------------------
1 | //
2 | // Generated by class-dump 3.5 (64 bit).
3 | //
4 | // class-dump is Copyright (C) 1997-1998, 2000-2001, 2004-2013 by Steve Nygard.
5 | //
6 |
7 | @class NSArray, NSInvocation, NSMutableArray, NSMutableDictionary, NSMutableSet, NSString, XCTestCaseRun, XCTestContext, XCTestExpectationWaiter, XCTWaiter;
8 |
9 | #import "CDStructures.h"
10 |
11 | @interface _XCTestCaseImplementation : NSObject
12 | {
13 | NSInvocation *_invocation;
14 | XCTestCaseRun *_testCaseRun;
15 | BOOL _continueAfterFailure;
16 | NSMutableSet *_expectations;
17 | NSArray *_activePerformanceMetricIDs;
18 | NSMutableDictionary *_perfMetricsForID;
19 | unsigned long long _startWallClockTime;
20 | struct time_value _startUserTime;
21 | struct time_value _startSystemTime;
22 | unsigned long long _measuringIteration;
23 | BOOL _isMeasuringMetrics;
24 | BOOL _didMeasureMetrics;
25 | BOOL _didStartMeasuring;
26 | BOOL _didStopMeasuring;
27 | NSString *_filePathForUnexpectedFailure;
28 | unsigned long long _lineNumberForUnexpectedFailure;
29 | unsigned long long _callAddressForCurrentWait;
30 | NSArray *_callAddressesForLastCreatedExpectation;
31 | long long _runLoopNestingCount;
32 | XCTWaiter *_currentWaiter;
33 | NSMutableArray *_failureRecords;
34 | BOOL _shouldHaltWhenReceivesControl;
35 | BOOL _shouldIgnoreSubsequentFailures;
36 | NSMutableArray *_activityRecordStack;
37 | XCTestContext *_testContext;
38 | }
39 |
40 | @property(readonly) XCTestContext *testContext; // @synthesize testContext=_testContext;
41 | @property(retain, nonatomic) XCTWaiter *currentWaiter; // @synthesize currentWaiter=_currentWaiter;
42 | @property(retain, nonatomic) NSMutableArray *activityRecordStack; // @synthesize activityRecordStack=_activityRecordStack;
43 | @property BOOL shouldIgnoreSubsequentFailures; // @synthesize shouldIgnoreSubsequentFailures=_shouldIgnoreSubsequentFailures;
44 | @property BOOL shouldHaltWhenReceivesControl; // @synthesize shouldHaltWhenReceivesControl=_shouldHaltWhenReceivesControl;
45 | @property(retain, nonatomic) NSMutableArray *failureRecords; // @synthesize failureRecords=_failureRecords;
46 | @property long long runLoopNestingCount; // @synthesize runLoopNestingCount=_runLoopNestingCount;
47 | @property(copy) NSArray *callAddressesForLastCreatedExpectation; // @synthesize callAddressesForLastCreatedExpectation=_callAddressesForLastCreatedExpectation;
48 | @property unsigned long long callAddressForCurrentWait; // @synthesize callAddressForCurrentWait=_callAddressForCurrentWait;
49 | @property unsigned long long lineNumberForUnexpectedFailure; // @synthesize lineNumberForUnexpectedFailure=_lineNumberForUnexpectedFailure;
50 | @property(copy) NSString *filePathForUnexpectedFailure; // @synthesize filePathForUnexpectedFailure=_filePathForUnexpectedFailure;
51 | @property(retain, nonatomic) NSMutableSet *expectations; // @synthesize expectations=_expectations;
52 | @property BOOL didStopMeasuring; // @synthesize didStopMeasuring=_didStopMeasuring;
53 | @property BOOL didStartMeasuring; // @synthesize didStartMeasuring=_didStartMeasuring;
54 | @property BOOL didMeasureMetrics; // @synthesize didMeasureMetrics=_didMeasureMetrics;
55 | @property BOOL isMeasuringMetrics; // @synthesize isMeasuringMetrics=_isMeasuringMetrics;
56 | @property unsigned long long measuringIteration; // @synthesize measuringIteration=_measuringIteration;
57 | @property struct time_value startUserTime; // @synthesize startUserTime=_startUserTime;
58 | @property struct time_value startSystemTime; // @synthesize startSystemTime=_startSystemTime;
59 | @property unsigned long long startWallClockTime; // @synthesize startWallClockTime=_startWallClockTime;
60 | @property(retain) NSMutableDictionary *perfMetricsForID; // @synthesize perfMetricsForID=_perfMetricsForID;
61 | @property(copy) NSArray *activePerformanceMetricIDs; // @synthesize activePerformanceMetricIDs=_activePerformanceMetricIDs;
62 | @property BOOL continueAfterFailure; // @synthesize continueAfterFailure=_continueAfterFailure;
63 | @property(retain) XCTestCaseRun *testCaseRun; // @synthesize testCaseRun=_testCaseRun;
64 | @property(retain) NSInvocation *invocation; // @synthesize invocation=_invocation;
65 |
66 | - (void)resetExpectations;
67 | - (void)addExpectation:(id)arg1;
68 | - (id)init;
69 |
70 | @end
71 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/Server/Controllers/MonkeyUIAutomation.swift:
--------------------------------------------------------------------------------
1 | //
2 | // MonkeyUIAutomation.swift
3 | // Fleek
4 | //
5 | // Created by Dag Agren on 23/03/16.
6 | // Copyright © 2016 Zalando SE. All rights reserved.
7 | //
8 |
9 | import UIKit
10 |
11 | private let eventGenerator: UIASyntheticEvents = {
12 | let url = URL(fileURLWithPath: "/Developer/Library/PrivateFrameworks/UIAutomation.framework/UIAutomation")
13 |
14 | url.withUnsafeFileSystemRepresentation() { representation -> Void in
15 | dlopen(representation, RTLD_LOCAL)
16 | }
17 |
18 | let eventsclass = unsafeBitCast(NSClassFromString("UIASyntheticEvents"), to: UIASyntheticEvents.Type.self)
19 | return eventsclass.sharedEventGenerator()
20 | }()
21 |
22 | /**
23 | Extension using private funcctions from the UIAutomation
24 | API to generate events. Currently does not seem to work
25 | on actual devices for unknown reasons.
26 |
27 | The public XCTest API is far too slow for useful random testing,
28 | so currently using private APIs is the only option.
29 |
30 | As this code is only used in your tests, and never
31 | distributed, it will not cause problems with App Store
32 | approval.
33 | */
34 | extension Monkey {
35 | /**
36 | Add a sane default set of event generation actions
37 | using the private UIAutomation API. Use this function if you
38 | just want to generate some events, and do not have
39 | strong requirements on exactly which ones you need.
40 | */
41 | public func addDefaultUIAutomationActions() {
42 | addUIAutomationTapAction(weight: 50)
43 | addUIAutomationDragAction(weight: 1)
44 | addUIAutomationFlickAction(weight: 1)
45 | addUIAutomationPinchCloseAction(weight: 1)
46 | addUIAutomationPinchOpenAction(weight: 1)
47 | //addUIAutomationRotateAction(weight: 1) // TODO: Investigate why this is broken.
48 | addUIAutomationOrientationAction(weight: 1)
49 | addUIAutomationClickVolumeUpAction(weight: 1)
50 | addUIAutomationClickVolumeDownAction(weight: 1)
51 | addUIAutomationShakeAction(weight: 1)
52 | addUIAutomationLockAction(weight: 1)
53 | }
54 |
55 | /**
56 | Add an action that generates a single tap event
57 | using the private UIAutomation API.
58 |
59 | - Parameter weight: The relative probability of this
60 | event being generated. Can be any value larger than
61 | zero. Probabilities will be normalised to the sum
62 | of all relative probabilities.
63 | */
64 | public func addUIAutomationSingleTapAction(weight: Double) {
65 | addAction(weight: weight) { [weak self] in
66 | eventGenerator.sendTap(self!.randomPoint())
67 | }
68 | }
69 |
70 | /**
71 | Add an action that generates a tap, with a possibility for
72 | multiple taps with multiple fingers, or long taps, using
73 | the private UIAutomation API.
74 |
75 | - parameter weight: The relative probability of this
76 | event being generated. Can be any value larger than
77 | zero. Probabilities will be normalised to the sum
78 | of all relative probabilities.
79 | - parameter multipleTapProbability: Probability that
80 | the tap event will tap multiple times. Between 0 and 1.
81 | - parameter multipleTouchProbability: Probability that
82 | the tap event will use multiple fingers. Between 0 and 1.
83 | - parameter longPressProbability: Probability that
84 | the tap event will be a long press. Between 0 and 1.
85 | */
86 | public func addUIAutomationTapAction(weight: Double, multipleTapProbability: Double = 0.05,
87 | multipleTouchProbability: Double = 0.05, longPressProbability: Double = 0.05) {
88 | addAction(weight: weight) { [weak self] in
89 | let numberOfTaps: Int
90 | if self!.r.randomDouble() UIASyntheticEvents
302 |
303 | //@property(readonly) struct __IOHIDEventSystemClient *ioSystemClient; // @synthesize ioSystemClient=_ioSystemClient;
304 | var voiceOverStyleTouchEventsEnabled: Bool { get set }
305 | var activePointCount: UInt64 { get set }
306 | //@property(nonatomic) CDStruct_3eca2549 *activePoints; // @synthesize activePoints=_activePoints;
307 | var gsScreenScale: Double { get set }
308 | var gsScreenSize: CGSize { get set }
309 | var screenSize: CGSize { get set }
310 | var screen: UIScreen { get set }
311 | var onScreenRect: CGRect { get set }
312 |
313 | func sendPinchCloseWithStartPoint(_: CGPoint, endPoint: CGPoint, duration: Double, inRect: CGRect)
314 | func sendPinchOpenWithStartPoint(_: CGPoint, endPoint: CGPoint, duration: Double, inRect: CGRect)
315 | func sendDragWithStartPoint(_: CGPoint, endPoint: CGPoint, duration: Double, withFlick: Bool, inRect: CGRect)
316 | func sendRotate(_: CGPoint, withRadius: Double, rotation: Double, duration: Double, touchCount: UInt64)
317 | func sendMultifingerDragWithPointArray(_: UnsafePointer, numPoints: Int32, duration: Double, numFingers: Int32)
318 | func sendPinchCloseWithStartPoint(_: CGPoint, endPoint: CGPoint, duration: Double)
319 | func sendPinchOpenWithStartPoint(_: CGPoint, endPoint: CGPoint, duration: Double)
320 | func sendFlickWithStartPoint(_: CGPoint, endPoint: CGPoint, duration: Double)
321 | func sendDragWithStartPoint(_: CGPoint, endPoint: CGPoint, duration: Double)
322 | func sendTaps(_: Int, location: CGPoint, withNumberOfTouches: Int, inRect: CGRect)
323 | func sendDoubleFingerTap(_: CGPoint)
324 | func sendDoubleTap(_: CGPoint)
325 | func _sendTap(_: CGPoint, withPressure: Double)
326 | func sendTap(_: CGPoint)
327 | func _setMajorRadiusForAllPoints(_: Double)
328 | func _setPressureForAllPoints(_: Double)
329 | func moveToPoints(_: UnsafePointer, touchCount: UInt64, duration: Double)
330 | func _moveLastTouchPoint(_: CGPoint)
331 | func liftUp(_: CGPoint)
332 | func liftUp(_: CGPoint, touchCount: UInt64)
333 | func liftUpAtPoints(_: UnsafePointer, touchCount: UInt64)
334 | func touchDown(_: CGPoint)
335 | func touchDown(_: CGPoint, touchCount: UInt64)
336 | func touchDownAtPoints(_: UnsafePointer, touchCount: UInt64)
337 | func shake()
338 | func setRinger(_: Bool)
339 | func holdVolumeDown(_: Double)
340 | func clickVolumeDown()
341 | func holdVolumeUp(_: Double)
342 | func clickVolumeUp()
343 | func holdLock(_: Double)
344 | func clickLock()
345 | func lockDevice()
346 | func holdMenu(_: Double)
347 | func clickMenu()
348 | func _sendSimpleEvent(_: Int)
349 | func setOrientation(_: Int32)
350 | func sendAccelerometerX(_: Double, Y: Double, Z: Double, duration: Double)
351 | func sendAccelerometerX(_: Double, Y: Double, Z: Double)
352 | func _updateTouchPoints(_: UnsafePointer, count: UInt64)
353 | func _sendHIDVendorDefinedEvent(_: UInt32, usage: UInt32, data: UnsafePointer, dataLength: UInt32) -> Bool
354 | func _sendHIDScrollEventX(_: Double, Y: Double, Z: Double) -> Bool
355 | func _sendHIDKeyboardEventPage(_: UInt32, usage: UInt32, duration: Double) -> Bool
356 | //- (_Bool)_sendHIDEvent:(struct __IOHIDEvent *)arg1;
357 | //- (struct __IOHIDEvent *)_UIACreateIOHIDEventType:(unsigned int)arg1; func _isEdgePoint(_: CGPoint) -> Bool
358 | func _normalizePoint(_: CGPoint) -> CGPoint
359 | //- (void)dealloc;
360 | func _initScreenProperties()
361 | //- (id)init;
362 | }
363 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/Server/Controllers/MonkeyXCTest.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestWDMonkeyController.swift
3 | // FastMonkey
4 | //
5 | // fixed by zhangzhao on 2017/7/17.
6 | //
7 |
8 | import Foundation
9 | import XCTest
10 |
11 | /**
12 | Extension using the public XCTest API to generate
13 | events.
14 | */
15 | @available(iOS 9.0, *)
16 | extension Monkey {
17 |
18 | /**
19 | Add an action that checks, at a fixed interval,
20 | if an alert is being displayed, and if so, selects
21 | a random button on it.
22 |
23 | - parameter interval: How often to generate this
24 | event. One of these events will be generated after
25 | this many randomised events have been generated.
26 | - parameter application: The `XCUIApplication` object
27 | for the current application.
28 | */
29 | public func addXCTestTapAlertAction(interval: Int, application: XCUIApplication) {
30 | addAction(interval: interval) { [weak self] in
31 | // The test for alerts on screen and dismiss them if there are any.
32 | // for i in 0 ..< application.alerts.count {
33 | // let alert = application.alerts.element(boundBy: i)
34 | // let buttons = alert.descendants(matching: .button)
35 | // XCTAssertNotEqual(buttons.count, 0, "No buttons in alert")
36 | // let index = UInt(self!.r.randomUInt32() % UInt32(buttons.count))
37 | // let button = buttons.element(boundBy: index)
38 | // button.tap()
39 | // }
40 | usleep(2000000)
41 | //let isRunning = application.running
42 | //let current = Int(XCTestWDFindElementUtils.getAppPid())
43 | //if current == 0 {
44 | // return
45 | //}
46 | if application.state == XCUIApplication.State.runningForeground {
47 | for i in 0 ..< application.alerts.count {
48 | let alert = application.alerts.element(boundBy: i)
49 | let buttons = alert.descendants(matching: .button)
50 | let index: Int = Int(self!.r.randomUInt32() % UInt32(buttons.count))
51 | let button = buttons.element(boundBy: index)
52 | button.tap()
53 | }
54 | }else{
55 | application.activate()
56 | self!.sleep(5)
57 | self?.pid = Int(XCTestWDFindElementUtils.getAppPid())
58 | }
59 | }
60 | }
61 |
62 | /**
63 | Add an action that checks current app, at a fixed interval,
64 | if app is not running , so launch app
65 | */
66 |
67 | public func addXCTestCheckCurrentApp(interval:Int, application:XCUIApplication) {
68 | addCheck(interval:interval){ [weak self] in
69 | //let work = DispatchWorkItem(qos:.userInteractive){
70 | /** too slow **/
71 | //application._waitForQuiescence()
72 | // let isRunning = application.running
73 | // let current = Int(XCTestWDFindElementUtils.getAppPid())
74 | // if current != self?.pid || !isRunning{
75 | // application.launch()
76 | // self?.sleep(5)
77 | // self?.pid = Int(XCTestWDFindElementUtils.getAppPid())
78 | // }
79 | //}
80 | //DispatchQueue.main.async(execute:work)
81 | let work = DispatchWorkItem(qos:.userInteractive){
82 | if (application.state != XCUIApplication.State.runningForeground){
83 | application.activate()
84 | self?.sleep(5)
85 | self?.pid = Int(XCTestWDFindElementUtils.getAppPid())
86 | }
87 | }
88 | DispatchQueue.main.async(execute:work)
89 | }
90 | }
91 |
92 | /**
93 | Add an action that check login keypoint, at a fixed interval,
94 | if find key point, take login event
95 | */
96 |
97 | public func addXCTestAppLogin(interval:Int, application:XCUIApplication) {
98 | addAction(interval:interval){ [weak self] in
99 | do{
100 | let session = try XCTestWDSessionManager.singleton.checkDefaultSession()
101 | let root = session.application
102 | if root != nil{
103 | let usage = "xpath"
104 | let tag = "//XCUIElementTypeOther[@name='登录']/XCUIElementTypeTextField"
105 | let element = try? XCTestWDFindElementUtils.filterElement(usingText: usage, withvalue: tag, underElement: root!)
106 | if let element = element {
107 | if element != nil {
108 | self?.addXCTestLoginAction(application: application)
109 | }
110 | else{
111 | return
112 | }
113 | }
114 | }
115 | }catch{
116 | return
117 | }
118 | }
119 | }
120 | }
121 |
122 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/Server/Controllers/Random.swift:
--------------------------------------------------------------------------------
1 | //
2 | // Random.swift
3 | // Fleek
4 | //
5 | // Created by Dag Agren on 14/03/16.
6 | // Copyright © 2016 Zalando SE. All rights reserved.
7 | //
8 |
9 | import Foundation
10 |
11 | /**
12 | Simple implementation of a PCG random number generator:
13 | http://www.pcg-random.org/
14 | */
15 | struct Random {
16 | var state: UInt64 = 0
17 | let increment: UInt64
18 |
19 | init() {
20 | self.init(seed: 0)
21 | }
22 |
23 | init(seed: UInt32) {
24 | self.init(seed: 0, sequence: 0)
25 | }
26 |
27 | init(seed: UInt32, sequence: UInt32) {
28 | state = 0
29 | increment = (UInt64(sequence) << 1) | 1
30 | _ = randomUInt32()
31 | state = state &+ UInt64(seed)
32 | _ = randomUInt32()
33 | }
34 |
35 | mutating func randomUInt32() -> UInt32 {
36 | let oldstate = state
37 | state = oldstate &* 6364136223846793005 &+ increment
38 | let xorshifted = UInt32((((oldstate >> 18) ^ oldstate) >> 27) & 0xffffffff)
39 | let rot = UInt32(oldstate >> 59)
40 | return (xorshifted >> rot) | (xorshifted << UInt32(-Int(rot) & 31))
41 | }
42 |
43 | mutating func randomInt(lessThan: Int) -> Int {
44 | return Int(randomUInt32() % UInt32(lessThan))
45 | }
46 |
47 | mutating func randomUInt(lessThan: UInt) -> UInt {
48 | return UInt(randomUInt32() % UInt32(lessThan))
49 | }
50 |
51 | mutating func randomFloat() -> Float {
52 | return Float(randomUInt32()) / 4294967296.0
53 | }
54 |
55 | mutating func randomFloat(lessThan: Float) -> Float {
56 | return randomFloat() * lessThan
57 | }
58 |
59 | mutating func randomDouble() -> Double {
60 | return Double(randomUInt32()) / 4294967296.0
61 | }
62 |
63 | mutating func randomDouble(lessThan: Double) -> Double {
64 | return randomDouble() * lessThan
65 | }
66 | }
67 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/Server/Controllers/XCTestWDActionsController.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestAlertViewCommand.swift
3 | // XCTestWebdriver
4 | //
5 | // Created by zhaoy on 21/4/17.
6 | // Copyright © 2017 XCTestWebdriver. All rights reserved.
7 | //
8 |
9 | import Foundation
10 | import Swifter
11 |
12 | internal class XCTestWDActionsController: Controller {
13 |
14 | //MARK: Controller - Protocol
15 | static func routes() -> [(RequestRoute, RoutingCall)] {
16 | return [(RequestRoute("/actions", "post"), actions)]
17 | }
18 |
19 | static func shouldRegisterAutomatically() -> Bool {
20 | return false
21 | }
22 |
23 | //MARK: Routing Logic Specification
24 | internal static func actions(request: Swifter.HttpRequest) -> Swifter.HttpResponse {
25 | return HttpResponse.ok(.html("actions"))
26 | }
27 |
28 | }
29 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/Server/Controllers/XCTestWDAlertController.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestAlertViewCommand.swift
3 | // XCTestWebdriver
4 | //
5 | // Created by zhaoy on 21/4/17.
6 | // Copyright © 2017 XCTestWebdriver. All rights reserved.
7 | //
8 |
9 | import Foundation
10 | import Swifter
11 | import SwiftyJSON
12 | import CocoaLumberjackSwift
13 |
14 | internal class XCTestWDAlertController: Controller {
15 |
16 | //MARK: Controller - Protocol
17 | static func routes() -> [(RequestRoute, RoutingCall)] {
18 | return [(RequestRoute("/wd/hub/session/:sessionId/accept_alert", "post"), acceptAlert),
19 | (RequestRoute("/wd/hub/session/:sessionId/dismiss_alert", "post"), dismissAlert),
20 | (RequestRoute("/wd/hub/session/:sessionId/alert_text", "get"), alertText),
21 | (RequestRoute("/wd/hub/session/:sessionId/alert_text", "post"), alertKeys)]
22 | }
23 |
24 | static func shouldRegisterAutomatically() -> Bool {
25 | return false
26 | }
27 |
28 | //MARK: Routing Logic Specification
29 | internal static func acceptAlert(request: Swifter.HttpRequest) -> Swifter.HttpResponse {
30 | if request.session == nil {
31 | return XCTestWDResponse.response(session: nil, error: WDStatus.SessionNotCreatedException)
32 | } else {
33 | let alert = XCTestWDAlert(request.session!.application)
34 | if alert.accept() {
35 | DDLogDebug("\(XCTestWDDebugInfo.DebugLogPrefix) accepAlert success")
36 | return XCTestWDResponse.response(session: request.session!, value: nil)
37 | } else {
38 | DDLogDebug("\(XCTestWDDebugInfo.DebugLogPrefix) accepAlert failure")
39 | return XCTestWDResponse.response(session: request.session!, error: WDStatus.NoAlertOpenError)
40 | }
41 | }
42 | }
43 |
44 | internal static func dismissAlert(request: Swifter.HttpRequest) -> Swifter.HttpResponse {
45 | if request.session == nil {
46 | return XCTestWDResponse.response(session: nil, error: WDStatus.SessionNotCreatedException)
47 | } else {
48 | let alert = XCTestWDAlert(request.session!.application)
49 | if alert.dismiss() {
50 | DDLogDebug("\(XCTestWDDebugInfo.DebugLogPrefix) dismissAlert success")
51 | return XCTestWDResponse.response(session: request.session!, value: nil)
52 | } else {
53 | DDLogDebug("\(XCTestWDDebugInfo.DebugLogPrefix) dismissAlert failure")
54 | return XCTestWDResponse.response(session: request.session!, error: WDStatus.NoAlertOpenError)
55 | }
56 | }
57 | }
58 |
59 | internal static func alertText(request: Swifter.HttpRequest) -> Swifter.HttpResponse {
60 | if request.session == nil {
61 | return XCTestWDResponse.response(session: nil, error: WDStatus.SessionNotCreatedException)
62 | } else {
63 | let alert = XCTestWDAlert(request.session!.application)
64 | let text = alert.text()
65 | if text != nil {
66 | DDLogDebug("\(XCTestWDDebugInfo.DebugLogPrefix) retrieving alert text \(text!)")
67 | return XCTestWDResponse.response(session: request.session!, value: JSON(text!))
68 | } else {
69 | DDLogDebug("\(XCTestWDDebugInfo.DebugLogPrefix) retrieving alert text nil")
70 | return XCTestWDResponse.response(session: request.session!, error: WDStatus.NoAlertOpenError)
71 | }
72 | }
73 | }
74 |
75 | internal static func alertKeys(request: Swifter.HttpRequest) -> Swifter.HttpResponse {
76 | if request.session == nil {
77 | return XCTestWDResponse.response(session: nil, error: WDStatus.SessionNotCreatedException)
78 | } else {
79 | let alert = XCTestWDAlert(request.session!.application)
80 | if alert.keys(input: request.params["text"] ?? "") {
81 | return XCTestWDResponse.response(session: request.session!, value: JSON(text!))
82 | } else {
83 | return XCTestWDResponse.response(session: request.session!, error: WDStatus.NoAlertOpenError)
84 | }
85 | }
86 | }
87 |
88 | }
89 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/Server/Controllers/XCTestWDContextController.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestAlertViewCommand.swift
3 | // XCTestWebdriver
4 | //
5 | // Created by zhaoy on 21/4/17.
6 | // Copyright © 2017 XCTestWebdriver. All rights reserved.
7 | //
8 |
9 | import Foundation
10 | import Swifter
11 |
12 | internal class XCTestWDContextController: Controller {
13 |
14 | //MARK: Controller - Protocol
15 | static func routes() -> [(RequestRoute, RoutingCall)] {
16 | return [(RequestRoute("/context", "get"), getContext),
17 | (RequestRoute("/context", "post"), setContext),
18 | (RequestRoute("/contexts", "get"), getContexts)]
19 | }
20 |
21 | static func shouldRegisterAutomatically() -> Bool {
22 | return false
23 | }
24 |
25 | //MARK: Routing Logic Specification
26 | internal static func getContext(request: Swifter.HttpRequest) -> Swifter.HttpResponse {
27 | return HttpResponse.ok(.html("getContext"))
28 | }
29 |
30 | internal static func setContext(request: Swifter.HttpRequest) -> Swifter.HttpResponse {
31 | return HttpResponse.ok(.html("setContext"))
32 | }
33 |
34 | internal static func getContexts(request: Swifter.HttpRequest) -> Swifter.HttpResponse {
35 | return HttpResponse.ok(.html("getContexts"))
36 | }
37 | }
38 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/Server/Controllers/XCTestWDExecuteController.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestAlertViewCommand.swift
3 | // XCTestWebdriver
4 | //
5 | // Created by zhaoy on 21/4/17.
6 | // Copyright © 2017 XCTestWebdriver. All rights reserved.
7 | //
8 |
9 | import Foundation
10 | import Swifter
11 |
12 | internal class XCTestWDExecuteController: Controller {
13 |
14 | //MARK: Controller - Protocol
15 | static func routes() -> [(RequestRoute, RoutingCall)] {
16 | return [(RequestRoute("/execute", "post"), execute)]
17 | }
18 |
19 | static func shouldRegisterAutomatically() -> Bool {
20 | return false
21 | }
22 |
23 | //MARK: Routing Logic Specification
24 | internal static func execute(request: Swifter.HttpRequest) -> Swifter.HttpResponse {
25 | return HttpResponse.ok(.html("execute"))
26 | }
27 |
28 | }
29 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/Server/Controllers/XCTestWDKeysController.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestAlertViewCommand.swift
3 | // XCTestWebdriver
4 | //
5 | // Created by zhaoy on 21/4/17.
6 | // Copyright © 2017 XCTestWebdriver. All rights reserved.
7 | //
8 |
9 | import Foundation
10 | import Swifter
11 |
12 | internal class XCTestWDKeysController: Controller {
13 |
14 | //MARK: Controller - Protocol
15 | static func routes() -> [(RequestRoute, RoutingCall)] {
16 | return [(RequestRoute("/keys", "post"), keys)]
17 | }
18 |
19 | static func shouldRegisterAutomatically() -> Bool {
20 | return false
21 | }
22 |
23 | //MARK: Routing Logic Specification
24 | internal static func keys(request: Swifter.HttpRequest) -> Swifter.HttpResponse {
25 | return HttpResponse.ok(.html("keys"))
26 | }
27 |
28 | }
29 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/Server/Controllers/XCTestWDMonkeyController.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestWDMonkeyController.swift
3 | // FastMonkey
4 | //
5 | // Created by zhangzhao on 2017/7/17.
6 | // Copyright © 2017年 FastMonkey. All rights reserved.
7 | //
8 |
9 | import Foundation
10 | import Swifter
11 | import XCTest
12 | import SwiftyJSON
13 |
14 |
15 | internal class XCTestWDMonkeyController: Controller {
16 |
17 | //MARK: Controller - Protocol
18 | static func routes() -> [(RequestRoute, RoutingCall)] {
19 | return [(RequestRoute("/wd/hub/monkey", "post"), swiftmonkey),
20 | (RequestRoute("/wd/hub/appname", "get"), getappname)
21 | ]
22 | }
23 |
24 | static func shouldRegisterAutomatically() -> Bool {
25 | return false
26 | }
27 |
28 | internal static func getappname(request: Swifter.HttpRequest) -> Swifter.HttpResponse {
29 | let application = request.session?.application ?? XCTestWDSessionManager.singleton.checkDefaultSession().application
30 | let name = XCTestWDFindElementUtils.getAppName(underElement: application!)
31 | return HttpResponse.ok(.html(name))
32 | }
33 |
34 |
35 | //MARK: Routing Logic Specification
36 | internal static func swiftmonkey(request: Swifter.HttpRequest) -> Swifter.HttpResponse {
37 | var app : XCUIApplication!
38 | var session : XCTestWDSession!
39 |
40 | let desiredCapabilities = request.jsonBody["desiredCapabilities"].dictionary
41 | let path = desiredCapabilities?["app"]?.string ?? nil
42 | let bundleID = desiredCapabilities?["bundleId"]?.string ?? nil
43 | if bundleID == nil {
44 | app = XCTestWDSession.activeApplication()
45 | } else {
46 | app = XCUIApplication.init(privateWithPath: path, bundleID: bundleID)!
47 | app!.launchArguments = desiredCapabilities?["arguments"]?.arrayObject as! [String]? ?? [String]()
48 | app!.launchEnvironment = desiredCapabilities?["environment"]?.dictionaryObject as! [String : String]? ?? [String:String]();
49 | app!.launch()
50 | }
51 |
52 | if app != nil {
53 | session = XCTestWDSession.sessionWithApplication(app!)
54 | XCTestWDSessionManager.singleton.mountSession(session)
55 | try? session.resolve()
56 | }
57 |
58 | if app?.processID == 0 {
59 | return HttpResponse.internalServerError
60 | }
61 |
62 | sleep(10)
63 | NSLog("XCTestWDSetup->start fastmonkey<-XCTestWDSetup")
64 |
65 | _ = app.descendants(matching: .any).element(boundBy: 0).frame
66 | let monkey = Monkey(frame: app.frame)
67 | monkey.addDefaultXCTestPrivateActions()
68 | monkey.addXCTestTapAlertAction(interval: 100, application: app)
69 | monkey.addXCTestCheckCurrentApp(interval: 10, application: app)
70 | //monkey.addXCTestAppLogin(interval: 50, application: app)
71 | monkey.monkeyAround()
72 |
73 | return XCTestWDResponse.response(session: session, value: sessionInformation(session))
74 | }
75 |
76 | //MARK: Response helpers
77 | private static func sessionInformation(_ session:XCTestWDSession) -> JSON {
78 | var result:JSON = ["sessionId":session.identifier]
79 | var capabilities:JSON = ["device": UIDevice.current.userInterfaceIdiom == UIUserInterfaceIdiom.pad ? "ipad" : "iphone"]
80 | capabilities["sdkVersion"] = JSON(UIDevice.current.systemVersion)
81 | capabilities["browserName"] = JSON(session.application.label)
82 | capabilities["CFBundleIdentifier"] = JSON(session.application.bundleID ?? "Null")
83 | result["capabilities"] = capabilities
84 | return result
85 | }
86 |
87 | }
88 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/Server/Controllers/XCTestWDScreenshotController.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestAlertViewCommand.swift
3 | // XCTestWebdriver
4 | //
5 | // Created by zhaoy on 21/4/17.
6 | // Copyright © 2017 XCTestWebdriver. All rights reserved.
7 | //
8 |
9 | import Foundation
10 | import Swifter
11 | import SwiftyJSON
12 |
13 | internal class XCTestWDScreenshotController: Controller {
14 |
15 | //MARK: Controller - Protocol
16 | static func routes() -> [(RequestRoute, RoutingCall)] {
17 | return [(RequestRoute("/wd/hub/screenshot", "get"), getScreenshot),
18 | (RequestRoute("/wd/hub/session/:sessionId/screenshot", "get"), getScreenshot)]
19 | }
20 |
21 | static func shouldRegisterAutomatically() -> Bool {
22 | return false
23 | }
24 |
25 | //MARK: Routing Logic Specification
26 | internal static func getScreenshot(request: Swifter.HttpRequest) -> Swifter.HttpResponse {
27 | var base64String:String!
28 | let xcScreen:AnyClass? = NSClassFromString("XCUIScreen")
29 | if xcScreen != nil {
30 | let data = xcScreen?.value(forKeyPath: "mainScreen.screenshot.PNGRepresentation") as? NSData
31 | base64String = ((data?.base64EncodedString()))!
32 | } else {
33 | let data = (XCAXClient_iOS.sharedClient() as! XCAXClient_iOS).screenshotData()
34 | base64String = ((data?.base64EncodedString()))!
35 | }
36 |
37 | return XCTestWDResponse.response(session: request.session, value: JSON(base64String!))
38 | }
39 |
40 | }
41 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/Server/Controllers/XCTestWDSessionController.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestAlertViewCommand.swift
3 | // XCTestWebdriver
4 | //
5 | // Created by zhaoy on 21/4/17.
6 | // Copyright © 2017 XCTestWebdriver. All rights reserved.
7 | //
8 |
9 | import Foundation
10 | import Swifter
11 | import XCTest
12 | import SwiftyJSON
13 | import CocoaLumberjackSwift
14 |
15 | let XCTestWDSessionShutDown = "XCTestWDSessionShutDown"
16 |
17 | internal class XCTestWDSessionController: Controller {
18 |
19 | //MARK: Controller - Protocol
20 | static func routes() -> [(RequestRoute, RoutingCall)] {
21 | return [(RequestRoute("/wd/hub/session", "post"), createSession),
22 | (RequestRoute("/wd/hub/sessions", "get"), getSessions),
23 | (RequestRoute("/wd/hub/session/:sessionId", "delete"), delSession)]
24 | }
25 |
26 | static func shouldRegisterAutomatically() -> Bool {
27 | return false
28 | }
29 |
30 | //MARK: Routing Logic Specification
31 | internal static func createSession(request: Swifter.HttpRequest) -> Swifter.HttpResponse {
32 | var app : XCUIApplication!
33 | var session : XCTestWDSession!
34 |
35 | let desiredCapabilities = request.jsonBody["desiredCapabilities"].dictionary
36 | let path = desiredCapabilities?["app"]?.string ?? nil
37 | let bundleID = desiredCapabilities?["bundleId"]?.string ?? nil
38 |
39 | if bundleID == nil {
40 | DDLogDebug("\(XCTestWDDebugInfo.DebugLogPrefix) bundle ID input is nil, create session with current active app")
41 | app = XCTestWDSession.activeApplication()
42 | } else {
43 | DDLogDebug("\(XCTestWDDebugInfo.DebugLogPrefix) create bundle from launching input")
44 | app = XCUIApplication.init(privateWithPath: path, bundleID: bundleID)!
45 | app!.launchArguments = desiredCapabilities?["arguments"]?.arrayObject as! [String]? ?? [String]()
46 | app!.launchEnvironment = desiredCapabilities?["environment"]?.dictionaryObject as! [String : String]? ?? [String:String]();
47 | app!.launch()
48 | sleep(1)
49 | }
50 |
51 | if app != nil {
52 | DDLogDebug("\(XCTestWDDebugInfo.DebugLogPrefix) create app failure ")
53 | session = XCTestWDSession.sessionWithApplication(app!)
54 | XCTestWDSessionManager.singleton.defaultSession = session;
55 | XCTestWDSessionManager.singleton.mountSession(session)
56 | session.resolve()
57 | }
58 |
59 | if app?.processID == 0 {
60 | return HttpResponse.internalServerError
61 | }
62 |
63 | return XCTestWDResponse.response(session: session, value: sessionInformation(session))
64 | }
65 |
66 | internal static func getSessions(request: Swifter.HttpRequest) -> Swifter.HttpResponse {
67 | return XCTestWDResponse.response(session: nil, value: sessionList())
68 | }
69 |
70 | internal static func delSession(request: Swifter.HttpRequest) -> Swifter.HttpResponse {
71 | return XCTestWDResponse.response(session: nil, value: removeSessionById(request.session?.identifier ?? ""))
72 | }
73 |
74 | //MARK: Response helpers
75 | private static func sessionInformation(_ session:XCTestWDSession) -> JSON {
76 | var result:JSON = ["sessionId":session.identifier]
77 | var capabilities:JSON = ["device": UIDevice.current.userInterfaceIdiom == UIUserInterfaceIdiom.pad ? "ipad" : "iphone"]
78 | capabilities["sdkVersion"] = JSON(UIDevice.current.systemVersion)
79 | capabilities["browserName"] = JSON(session.application.label)
80 | capabilities["CFBundleIdentifier"] = JSON(session.application.bundleID ?? "Null")
81 | result["capabilities"] = capabilities
82 | return result
83 | }
84 |
85 | private static func sessionList() -> JSON {
86 | var raw = [[String:String]]()
87 | let sessionMap = XCTestWDSessionManager.singleton.queryAll()
88 | for (sessionId, _) in sessionMap {
89 | raw.append(["id":sessionId])
90 | }
91 | return JSON(raw)
92 | }
93 |
94 | private static func removeSessionById(_ sessionId:String) -> JSON {
95 | XCTestWDSessionManager.singleton.deleteSession(sessionId)
96 | return JSON("")
97 | }
98 | }
99 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/Server/Controllers/XCTestWDSourceController.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestAlertViewCommand.swift
3 | // XCTestWebdriver
4 | //
5 | // Created by zhaoy on 21/4/17.
6 | // Copyright © 2017 XCTestWebdriver. All rights reserved.
7 | //
8 |
9 | import Foundation
10 | import Swifter
11 | import SwiftyJSON
12 |
13 | internal class XCTestWDSourceController: Controller {
14 |
15 | //MARK: Controller - Protocol
16 | static func routes() -> [(RequestRoute, RoutingCall)] {
17 | return [(RequestRoute("/wd/hub/session/:sessionId/source", "get"), source),
18 | (RequestRoute("/wd/hub/source", "get"), sourceWithoutSession),
19 | (RequestRoute("/wd/hub/session/:sessionId/accessibleSource", "get"), accessiblitySource),
20 | (RequestRoute("/wd/hub/accessibleSource", "get"), accessiblitySourceWithoutSession)]
21 | }
22 |
23 | static func shouldRegisterAutomatically() -> Bool {
24 | return false
25 | }
26 |
27 | //MARK: Routing Logic Specification
28 | internal static func source(request: Swifter.HttpRequest) -> Swifter.HttpResponse {
29 | let _ = request.session?.application.query()
30 | request.session?.application.resolve()
31 | let temp = request.session?.application.tree()
32 | return XCTestWDResponse.response(session: request.session, value: JSON(JSON(temp!).rawString() ?? ""))
33 | }
34 |
35 | internal static func sourceWithoutSession(request: Swifter.HttpRequest) -> Swifter.HttpResponse {
36 | let temp = XCTestWDSession.activeApplication()?.tree()
37 | return XCTestWDResponse.response(session: request.session, value: JSON(temp!))
38 | }
39 |
40 | internal static func accessiblitySource(request: Swifter.HttpRequest) -> Swifter.HttpResponse {
41 | let _ = request.session?.application.query()
42 | request.session?.application.resolve()
43 | let temp = request.session?.application.accessibilityTree()
44 | return XCTestWDResponse.response(session: request.session, value: JSON(JSON(temp!).rawString() ?? ""))
45 | }
46 |
47 | internal static func accessiblitySourceWithoutSession(request: Swifter.HttpRequest) -> Swifter.HttpResponse {
48 | let temp = XCTestWDSessionManager.singleton.checkDefaultSession().application.accessibilityTree()
49 | return XCTestWDResponse.response(session: request.session, value: JSON(temp!))
50 | }
51 | }
52 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/Server/Controllers/XCTestWDStatusController.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestAlertViewCommand.swift
3 | // XCTestWebdriver
4 | //
5 | // Created by zhaoy on 21/4/17.
6 | // Copyright © 2017 XCTestWebdriver. All rights reserved.
7 | //
8 |
9 | import Foundation
10 | import Swifter
11 |
12 | internal class XCTestWDStatusController: Controller {
13 |
14 | //MARK: Controller - Protocol
15 | static func routes() -> [(RequestRoute, RoutingCall)] {
16 | return [(RequestRoute("/wd/hub/status", "get"), status)]
17 | }
18 |
19 | static func shouldRegisterAutomatically() -> Bool {
20 | return false
21 | }
22 |
23 | //MARK: Routing Logic Specification
24 | internal static func status(request: Swifter.HttpRequest) -> Swifter.HttpResponse {
25 | return HttpResponse.ok(.html("status"))
26 | }
27 |
28 | }
29 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/Server/Controllers/XCTestWDTimeoutController.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestAlertViewCommand.swift
3 | // XCTestWebdriver
4 | //
5 | // Created by zhaoy on 21/4/17.
6 | // Copyright © 2017 XCTestWebdriver. All rights reserved.
7 | //
8 |
9 | import Foundation
10 | import Swifter
11 |
12 | internal class XCTestWDTimeoutController: Controller {
13 |
14 | //MARK: Controller - Protocol
15 | static func routes() -> [(RequestRoute, RoutingCall)] {
16 | return [(RequestRoute("/timeouts/implicit_wait", "post"), implicitWait)]
17 | }
18 |
19 | static func shouldRegisterAutomatically() -> Bool {
20 | return false
21 | }
22 |
23 | //MARK: Routing Logic Specification
24 | internal static func implicitWait(request: Swifter.HttpRequest) -> Swifter.HttpResponse {
25 | return HttpResponse.ok(.html("implicitWait"))
26 | }
27 |
28 | }
29 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/Server/Controllers/XCTestWDTitleController.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestAlertViewCommand.swift
3 | // XCTestWebdriver
4 | //
5 | // Created by zhaoy on 21/4/17.
6 | // Copyright © 2017 XCTestWebdriver. All rights reserved.
7 | //
8 |
9 | import Foundation
10 | import Swifter
11 |
12 | internal class XCTestWDTitleController: Controller {
13 |
14 | //MARK: Controller - Protocol
15 | static func routes() -> [(RequestRoute, RoutingCall)] {
16 | return [(RequestRoute("/title", "get"), title)]
17 | }
18 |
19 | static func shouldRegisterAutomatically() -> Bool {
20 | return false
21 | }
22 |
23 | //MARK: Routing Logic Specification
24 | internal static func title(request: Swifter.HttpRequest) -> Swifter.HttpResponse {
25 | return HttpResponse.ok(.html("title"))
26 | }
27 |
28 | }
29 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/Server/Controllers/XCTestWDUrlController.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestAlertViewCommand.swift
3 | // XCTestWebdriver
4 | //
5 | // Created by zhaoy on 21/4/17.
6 | // Copyright © 2017 XCTestWebdriver. All rights reserved.
7 | //
8 |
9 | import Foundation
10 | import Swifter
11 |
12 | internal class XCTestWDUrlController: Controller {
13 |
14 | //MARK: Controller - Protocol
15 | static func routes() -> [(RequestRoute, RoutingCall)] {
16 | return [(RequestRoute("/wd/hub/session/:sessionId/url", "post"), url),
17 | (RequestRoute("/wd/hub/session/:sessionId/url", "get"), getUrl),
18 | (RequestRoute("/wd/hub/session/:sessionId/forward", "post"), forward),
19 | (RequestRoute("/wd/hub/session/:sessionId/back", "post"), back),
20 | (RequestRoute("/wd/hub/session/:sessionId/refresh", "post"), refresh)]
21 | }
22 |
23 | static func shouldRegisterAutomatically() -> Bool {
24 | return false
25 | }
26 |
27 | //MARK: Routing Logic Specification
28 | internal static func url(request: Swifter.HttpRequest) -> Swifter.HttpResponse {
29 | return HttpResponse.ok(.html("url"))
30 | }
31 |
32 | internal static func getUrl(request: Swifter.HttpRequest) -> Swifter.HttpResponse {
33 | return HttpResponse.ok(.html("getUrl"))
34 | }
35 |
36 | internal static func forward(request: Swifter.HttpRequest) -> Swifter.HttpResponse {
37 | return HttpResponse.ok(.html("forward"))
38 | }
39 |
40 | internal static func back(request: Swifter.HttpRequest) -> Swifter.HttpResponse {
41 | let session = request.session ?? XCTestWDSessionManager.singleton.checkDefaultSession()
42 | let application = session.application
43 | if ((application?.navigationBars.buttons.count) ?? 0 > 0) {
44 | application?.navigationBars.buttons.element(boundBy: 0).tap()
45 | return XCTestWDResponse.response(session: nil, error: WDStatus.Success)
46 | }
47 |
48 | return XCTestWDResponse.response(session: nil, error: WDStatus.ElementIsNotSelectable)
49 | }
50 |
51 | internal static func refresh(request: Swifter.HttpRequest) -> Swifter.HttpResponse {
52 | return HttpResponse.ok(.html("refresh"))
53 | }
54 |
55 | }
56 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/Server/Controllers/XCTestWDWindowController.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestAlertViewCommand.swift
3 | // XCTestWebdriver
4 | //
5 | // Created by zhaoy on 21/4/17.
6 | // Copyright © 2017 XCTestWebdriver. All rights reserved.
7 | //
8 |
9 | import Foundation
10 | import Swifter
11 | import SwiftyJSON
12 |
13 | internal class XCTestWDWindowController: Controller {
14 |
15 | //MARK: Controller - Protocol
16 | static func routes() -> [(RequestRoute, RoutingCall)] {
17 | return [(RequestRoute("/wd/hub/session/:sessionId/window/current/size", "get"), getWindowSize)]
18 | }
19 |
20 | static func shouldRegisterAutomatically() -> Bool {
21 | return false
22 | }
23 |
24 | //MARK: Routing Logic Specification
25 | internal static func getWindowSize(request: Swifter.HttpRequest) -> Swifter.HttpResponse {
26 | let application = XCTestWDSessionManager.singleton.checkDefaultSession().application
27 | let frame = application?.wdFrame()
28 | let screenSize = MathUtils.adjustDimensionsForApplication(frame!.size, UIDeviceOrientation.init(rawValue:(application?.interfaceOrientation.rawValue)!)!)
29 |
30 | return XCTestWDResponse.response(session: nil, value: JSON(["width":screenSize.width,"height":screenSize.height]))
31 | }
32 |
33 | }
34 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/Server/Modules/Extensions/XCTestWDFindElementUtils.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestWDFindElementUtils.swift
3 | // XCTestWD
4 | //
5 | // fixed by zhangzhao on 8/1/17.
6 | //
7 |
8 | import Foundation
9 |
10 | class XCTestWDFindElementUtils {
11 |
12 | // TODO: provide alert filter here
13 |
14 | static func tree(underElement:XCUIElement) throws -> [CGPoint]? {
15 | return underElement.pageSourceToPoint()
16 | }
17 |
18 | static func getAppName(underElement:XCUIElement) -> String{
19 | return underElement.rootName()
20 | }
21 |
22 | static func getAppPid() -> Int32{
23 | let application = XCTestWDSession.activeApplication()
24 | let pid = application?.processID
25 | if pid == nil{
26 | return 0
27 | }
28 | return pid!
29 | }
30 |
31 | static func filterElement(usingText:String, withvalue:String, underElement:XCUIElement) throws -> XCUIElement? {
32 |
33 | return try filterElements(usingText:usingText, withValue:withvalue, underElement:underElement, returnAfterFirstMatch:true)?.first
34 | }
35 |
36 |
37 | // Routing for xpath, class name, name, id
38 | static func filterElements(usingText:String, withValue:String, underElement:XCUIElement, returnAfterFirstMatch:Bool) throws -> [XCUIElement]? {
39 |
40 | let isSearchByIdentifier = (usingText == "name" || usingText == "id" || usingText == "accessibility id")
41 |
42 | if usingText == "xpath" {
43 | return underElement.descendantsMatchingXPathQuery(xpathQuery: withValue,
44 | returnAfterFirstMatch: returnAfterFirstMatch)
45 | } else if usingText == "class name" {
46 | return underElement.descendantsMatchingClassName(className: withValue,
47 | returnAfterFirstMatch: returnAfterFirstMatch)
48 | } else if isSearchByIdentifier {
49 | return underElement.descendantsMatchingIdentifier(accessibilityId: withValue,
50 | returnAfterFirstMatch: returnAfterFirstMatch)
51 | }
52 |
53 | throw XCTestWDRoutingError.noSuchUsingMethod
54 | }
55 |
56 | }
57 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/Server/Modules/Extensions/XCTestWDMathUtils.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestWDMathUtils.swift
3 | // XCTestWD
4 | //
5 | // Created by zhaoy on 5/5/17.
6 | // Copyright © 2017 XCTestWD. All rights reserved.
7 | //
8 |
9 | import Foundation
10 |
11 | class MathUtils {
12 |
13 | static func adjustDimensionsForApplication(_ actualSize:CGSize , _ orientation:UIDeviceOrientation) -> CGSize {
14 | if (orientation == UIDeviceOrientation.landscapeLeft || orientation == UIDeviceOrientation.landscapeRight) {
15 | /*
16 | There is an XCTest bug that application.frame property returns exchanged dimensions for landscape mode.
17 | This verification is just to make sure the bug is still there (since height is never greater than width in landscape)
18 | and to make it still working properly after XCTest itself starts to respect landscape mode.
19 | */
20 | if (actualSize.height > actualSize.width) {
21 | return CGSize(width:actualSize.height, height:actualSize.width)
22 | }
23 | }
24 | return actualSize;
25 | }
26 | }
27 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/Server/Modules/Extensions/XCTestWDXPath.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestWDXPath.swift
3 | // XCTestWD
4 | //
5 | // Created by zhaoy on 5/5/17.
6 | // Copyright © 2017 XCTestWD. All rights reserved.
7 | //
8 |
9 | import Foundation
10 | import AEXML
11 | import Fuzi
12 |
13 | internal class XCTestWDXPath {
14 |
15 | //MARK: External API
16 | static let defaultTopDir = "top"
17 |
18 | static func xpathToList(_ root:XCElementSnapshot, _ xpathQuery:String) -> [CGPoint]? {
19 |
20 | var mapping = [String:XCElementSnapshot]()
21 | let xml = generateXMLPresentation(root,nil,nil,defaultTopDir,&mapping)?.xml
22 | if xml == nil
23 | {return nil}
24 |
25 | let tree = try? XMLDocument(string: xml!, encoding:String.Encoding.utf8)
26 | let nodes = tree?.xpath(xpathQuery)
27 | var list = [CGPoint]()
28 | for node in nodes! {
29 | if mapping[node.attr("private_indexPath")!] != nil{
30 | let x = (node.attr("x")! as NSString).floatValue
31 | let y = (node.attr("y")! as NSString).floatValue
32 | if (x <= 0) && (y <= 0)
33 | {continue}
34 |
35 | let snapshot = mapping[node.attr("private_indexPath")!]
36 | let isvisible = try? snapshot?.isWDVisible()
37 | if isvisible == nil || isvisible! == false
38 | {continue}
39 |
40 | let w = (node.attr("width")! as NSString).floatValue
41 | let h = (node.attr("height")! as NSString).floatValue
42 | let cX = Int(x + w/2)
43 | let cY = Int(y + h/2)
44 | let point = CGPoint(x:cX,y:cY)
45 | if list.contains(point) == false {
46 | list.append(point)
47 | }
48 | }
49 | }
50 | return list
51 | }
52 |
53 | static func findMatchesIn(_ root:XCElementSnapshot, _ xpathQuery:String) -> [XCElementSnapshot]? {
54 |
55 | var mapping = [String:XCElementSnapshot]()
56 | let documentXml = generateXMLPresentation(root,
57 | nil,
58 | nil,
59 | defaultTopDir,
60 | &mapping)?.xml
61 |
62 | if documentXml == nil {
63 | return nil
64 | }
65 |
66 |
67 | let document = try? XMLDocument(string: documentXml!, encoding:String.Encoding.utf8)
68 | let nodes = document?.xpath(xpathQuery)
69 | var results = [XCElementSnapshot]()
70 | for node in nodes! {
71 | if mapping[node.attr("private_indexPath")!] != nil {
72 | results.append(mapping[node.attr("private_indexPath")!]!)
73 | }
74 | }
75 |
76 | return results
77 | }
78 |
79 | //MARK: Internal Utils
80 | static func generateXMLPresentation(_ root:XCElementSnapshot, _ parentElement:AEXMLElement?, _ writingDocument:AEXMLDocument?, _ indexPath:String, _ mapping: inout [String:XCElementSnapshot]) -> AEXMLDocument? {
81 |
82 | let elementName = XCUIElementTypeTransformer.singleton.stringWithElementType(root.elementType)
83 | let currentElement = AEXMLElement(name:elementName)
84 | recordAttributeForElement(root, currentElement, indexPath)
85 |
86 | let document : AEXMLDocument!
87 | if parentElement == nil || writingDocument == nil {
88 | document = AEXMLDocument()
89 | document.addChild(currentElement)
90 | } else {
91 | document = writingDocument!
92 | parentElement?.addChild(currentElement)
93 | }
94 |
95 | var index = 0;
96 | for child in root.children {
97 | let childSnapshot = child as! XCElementSnapshot
98 | let childIndexPath = indexPath.appending(",\(index)")
99 | index += 1
100 | mapping[childIndexPath] = childSnapshot
101 |
102 | _ = generateXMLPresentation(childSnapshot, currentElement, document, childIndexPath, &mapping)
103 | }
104 |
105 | return document
106 | }
107 |
108 | static func recordAttributeForElement(_ snapshot:XCElementSnapshot, _ currentElement:AEXMLElement, _ indexPath:String?) {
109 |
110 | currentElement.attributes["type"] = XCUIElementTypeTransformer.singleton.stringWithElementType(snapshot.elementType)
111 |
112 | if snapshot.wdValue() != nil {
113 | let value = snapshot.wdValue()!
114 | if let str = value as? String {
115 | currentElement.attributes["value"] = str
116 | } else if let bin = value as? Bool {
117 | currentElement.attributes["value"] = bin ? "1":"0";
118 | } else {
119 | currentElement.attributes["value"] = (value as AnyObject).debugDescription
120 | }
121 | }
122 |
123 | if snapshot.wdName() != nil {
124 | currentElement.attributes["name"] = snapshot.wdName()!
125 | }
126 |
127 | if snapshot.wdLabel() != nil {
128 | currentElement.attributes["label"] = snapshot.wdLabel()!
129 | }
130 |
131 | currentElement.attributes["enabled"] = snapshot.isWDEnabled() ? "true":"false"
132 |
133 | let rect = snapshot.wdRect()
134 | for key in ["x","y","width","height"] {
135 | currentElement.attributes[key] = rect[key]!.description
136 | }
137 |
138 | if indexPath != nil {
139 | currentElement.attributes["private_indexPath"] = indexPath!
140 | }
141 | }
142 | }
143 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/Server/Modules/Utils/XCTestWDApplicationTree.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestWDApplicationTree.swift
3 | // XCTestWD
4 | //
5 | // Created by zhaoy on 5/5/17.
6 | // Copyright © 2017 XCTestWD. All rights reserved.
7 | //
8 |
9 | import Foundation
10 | import SwiftyJSON
11 |
12 | extension XCUIApplication {
13 |
14 | func mainWindowSnapshot() -> XCElementSnapshot? {
15 | let mainWindows = (self.lastSnapshot() as! XCElementSnapshot).descendantsByFiltering { (snapshot) -> Bool in
16 | return snapshot?.isMainWindow ?? false
17 | }
18 | return mainWindows?.last
19 | }
20 | }
21 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/Server/Modules/XCTestWDAlert.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestWDAlert.swift
3 | // XCTestWD
4 | //
5 | // Created by zhaoy on 27/4/17.
6 | // Copyright © 2017 XCTestWD. All rights reserved.
7 | //
8 |
9 | import Foundation
10 |
11 | internal class XCTestWDAlert {
12 |
13 | private let application:XCUIApplication!
14 |
15 | init(_ application:XCUIApplication) {
16 | self.application = application
17 | }
18 |
19 | //MARK: Commands
20 |
21 | //TODO: works on XPATH and then works on getting text
22 | internal func text() -> String? {
23 |
24 | let alertElement = self.alertElement()
25 | if alertElement != nil {
26 | return nil
27 | }
28 |
29 | return nil
30 | }
31 | //TODO: works on XPATH and then works on getting this
32 | internal func keys(input: String) -> Bool {
33 |
34 | return false
35 | }
36 |
37 | internal func accept() -> Bool {
38 |
39 | let alertElement = self.alertElement()
40 | let buttons = self.alertElement()?.descendants(matching: XCUIElement.ElementType.button).allElementsBoundByIndex
41 | var defaultButton:XCUIElement?
42 |
43 | if alertElement?.elementType == XCUIElement.ElementType.alert {
44 | defaultButton = (buttons?.last)
45 | } else {
46 | defaultButton = (buttons?.first)
47 | }
48 |
49 | if defaultButton != nil {
50 | defaultButton?.tap()
51 | return true
52 | }
53 |
54 | return false
55 | }
56 |
57 | internal func dismiss() -> Bool {
58 |
59 | let alertElement = self.alertElement()
60 | let buttons = self.alertElement()?.descendants(matching: XCUIElement.ElementType.button).allElementsBoundByIndex
61 | var defaultButton:XCUIElement?
62 |
63 | if alertElement?.elementType == XCUIElement.ElementType.alert {
64 | defaultButton = (buttons?.first)
65 | } else {
66 | defaultButton = (buttons?.last)
67 | }
68 |
69 | if defaultButton != nil {
70 | defaultButton?.tap()
71 | return true
72 | }
73 |
74 | return false
75 | }
76 |
77 | //MARK: Utils
78 | private func alertElement() -> XCUIElement? {
79 | var alert = self.application.alerts.element
80 | // Check default alerts exists
81 | if !(alert.exists) {
82 | alert = self.application.sheets.element
83 | // Check actionsheet exists
84 | if !(alert.exists) {
85 | let sprintboard = XCUIApplication.init(privateWithPath: nil, bundleID: "com.apple.springboard")
86 | alert = (sprintboard?.alerts.element) ?? alert
87 | if !(alert.exists) {
88 | return nil
89 | }
90 | }
91 | }
92 |
93 | alert.resolve()
94 | self.application.query()
95 | self.application.resolve()
96 | return alert
97 | }
98 | }
99 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/Server/Modules/XCTestWDErrors.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestWDErrors.swift
3 | // XCTestWD
4 | //
5 | // Created by zhaoy on 11/5/17.
6 | // Copyright © 2017 XCTestWD. All rights reserved.
7 | //
8 |
9 | import Foundation
10 |
11 | enum XCTestWDRoutingError: Error {
12 | case noSuchUsingMethod
13 | }
14 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/Server/Modules/XCTestWDReponse.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestWDReponse.swift
3 | // XCTestWD
4 | //
5 | // Created by zhaoy on 24/4/17.
6 | // Copyright © 2017 XCTestWD. All rights reserved.
7 | //
8 |
9 | import Foundation
10 | import SwiftyJSON
11 | import Swifter
12 |
13 | internal class XCTestWDResponse {
14 |
15 | //MARK: Model & Constructor
16 | private var sessionId:String!
17 | private var status:WDStatus!
18 | private var value:JSON?
19 |
20 | private init(_ sessionId:String, _ status:WDStatus, _ value:JSON?) {
21 | self.sessionId = sessionId
22 | self.status = status
23 | self.value = value ?? JSON("")
24 | }
25 |
26 | private func response() -> HttpResponse {
27 | let response : JSON = ["sessionId":self.sessionId,
28 | "status":self.status.rawValue,
29 | "value":self.value as Any]
30 | let rawString = response.rawString(options:[])?.replacingOccurrences(of: "\n", with: "")
31 | return rawString != nil ? HttpResponse.ok(.text(rawString!)) : HttpResponse.ok(.text("{}"))
32 | }
33 |
34 | //MARK: Utils
35 | static func response(session:XCTestWDSession?, value:JSON?) -> HttpResponse {
36 | return XCTestWDResponse(session?.identifier ?? "", WDStatus.Success, value ?? JSON("{}")).response()
37 | }
38 |
39 | static func response(session:XCTestWDSession? ,error:WDStatus) -> HttpResponse {
40 | return XCTestWDResponse(session?.identifier ?? "", error, nil).response()
41 | }
42 |
43 | //MARK: Element Response
44 | static func responseWithCacheElement(_ element:XCUIElement, _ elementCache:XCTestWDElementCache) -> HttpResponse {
45 | let elementUUID = elementCache.storeElement(element)
46 | return getResponseFromDictionary(dictionaryWithElement(element, elementUUID, false))
47 | }
48 |
49 | static func responsWithCacheElements(_ elements:[XCUIElement], _ elementCache:XCTestWDElementCache) -> HttpResponse {
50 | var response = [[String:String]]()
51 | for element in elements {
52 | let elementUUID = elementCache.storeElement(element)
53 | response.append(dictionaryWithElement(element, elementUUID, false))
54 | }
55 | return XCTestWDResponse.response(session: nil, value: JSON(response))
56 | }
57 |
58 | // ------------ Internal Method ---------
59 | private static func dictionaryWithElement(_ element:XCUIElement, _ elementUUID:String, _ compact:Bool) -> [String:String] {
60 | var dictionary = [String:String]();
61 | dictionary["ELEMENT"] = elementUUID
62 |
63 | if compact == false {
64 | dictionary["label"] = element.wdLabel()
65 | dictionary["type"] = element.wdType()
66 | }
67 |
68 | return dictionary
69 | }
70 |
71 | private static func getResponseFromDictionary(_ dictionary:[String:String]) -> HttpResponse {
72 | return XCTestWDResponse.response(session:nil, value:JSON(dictionary))
73 | }
74 |
75 | }
76 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/Server/Modules/XCTestWDSession.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestWDSession.swift
3 | // XCTestWD
4 | //
5 | // Created by zhaoy on 23/4/17.
6 | // Copyright © 2017 XCTestWD. All rights reserved.
7 | //
8 |
9 | import Foundation
10 | import Swifter
11 | import SwiftyJSON
12 | import CocoaLumberjackSwift
13 |
14 | //MARK: Session & Cache for XCUIElement
15 | internal class XCTestWDElementCache
16 | {
17 |
18 | private var cache = [String: XCUIElement]()
19 |
20 | // Returns UUID of the stored element
21 | func storeElement(_ element:XCUIElement) -> String {
22 | let uuid = UUID.init().uuidString
23 | cache[uuid] = element
24 | return uuid
25 | }
26 |
27 | // Returns cached element
28 | func elementForUUID(_ uuid:String?) -> XCUIElement? {
29 | if uuid == nil {
30 | return nil
31 | }
32 | return cache[uuid!]
33 | }
34 | }
35 |
36 | public class XCTestWDSession {
37 |
38 | var identifier: String!
39 | private var _application: XCUIApplication!
40 | var application: XCUIApplication! {
41 | get {
42 | // Add protection for application resolve. only when application status active cam execute this
43 | if _application.accessibilityActivate() == true {
44 | resolve()
45 | }
46 | return _application
47 | }
48 | set {
49 | _application = newValue
50 | }
51 | }
52 |
53 | static func sessionWithApplication(_ application: XCUIApplication) -> XCTestWDSession {
54 |
55 | let session = XCTestWDSession()
56 | session.application = application
57 | session.identifier = UUID.init().uuidString
58 |
59 | return session
60 | }
61 |
62 | static func activeApplication() -> XCUIApplication?
63 | {
64 | return XCTestWDApplication.activeApplication()
65 | }
66 |
67 | func resolve() {
68 | self._application.query()
69 | self._application.resolve()
70 | }
71 | }
72 |
73 | //MARK: Multi-Session Control
74 | public class XCTestWDSessionManager {
75 |
76 | public static let singleton = XCTestWDSessionManager()
77 | static let commonCache: XCTestWDElementCache = XCTestWDElementCache()
78 |
79 | private var sessionMapping = [String: XCTestWDSession]()
80 | var defaultSession:XCTestWDSession?
81 |
82 | func mountSession(_ session: XCTestWDSession) {
83 | sessionMapping[session.identifier] = session
84 | }
85 |
86 | func querySession(_ identifier:String) -> XCTestWDSession? {
87 | return sessionMapping[identifier]
88 | }
89 |
90 | func checkDefaultSession() -> XCTestWDSession {
91 | if self.defaultSession == nil || self.defaultSession?.application.state != XCUIApplication.State.runningForeground {
92 | DDLogDebug("\(XCTestWDDebugInfo.DebugLogPrefix) current application not active, reloading active application")
93 | sleep(3)
94 | let application = XCTestWDSession.activeApplication()
95 | self.defaultSession = XCTestWDSession.sessionWithApplication(application!)
96 | self.defaultSession?.resolve()
97 | }
98 |
99 | return self.defaultSession!
100 | }
101 |
102 | func queryAll() -> [String:XCTestWDSession] {
103 | return sessionMapping
104 | }
105 |
106 | public func clearAll() {
107 | sessionMapping.removeAll()
108 | }
109 |
110 | func deleteSession(_ sessionId:String) {
111 | sessionMapping.removeValue(forKey: sessionId)
112 | NotificationCenter.default.post(name: NSNotification.Name(XCTestWDSessionShutDown), object: nil)
113 | }
114 | }
115 |
116 | //MARK: Extension
117 | extension HttpRequest {
118 | var session: XCTestWDSession? {
119 | get {
120 | if self.params["sessionId"] != nil && XCTestWDSessionManager.singleton.querySession(self.params["sessionId"]!) != nil {
121 | return XCTestWDSessionManager.singleton.querySession(self.params["sessionId"]!)
122 | } else if self.path.contains("/session/") {
123 | let components = self.path.components(separatedBy:"/")
124 | let index = components.index(of: "session")!
125 | if index >= components.count - 1 {
126 | DDLogDebug("\(XCTestWDDebugInfo.DebugLogPrefix) session can't be at the last component in the whole path")
127 | return nil
128 | }
129 | return XCTestWDSessionManager.singleton.querySession(components[index + 1])
130 | } else {
131 | DDLogDebug("\(XCTestWDDebugInfo.DebugLogPrefix) no session id in current request")
132 | return nil
133 | }
134 | }
135 | }
136 |
137 | var elementId: String? {
138 | get {
139 | if self.path.contains("/element/") {
140 | let components = self.path.components(separatedBy:"/")
141 | let index = components.index(of: "element")!
142 | if index < components.count - 1 {
143 | return components[index + 1]
144 | }
145 | }
146 |
147 | DDLogDebug("\(XCTestWDDebugInfo.DebugLogPrefix) no element id retrieved from current query")
148 | return nil
149 | }
150 | }
151 |
152 | var jsonBody:JSON {
153 | get {
154 | return (try? JSON(data: NSData(bytes: &self.body, length: self.body.count) as Data)) ?? JSON(parseJSON: "{}")
155 | }
156 | }
157 | }
158 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/Server/Modules/XCTestWDStatus.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestWDStatus.swift
3 | // XCTestWD
4 | //
5 | // Created by zhaoy on 24/4/17.
6 | // Copyright © 2017 XCTestWD. All rights reserved.
7 | //
8 |
9 | import Foundation
10 |
11 | enum WDStatus: Int {
12 | case
13 | Success = 0,
14 | NoSuchElement = 7,
15 | NoSuchFrame = 8,
16 | UnknownCommand = 9,
17 | StaleElementReference = 10,
18 | ElementNotVisible = 11,
19 | InvalidElementState = 12,
20 | UnknownError = 13,
21 | ElementIsNotSelectable = 15,
22 | JavaScriptError = 17,
23 | XPathLookupError = 19,
24 | Timeout = 21,
25 | NoSuchWindow = 23,
26 | InvalidCookieDomain = 24,
27 | UnableToSetCookie = 25,
28 | UnexpectedAlertOpen = 26,
29 | NoAlertOpenError = 27,
30 | ScriptTimeout = 28,
31 | InvalidElementCoordinates = 29,
32 | IMENotAvailable = 30,
33 | IMEEngineActivationFailed = 31,
34 | InvalidSelector = 32,
35 | SessionNotCreatedException = 33,
36 | MoveTargetOutOfBounds = 34
37 |
38 | static func evaluate(_ status:WDStatus) -> String {
39 | switch status {
40 |
41 | case .Success:
42 | return "The command executed successfully"
43 |
44 | case .NoSuchElement:
45 | return "An element could not be located on the page using the given search parameters."
46 |
47 | case .NoSuchFrame:
48 | return "A request to switch to a frame could not be satisfied because the frame could not be found."
49 |
50 | case .UnknownCommand:
51 | return "The requested resource could not be found, or a request was received using an HTTP method that is not supported by the mapped resource."
52 |
53 | case .StaleElementReference:
54 | return "An element command failed because the referenced element is no longer attached to the DOM."
55 |
56 | case .ElementNotVisible:
57 | return "An element command could not be completed because the element is not visible on the page."
58 |
59 | case .InvalidElementState:
60 | return "An element command could not be completed because the element is in an invalid state (e.g. attempting to click a disabled element)."
61 |
62 | case .UnknownError:
63 | return "An unknown server-side error occurred while processing the command."
64 |
65 | case .ElementIsNotSelectable:
66 | return "An attempt was made to select an element that cannot be selected."
67 |
68 | case .JavaScriptError:
69 | return "An error occurred while executing user supplied JavaScript."
70 |
71 | case .XPathLookupError:
72 | return "An error occurred while searching for an element by XPath."
73 |
74 | case .Timeout:
75 | return "An operation did not complete before its timeout expired."
76 |
77 | case .NoSuchWindow:
78 | return "A request to switch to a different window could not be satisfied because the window could not be found."
79 |
80 | case .InvalidCookieDomain:
81 | return "An illegal attempt was made to set a cookie under a different domain than the current page."
82 |
83 | case .UnableToSetCookie:
84 | return "A request to set a cookie's value could not be satisfied."
85 |
86 | case .UnexpectedAlertOpen:
87 | return "A modal dialog was open, blocking this operation."
88 |
89 | case .NoAlertOpenError:
90 | return "An attempt was made to operate on a modal dialog when one was not open."
91 |
92 | case .ScriptTimeout:
93 | return "A script did not complete before its timeout expired."
94 |
95 | case .InvalidElementCoordinates:
96 | return "The coordinates provided to an interactions operation are invalid."
97 |
98 | case .IMENotAvailable:
99 | return "IME was not available."
100 |
101 | case .IMEEngineActivationFailed:
102 | return "An IME engine could not be started."
103 |
104 | case .InvalidSelector:
105 | return "Argument was an invalid selector (e.g. XPath/CSS)."
106 |
107 | case .SessionNotCreatedException:
108 | return "Session Not Created Exception"
109 |
110 | case .MoveTargetOutOfBounds:
111 | return "Move Target Out Of Bounds"
112 | }
113 | }
114 | }
115 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/Server/Modules/XCUIElementTypeTransformer.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCUIElementTypeTransformer.swift
3 | // XCTestWD
4 | //
5 | // Created by zhaoy on 29/4/17.
6 | // Copyright © 2017 XCTestWD. All rights reserved.
7 | //
8 |
9 | import Foundation
10 |
11 | class XCUIElementTypeTransformer {
12 |
13 | var elementStringMapping:[UInt:String]
14 | var stringElementMapping:[String:UInt]
15 |
16 | static let singleton = XCUIElementTypeTransformer()
17 |
18 | private init() {
19 | elementStringMapping = [
20 | 0 : "XCUIElementTypeAny",
21 | 1 : "XCUIElementTypeOther",
22 | 2 : "XCUIElementTypeApplication",
23 | 3 : "XCUIElementTypeGroup",
24 | 4 : "XCUIElementTypeWindow",
25 | 5 : "XCUIElementTypeSheet",
26 | 6 : "XCUIElementTypeDrawer",
27 | 7 : "XCUIElementTypeAlert",
28 | 8 : "XCUIElementTypeDialog",
29 | 9 : "XCUIElementTypeButton",
30 | 10 : "XCUIElementTypeRadioButton",
31 | 11 : "XCUIElementTypeRadioGroup",
32 | 12 : "XCUIElementTypeCheckBox",
33 | 13 : "XCUIElementTypeDisclosureTriangle",
34 | 14 : "XCUIElementTypePopUpButton",
35 | 15 : "XCUIElementTypeComboBox",
36 | 16 : "XCUIElementTypeMenuButton",
37 | 17 : "XCUIElementTypeToolbarButton",
38 | 18 : "XCUIElementTypePopover",
39 | 19 : "XCUIElementTypeKeyboard",
40 | 20 : "XCUIElementTypeKey",
41 | 21 : "XCUIElementTypeNavigationBar",
42 | 22 : "XCUIElementTypeTabBar",
43 | 23 : "XCUIElementTypeTabGroup",
44 | 24 : "XCUIElementTypeToolbar",
45 | 25 : "XCUIElementTypeStatusBar",
46 | 26 : "XCUIElementTypeTable",
47 | 27 : "XCUIElementTypeTableRow",
48 | 28 : "XCUIElementTypeTableColumn",
49 | 29 : "XCUIElementTypeOutline",
50 | 30 : "XCUIElementTypeOutlineRow",
51 | 31 : "XCUIElementTypeBrowser",
52 | 32 : "XCUIElementTypeCollectionView",
53 | 33 : "XCUIElementTypeSlider",
54 | 34 : "XCUIElementTypePageIndicator",
55 | 35 : "XCUIElementTypeProgressIndicator",
56 | 36 : "XCUIElementTypeActivityIndicator",
57 | 37 : "XCUIElementTypeSegmentedControl",
58 | 38 : "XCUIElementTypePicker",
59 | 39 : "XCUIElementTypePickerWheel",
60 | 40 : "XCUIElementTypeSwitch",
61 | 41 : "XCUIElementTypeToggle",
62 | 42 : "XCUIElementTypeLink",
63 | 43 : "XCUIElementTypeImage",
64 | 44 : "XCUIElementTypeIcon",
65 | 45 : "XCUIElementTypeSearchField",
66 | 46 : "XCUIElementTypeScrollView",
67 | 47 : "XCUIElementTypeScrollBar",
68 | 48 : "XCUIElementTypeStaticText",
69 | 49 : "XCUIElementTypeTextField",
70 | 50 : "XCUIElementTypeSecureTextField",
71 | 51 : "XCUIElementTypeDatePicker",
72 | 52 : "XCUIElementTypeTextView",
73 | 53 : "XCUIElementTypeMenu",
74 | 54 : "XCUIElementTypeMenuItem",
75 | 55 : "XCUIElementTypeMenuBar",
76 | 56 : "XCUIElementTypeMenuBarItem",
77 | 57 : "XCUIElementTypeMap",
78 | 58 : "XCUIElementTypeWebView",
79 | 59 : "XCUIElementTypeIncrementArrow",
80 | 60 : "XCUIElementTypeDecrementArrow",
81 | 61 : "XCUIElementTypeTimeline",
82 | 62 : "XCUIElementTypeRatingIndicator",
83 | 63 : "XCUIElementTypeValueIndicator",
84 | 64 : "XCUIElementTypeSplitGroup",
85 | 65 : "XCUIElementTypeSplitter",
86 | 66 : "XCUIElementTypeRelevanceIndicator",
87 | 67 : "XCUIElementTypeColorWell",
88 | 68 : "XCUIElementTypeHelpTag",
89 | 69 : "XCUIElementTypeMatte",
90 | 70 : "XCUIElementTypeDockItem",
91 | 71 : "XCUIElementTypeRuler",
92 | 72 : "XCUIElementTypeRulerMarker",
93 | 73 : "XCUIElementTypeGrid",
94 | 74 : "XCUIElementTypeLevelIndicator",
95 | 75 : "XCUIElementTypeCell",
96 | 76 : "XCUIElementTypeLayoutArea",
97 | 77 : "XCUIElementTypeLayoutItem",
98 | 78 : "XCUIElementTypeHandle",
99 | 79 : "XCUIElementTypeStepper",
100 | 80 : "XCUIElementTypeTab"]
101 |
102 | stringElementMapping = [String:UInt]()
103 | for (key, value) in elementStringMapping {
104 | stringElementMapping[value] = key
105 | }
106 | }
107 |
108 | func elementTypeWithTypeName(_ typeName:String) -> XCUIElement.ElementType {
109 | return XCUIElement.ElementType(rawValue: stringElementMapping[typeName]!)!
110 | }
111 |
112 | func stringWithElementType(_ elementType:XCUIElement.ElementType) -> String {
113 | return elementStringMapping[elementType.rawValue]!
114 | }
115 |
116 | func shortStringWithElementType(_ elementType:XCUIElement.ElementType) -> String {
117 | return stringWithElementType(elementType).replacingOccurrences(of: "XCUIElementType", with: "")
118 | }
119 |
120 | }
121 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/Server/XCTestWDController.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestCommandHandler.swift
3 | // XCTestWebdriver
4 | //
5 | // Created by zhaoy on 21/4/17.
6 | // Copyright © 2017 XCTestWebdriver. All rights reserved.
7 | //
8 |
9 | import Swifter
10 |
11 | class RequestRoute: Hashable, Equatable {
12 |
13 | internal var path:String!
14 | internal var verb:String!
15 | internal var requiresSession:Bool
16 |
17 | init(_ path:String , _ verb:String = "GET", _ requiresSession:Bool = true) {
18 | self.path = path
19 | self.verb = verb
20 | self.requiresSession = requiresSession
21 | }
22 |
23 | public var hashValue: Int {
24 | get {
25 | return "\(path)_\(verb)_\(requiresSession)".hashValue
26 | }
27 | }
28 |
29 | public static func ==(lhs: RequestRoute, rhs: RequestRoute) -> Bool {
30 | return lhs.path == rhs.path && lhs.verb == rhs.verb && lhs.requiresSession == rhs.requiresSession
31 | }
32 | }
33 |
34 | typealias RoutingCall = ((Swifter.HttpRequest) -> Swifter.HttpResponse)
35 |
36 | internal protocol Controller {
37 |
38 | static func routes() -> [(RequestRoute, RoutingCall)]
39 |
40 | static func shouldRegisterAutomatically() -> Bool
41 |
42 | }
43 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/Server/XCTestWDDispatch.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestWDDispatch.swift
3 | // XCTestWD
4 | //
5 | // Created by zhaoy on 25/4/17.
6 | // Copyright © 2017 XCTestWD. All rights reserved.
7 | //
8 |
9 | import Foundation
10 | import Swifter
11 |
12 | //MARK: synchronous execution on main
13 | func SyncOnMain(_ executionBlock:(()->(HttpResponse))!) -> HttpResponse {
14 | var response: HttpResponse = HttpResponse.internalServerError
15 | DispatchQueue.main.sync {
16 | response = executionBlock()
17 | }
18 | return response
19 | }
20 |
21 | func RouteOnMain(_ routingCall:@escaping RoutingCall) -> RoutingCall {
22 | return { (request: HttpRequest) -> HttpResponse in
23 | var response:HttpResponse = HttpResponse.internalServerError
24 | DispatchQueue.main.sync {
25 | response = routingCall(request)
26 | }
27 | return response
28 | }
29 | }
30 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/Server/XCTestWDFailureProofTestCase.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestWDFailureProofTestCase.swift
3 | // XCTestWD
4 | //
5 | // Created by SamuelZhaoY on 3/10/18.
6 | // Copyright © 2018 XCTestWD. All rights reserved.
7 | //
8 |
9 | import Foundation
10 | import XCTest
11 |
12 | open class XCTestWDFailureProofTest : XCTestCase
13 | {
14 | override open func setUp() {
15 | super.setUp()
16 | continueAfterFailure = true;
17 | internalImplementation = XCTestWDImplementationFailureHoldingProxy.proxy(with: self.internalImplementation)
18 | }
19 |
20 | override open func recordFailure(withDescription description: String, inFile filePath: String, atLine lineNumber: Int, expected: Bool) {
21 | print("catching internal failure: \(description) in file: \(filePath) at line: \(lineNumber)")
22 | }
23 | }
24 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/Server/XCTestWDMonkey.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestWDMonkey.swift
3 | // XCTestWD
4 | //
5 | // Created by zhangzhao on 2017/8/29.
6 | // Copyright © 2017年 FastMonkey. All rights reserved.
7 |
8 |
9 | import Foundation
10 |
11 | public class XCTestWDMonkey {
12 | public init() {
13 |
14 | }
15 | public func startMonkey() -> Int {
16 |
17 | let bundleID = "com.pandatv.test.meizi"
18 |
19 | var app : XCUIApplication!
20 | var session : XCTestWDSession!
21 | let path :String? = nil
22 | app = XCUIApplication.init(privateWithPath: path, bundleID: bundleID)!
23 | app!.launch()
24 |
25 | if app != nil {
26 | session = XCTestWDSession.sessionWithApplication(app!)
27 | XCTestWDSessionManager.singleton.mountSession(session)
28 | try? session.resolve()
29 | }
30 |
31 | if app?.processID == 0 {
32 | return -1
33 | }
34 |
35 | sleep(4)
36 | NSLog("XCTestWDSetup->start fastmonkey<-XCTestWDSetup")
37 |
38 | _ = app.descendants(matching: .any).element(boundBy: 0).frame
39 | let monkey = Monkey(frame: app.frame)
40 | monkey.addDefaultXCTestPrivateActions()
41 | monkey.addXCTestTapAlertAction(interval: 100, application: app)
42 | monkey.addXCTestCheckCurrentApp(interval: 10, application: app)
43 | //monkey.addXCTestAppLogin(interval: 50, application: app)
44 | monkey.monkeyAround()
45 | RunLoop.main.run()
46 | return 0
47 | }
48 |
49 | }
50 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/Server/XCTestWDServer.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestWebDriverServer.swift
3 | // XCTestWebdriver
4 | //
5 | // Created by zhaoy on 21/4/17.
6 | // Copyright © 2017 XCTestWebdriver. All rights reserved.
7 | //
8 |
9 | import Foundation
10 | import Swifter
11 | import CocoaLumberjackSwift
12 |
13 | struct XCTestWDDebugInfo {
14 | static let DebugLogPrefix = "XCTestWD-Debug-Info: \n"
15 | }
16 |
17 | public class XCTestWDServer {
18 |
19 | private let server = HttpServer()
20 |
21 | public init() {
22 | NSLog("initializing wd server")
23 | NSLog("check log dir @:\( NSSearchPathForDirectoriesInDomains(FileManager.SearchPathDirectory.documentDirectory, FileManager.SearchPathDomainMask.userDomainMask, true) )")
24 | setupLog()
25 | }
26 |
27 | public func startServer() {
28 | do {
29 | try server.start(fetchPort())
30 | registerRouters()
31 |
32 | NSLog("\(Bundle.main.bundleIdentifier!)")
33 | NSLog("XCTestWDSetup->http://localhost:\(try! server.port())<-XCTestWDSetup")
34 |
35 | RunLoop.main.run()
36 | } catch {
37 | NSLog("Server start error: \(error)")
38 | }
39 | }
40 |
41 | public func stopServer() {
42 | server.stop()
43 | }
44 |
45 | private func setupLog() {
46 | DDLog.add(DDTTYLogger.sharedInstance)
47 | DDLog.add(DDASLLogger.sharedInstance)
48 |
49 | let paths = NSSearchPathForDirectoriesInDomains(FileManager.SearchPathDirectory.documentDirectory, FileManager.SearchPathDomainMask.userDomainMask, true)
50 | let logDir = "\(paths[0])/Logs"
51 | let ddLogFileManager : DDLogFileManagerDefault = DDLogFileManagerDefault.init(logsDirectory: logDir)
52 | let fileLogger: DDFileLogger = DDFileLogger.init(logFileManager: ddLogFileManager)
53 | fileLogger.rollingFrequency = TimeInterval(60*60*24)
54 | fileLogger.logFileManager.maximumNumberOfLogFiles = 7
55 | DDLog.add(fileLogger)
56 | DDLogError("\(XCTestWDDebugInfo.DebugLogPrefix)setup debug log")
57 | }
58 |
59 | private func registerRouters() {
60 |
61 | var controllers = [Controller]()
62 |
63 | controllers.append(XCTestWDAlertController())
64 | controllers.append(XCTestWDElementController())
65 | controllers.append(XCTestWDScreenshotController())
66 | controllers.append(XCTestWDSessionController())
67 | controllers.append(XCTestWDSourceController())
68 | controllers.append(XCTestWDTitleController())
69 | controllers.append(XCTestWDElementController())
70 | controllers.append(XCTestWDWindowController())
71 | controllers.append(XCTestWDUrlController())
72 |
73 | for controller in controllers {
74 | let routes = Swift.type(of: controller).routes()
75 | for i in 0...routes.count - 1 {
76 | let (router, requestHandler) = routes[i]
77 | var routeMethod: HttpServer.MethodRoute?
78 |
79 | switch router.verb {
80 | case "post","POST":
81 | routeMethod = server.POST
82 | break
83 | case "get","GET":
84 | routeMethod = server.GET
85 | break
86 | case "put", "PUT":
87 | routeMethod = server.PUT
88 | break
89 | case "delete", "DELETE":
90 | routeMethod = server.DELETE
91 | break
92 | case "update", "UPDATE":
93 | routeMethod = server.UPDATE
94 | break
95 | default:
96 | routeMethod = nil
97 | break
98 | }
99 |
100 | routeMethod?[router.path] = RouteOnMain(requestHandler)
101 | }
102 | }
103 | }
104 |
105 | private func fetchPort() -> in_port_t {
106 |
107 | let arguments = ProcessInfo.processInfo.arguments
108 | let index = arguments.index(of: "--port")
109 | var startingPort:Int = Int(portNumber())
110 | if index != nil {
111 | if index! != NSNotFound || index! < arguments.count - 1{
112 | startingPort = Int(arguments[index!+1])!
113 | }
114 | }
115 |
116 | var (isValid, _) = checkTcpPortForListen(port: in_port_t(startingPort))
117 | while isValid == false {
118 | startingPort = startingPort + 1
119 | (isValid, _) = checkTcpPortForListen(port: in_port_t(startingPort))
120 | }
121 |
122 | return in_port_t(startingPort)
123 | }
124 |
125 | //MARK: Check Port is occupied
126 | func checkTcpPortForListen(port: in_port_t) -> (Bool, descr: String){
127 |
128 | let socketFileDescriptor = socket(AF_INET, SOCK_STREAM, 0)
129 | if socketFileDescriptor == -1 {
130 | return (false, "SocketCreationFailed, \(descriptionOfLastError())")
131 | }
132 |
133 | var addr = sockaddr_in()
134 | addr.sin_len = __uint8_t(MemoryLayout.size)
135 | addr.sin_family = sa_family_t(AF_INET)
136 | addr.sin_port = Int(OSHostByteOrder()) == OSLittleEndian ? _OSSwapInt16(port) : port
137 | addr.sin_addr = in_addr(s_addr: inet_addr("0.0.0.0"))
138 | addr.sin_zero = (0, 0, 0, 0, 0, 0, 0, 0)
139 | var bind_addr = sockaddr()
140 | memcpy(&bind_addr, &addr, Int(MemoryLayout.size))
141 |
142 | if bind(socketFileDescriptor, &bind_addr, socklen_t(MemoryLayout.size)) == -1 {
143 | let details = descriptionOfLastError()
144 | release(socket: socketFileDescriptor)
145 | return (false, "\(port), BindFailed, \(details)")
146 | }
147 | if listen(socketFileDescriptor, SOMAXCONN ) == -1 {
148 | let details = descriptionOfLastError()
149 | release(socket: socketFileDescriptor)
150 | return (false, "\(port), ListenFailed, \(details)")
151 | }
152 | release(socket: socketFileDescriptor)
153 | return (true, "\(port) is free for use")
154 | }
155 |
156 | func release(socket: Int32) {
157 | _ = Darwin.shutdown(socket, SHUT_RDWR)
158 | close(socket)
159 | }
160 |
161 | func descriptionOfLastError() -> String {
162 | return "Error: \(errno)"
163 | }
164 | }
165 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWD/XCTestWD.h:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestWD.h
3 | // XCTestWD
4 | //
5 | // Created by zhaoy on 22/02/2018.
6 | // Copyright © 2018 XCTestWD. All rights reserved.
7 | //
8 |
9 | #import
10 |
11 | //! Project version number for XCTestWD.
12 | FOUNDATION_EXPORT double XCTestWDVersionNumber;
13 |
14 | //! Project version string for XCTestWD.
15 | FOUNDATION_EXPORT const unsigned char XCTestWDVersionString[];
16 |
17 | //! Export debug level
18 | #define LOG_LEVEL_DEF ddLogLevel
19 |
20 | // In this header, you should import all the public headers of your framework using statements like #import
21 |
22 | #import
23 | #import
24 | #import
25 | #import
26 | #import
27 | #import
28 | #import
29 | #import
30 | #import
31 | #import
32 | #import
33 | #import
34 | #import
35 | #import
36 | #import
37 | #import
38 | #import
39 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWDUITests/Info.plist:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | UIFileSharingEnabled
6 |
7 | CFBundleDevelopmentRegion
8 | en
9 | CFBundleExecutable
10 | $(EXECUTABLE_NAME)
11 | CFBundleIdentifier
12 | $(PRODUCT_BUNDLE_IDENTIFIER)
13 | CFBundleInfoDictionaryVersion
14 | 6.0
15 | CFBundleName
16 | $(PRODUCT_NAME)
17 | CFBundlePackageType
18 | BNDL
19 | CFBundleShortVersionString
20 | 1.0
21 | CFBundleVersion
22 | 1
23 |
24 |
25 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWDUITests/XCTestWDRunner.swift:
--------------------------------------------------------------------------------
1 | //
2 | // testUITests.swift
3 | // testUITests
4 | //
5 | // Created by xdf on 14/04/2017.
6 | // Copyright © 2017 xdf. All rights reserved.
7 | //
8 |
9 | import XCTest
10 | import Swifter
11 | import XCTestWD
12 |
13 | public class XCTextWDRunner: XCTestWDFailureProofTest {
14 | var server: XCTestWDServer?
15 | var monkey: XCTestWDMonkey?
16 | override public func setUp() {
17 | super.setUp()
18 | continueAfterFailure = false
19 | XCTestWDSessionManager.singleton.clearAll()
20 | XCUIDevice.shared.press(XCUIDevice.Button.home)
21 | sleep(2)
22 |
23 | NotificationCenter.default.addObserver(self,
24 | selector: #selector(terminate(notification:)),
25 | name: NSNotification.Name(rawValue: "XCTestWDSessionShutDown"),
26 | object: nil)
27 | }
28 |
29 | override public func tearDown() {
30 | super.tearDown()
31 | XCUIDevice.shared.press(XCUIDevice.Button.home)
32 | XCUIDevice.shared.press(XCUIDevice.Button.home)
33 | XCTestWDSessionManager.singleton.clearAll()
34 | }
35 |
36 | func testRunner() {
37 | self.monkey = XCTestWDMonkey()
38 | _ = self.monkey?.startMonkey()
39 |
40 | }
41 |
42 | // func testMultipleApps() {
43 | //
44 | // let settingsApp = XCUIApplication(bundleIdentifier: "com.bytedance.ee.microapp.demo")
45 | // settingsApp.launch()
46 | // sleep(5)
47 | // settingsApp.terminate()
48 | //
49 | // print("lalalalalala:\(settingsApp.state)")
50 | //
51 | // }
52 |
53 | @objc func terminate(notification: NSNotification) {
54 | self.server?.stopServer();
55 | NSLog("XCTestWDTearDown->Session Reset")
56 | assert(false, "")
57 | }
58 | }
59 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWDUnitTest/ControllerTests/XCTestWDScreenShotControllerTest.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestWDScreenShotControllerTest.swift
3 | // XCTestWDUnitTest
4 | //
5 | // Created by SamuelZhaoY on 6/5/18.
6 | // Copyright © 2018 XCTestWD. All rights reserved.
7 | //
8 |
9 | import XCTest
10 | import Nimble
11 | @testable import XCTestWD
12 | @testable import Swifter
13 |
14 | class XCTestWDScreenShotControllerTest: XCTestWDUnitTestBase {
15 |
16 | func testScreenShotRetrieve() {
17 | let request = Swifter.HttpRequest.init()
18 | let response = XCTestWDScreenshotController.getScreenshot(request: request)
19 | let contentJSON = XCTestWDUnitTestBase.getResponseData(response)
20 | expect(contentJSON["status"].int).to(equal(WDStatus.Success.rawValue))
21 | }
22 |
23 | }
24 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWDUnitTest/ControllerTests/XCTestWDSourceControllerTests.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestWDSourceControllerTests.swift
3 | // XCTestWDUnitTest
4 | //
5 | // Created by SamuelZhaoY on 6/5/18.
6 | // Copyright © 2018 XCTestWD. All rights reserved.
7 | //
8 |
9 | import XCTest
10 | import Nimble
11 | import SwiftyJSON
12 | @testable import XCTestWD
13 | @testable import Swifter
14 |
15 | class XCTestWDSourceControllerTests: XCTestWDUnitTestBase {
16 |
17 | func testSourceRetrieve() {
18 | let request = Swifter.HttpRequest.init()
19 | let session = XCTestWDSessionManager.singleton.checkDefaultSession()
20 | XCTestWDSessionManager.singleton.mountSession(session)
21 | request.params["sessionId"] = session.identifier
22 |
23 | // case 1. test source in home panel, full amount of elements available.
24 | XCUIDevice.shared.press(XCUIDevice.Button.home)
25 | var response = XCTestWDSourceController.source(request: request)
26 | var contentJSON = XCTestWDUnitTestBase.getResponseData(response)
27 | expect(contentJSON["status"].int).to(equal(WDStatus.Success.rawValue))
28 |
29 | // case 2. test source in web app.
30 | request.body = [UInt8]((try? JSON(["value":"//*[@name=\"Safari\"]","using":"xpath"]).rawData()) ?? Data())
31 | response = XCTestWDElementController.findElement(request: request)
32 | expect(contentJSON["status"].int).to(equal(WDStatus.Success.rawValue))
33 | var jsonResponse = XCTestWDUnitTestBase.getResponseData(response)
34 | expect(jsonResponse["value"]["ELEMENT"]).toNot(beNil())
35 |
36 | // click and enter safari
37 | request.path = "/element/\(jsonResponse["value"]["ELEMENT"])"
38 | response = XCTestWDElementController.click(request: request)
39 | expect(contentJSON["status"].int).to(equal(WDStatus.Success.rawValue))
40 |
41 | response = XCTestWDSourceController.sourceWithoutSession(request: request)
42 | contentJSON = XCTestWDUnitTestBase.getResponseData(response)
43 | expect(contentJSON["status"].int).to(equal(WDStatus.Success.rawValue))
44 |
45 | // case 3. test source in native app.
46 | XCUIDevice.shared.press(XCUIDevice.Button.home)
47 | // sliding to first panel
48 | XCUIDevice.shared.press(XCUIDevice.Button.home)
49 |
50 | request.body = [UInt8]((try? JSON(["value":"//*[@name=\"Messages\"]","using":"xpath"]).rawData()) ?? Data())
51 | response = XCTestWDElementController.findElement(request: request)
52 | expect(contentJSON["status"].int).to(equal(WDStatus.Success.rawValue))
53 | jsonResponse = XCTestWDUnitTestBase.getResponseData(response)
54 | expect(jsonResponse["value"]["ELEMENT"]).toNot(beNil())
55 |
56 | // click and enter safari
57 | request.path = "/element/\(jsonResponse["value"]["ELEMENT"])"
58 | response = XCTestWDElementController.click(request: request)
59 | expect(contentJSON["status"].int).to(equal(WDStatus.Success.rawValue))
60 |
61 | response = XCTestWDSourceController.sourceWithoutSession(request: request)
62 | contentJSON = XCTestWDUnitTestBase.getResponseData(response)
63 | expect(contentJSON["status"].int).to(equal(WDStatus.Success.rawValue))
64 | }
65 | }
66 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWDUnitTest/ControllerTests/XCTestWDTitleControllerTests.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestWDTitleControllerTests.swift
3 | // XCTestWDUnitTest
4 | //
5 | // Created by SamuelZhaoY on 2/4/18.
6 | // Copyright © 2018 XCTestWD. All rights reserved.
7 | //
8 |
9 | import XCTest
10 | import Nimble
11 | @testable import XCTestWD
12 | @testable import Swifter
13 |
14 | class XCTestWDTitleControllerTests: XCTestWDUnitTestBase {
15 |
16 | func testTitleRetrieve() {
17 | let request = Swifter.HttpRequest.init()
18 | let response = XCTestWDTitleController.title(request: request)
19 | let contentJSON = XCTestWDUnitTestBase.getResponseData(response)
20 | expect(contentJSON["status"].int).to(equal(WDStatus.Success.rawValue))
21 | }
22 |
23 | }
24 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWDUnitTest/ControllerTests/XCTestWDUrlControllerTests.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestWDUrlController.swift
3 | // XCTestWDUnitTest
4 | //
5 | // Created by SamuelZhaoY on 2/4/18.
6 | // Copyright © 2018 XCTestWD. All rights reserved.
7 | //
8 |
9 | import XCTest
10 | import Nimble
11 | @testable import XCTestWD
12 | @testable import Swifter
13 |
14 | class XCTestWDUrlControllerTests: XCTestWDUnitTestBase {
15 |
16 | func testUrlController() {
17 | let request = Swifter.HttpRequest.init()
18 | let response = XCTestWDUrlController.url(request: request)
19 | response.shouldBeSuccessful()
20 | }
21 |
22 | func testGetUrlController() {
23 | let request = Swifter.HttpRequest.init()
24 | let response = XCTestWDUrlController.getUrl(request: request)
25 | response.shouldBeSuccessful()
26 | }
27 |
28 | func testForwardUrlController() {
29 | let request = Swifter.HttpRequest.init()
30 | let response = XCTestWDUrlController.forward(request: request)
31 | response.shouldBeSuccessful()
32 | }
33 |
34 | func testRefreshUrlController() {
35 | let request = Swifter.HttpRequest.init()
36 | let response = XCTestWDUrlController.refresh(request: request)
37 | response.shouldBeSuccessful()
38 | }
39 |
40 | func testBack() {
41 | let request = Swifter.HttpRequest.init()
42 | let response = XCTestWDUrlController.back(request: request)
43 | let contentJSON = XCTestWDUnitTestBase.getResponseData(response)
44 | expect(contentJSON["status"].int).to(equal(WDStatus.ElementIsNotSelectable.rawValue))
45 | }
46 | }
47 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWDUnitTest/ControllerTests/XCTestWDWindowControllerTests.swift:
--------------------------------------------------------------------------------
1 |
2 | //
3 | // XCTestWDWindowControllerTests.swift
4 | // XCTestWDUnitTest
5 | //
6 | // Created by SamuelZhaoY on 2/4/18.
7 | // Copyright © 2018 XCTestWD. All rights reserved.
8 | //
9 |
10 | import XCTest
11 | import Nimble
12 | @testable import XCTestWD
13 | @testable import Swifter
14 |
15 | class XCTestWDWindowControllerTests: XCTestWDUnitTestBase {
16 |
17 | func testWindowSize() {
18 | let request = Swifter.HttpRequest.init()
19 | let response = XCTestWDWindowController.getWindowSize(request: request)
20 | response.shouldBeSuccessful()
21 | }
22 |
23 | }
24 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWDUnitTest/Info.plist:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | CFBundleDevelopmentRegion
6 | $(DEVELOPMENT_LANGUAGE)
7 | CFBundleExecutable
8 | $(EXECUTABLE_NAME)
9 | CFBundleIdentifier
10 | $(PRODUCT_BUNDLE_IDENTIFIER)
11 | CFBundleInfoDictionaryVersion
12 | 6.0
13 | CFBundleName
14 | $(PRODUCT_NAME)
15 | CFBundlePackageType
16 | BNDL
17 | CFBundleShortVersionString
18 | 1.0
19 | CFBundleVersion
20 | 1
21 |
22 |
23 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWDUnitTest/XCTestWDSessionTest.swift:
--------------------------------------------------------------------------------
1 | //
2 | // XCTestWDUnitTest.swift
3 | // XCTestWDUnitTest
4 | //
5 | // Created by SamuelZhaoY on 31/3/18.
6 | // Copyright © 2018 XCTestWD. All rights reserved.
7 | //
8 |
9 | import XCTest
10 | import Swifter
11 | import Nimble
12 | @testable import XCTestWD
13 |
14 | class XCTestWDSessionTest: XCTestWDUnitTestBase {
15 |
16 | func testApplicationLaunch() {
17 | XCTAssert(self.springApplication != nil, "application should not be nil")
18 | }
19 |
20 | func testFetchSystemApplicaiton() {
21 | let systemApplication = (XCAXClient_iOS.sharedClient() as! XCAXClient_iOS).systemApplication()
22 | let springBoardApplication = XCTestWDApplication.create(byPID: pid_t(((systemApplication as! NSObject).value(forKey: "processIdentifier") as! NSNumber).intValue))
23 |
24 | XCTAssert(springBoardApplication != nil, "application should not be nil")
25 | }
26 |
27 | func testSessionCreation() {
28 | XCTAssert(self.springApplication?.bundleID == XCTestWDSession.activeApplication()?.bundleID)
29 |
30 | let session = XCTestWDSession.sessionWithApplication(self.springApplication!)
31 | XCTestWDSessionManager.singleton.mountSession(session)
32 |
33 | XCTAssert(XCTestWDSessionManager.singleton.queryAll().keys.count == 1, "key length should be one, containing");
34 | }
35 |
36 | func testSessionDeletion() {
37 | self.testSessionCreation()
38 |
39 | XCTestWDSessionManager.singleton.clearAll();
40 |
41 | XCTAssert(XCTestWDSessionManager.singleton.queryAll().keys.count == 0, "key length shoud be zero")
42 | }
43 |
44 | func testSessionIDDeletion() {
45 | let session = XCTestWDSession.sessionWithApplication(self.springApplication!)
46 | XCTestWDSessionManager.singleton.mountSession(session)
47 |
48 | XCTAssert(XCTestWDSessionManager.singleton.queryAll().keys.count == 1, "key length should be one, containing");
49 |
50 | XCTestWDSessionManager.singleton.deleteSession(session.identifier)
51 | XCTAssert(XCTestWDSessionManager.singleton.queryAll().keys.count == 0, "key length shoud be zero")
52 | }
53 |
54 | func testElementCache() {
55 | let uuid = XCTestWDSessionManager.commonCache.storeElement(self.springApplication!)
56 | expect(XCTestWDSessionManager.commonCache.elementForUUID(uuid)).to(equal(self.springApplication!))
57 | }
58 | }
59 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/XCTestWDUnitTest/XCTestWDUnitTestBase.swift:
--------------------------------------------------------------------------------
1 |
2 | //
3 | // XCTestWDUnitTestBase.swift
4 | // XCTestWDUnitTest
5 | //
6 | // Created by SamuelZhaoY on 1/4/18.
7 | // Copyright © 2018 XCTestWD. All rights reserved.
8 | //
9 |
10 | import XCTest
11 | import SwiftyJSON
12 | import Nimble
13 | @testable import XCTestWD
14 | @testable import Swifter
15 |
16 | class XCTestWDUnitTestBase: XCTestCase {
17 |
18 | var springApplication: XCUIApplication?
19 |
20 | override func setUp() {
21 | super.setUp()
22 | continueAfterFailure = false
23 | XCTestWDSessionManager.singleton.clearAll()
24 | self.springApplication = XCTestWDApplication.activeApplication()
25 | XCUIDevice.shared.press(XCUIDevice.Button.home)
26 | sleep(2)
27 | }
28 |
29 | override func tearDown() {
30 | super.tearDown()
31 | XCUIDevice.shared.press(XCUIDevice.Button.home)
32 | XCUIDevice.shared.press(XCUIDevice.Button.home)
33 | XCTestWDSessionManager.singleton.clearAll()
34 | }
35 |
36 | static func getResponseData(_ response: Swifter.HttpResponse) -> JSON {
37 | switch response {
38 | case .ok(let body):
39 | switch body {
40 | case .text(let content):
41 | if let dataFromString = content.data(using: .utf8, allowLossyConversion: false) {
42 | return (try? JSON(data: dataFromString)) ?? JSON.init(stringLiteral: "")
43 | } else {
44 | break
45 | }
46 | case .html( _):
47 | return JSON(["status": 0])
48 | default:
49 | break
50 | }
51 | default:
52 | break
53 | }
54 |
55 | return JSON.init("")
56 | }
57 | }
58 |
59 | extension HttpResponse {
60 | func shouldBeSuccessful()
61 | {
62 | let jsonContent = XCTestWDUnitTestBase.getResponseData(self)
63 | expect(jsonContent["status"]).to(equal(0))
64 | expect(self.statusCode()).to(equal(200))
65 | }
66 | }
67 |
68 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/curlTests.sh:
--------------------------------------------------------------------------------
1 |
2 | export JSON_HEADER='-H "Content-Type:application/json"'
3 | export DEVICE_URL='http://127.0.0.1:8001'
4 |
5 | TagHead() {
6 | echo "\n#### $1 ####"
7 | }
8 |
9 | #Session: create session
10 |
11 | TagHead "Create Session"
12 |
13 | curl -X POST $JSON_HEADER \
14 | -d "{\"desiredCapabilities\":{\"deviceName\":\"iPhone 8\",\"platformName\":\"iOS\", \"bundleId\":\"com.apple.mobilesafari\",\"autoAcceptAlerts\":false}}" \
15 | $DEVICE_URL/wd/hub/session \
16 |
17 | ### Read session as input for next stage testing
18 |
19 | echo "\n\ninput the sessionID generated:\n"
20 | read sessionID
21 |
22 | #Session: query sessions
23 |
24 | TagHead "Query Session"
25 |
26 | curl -X GET $JSON_HEADER \
27 | $DEVICE_URL/wd/hub/sessions \
28 |
29 | #Session: checkon source
30 |
31 | curl -X POST $JSON_HEADER \
32 | -d "{\"using\":\"xpath\",\"value\":\"//XCUIElementTypeTextField[1]\"}" \
33 | $DEVICE_URL/wd/hub/session/$sessionID/elements \
34 |
35 | echo "\n\ninput the elementID generated:\n"
36 | read elementID
37 |
38 | curl -X POST $JSON_HEADER \
39 | $DEVICE_URL/wd/hub/session/$sessionID/tap/$elementID \
40 |
41 | TagHead "Check Source"
42 |
43 | curl -X GET $JSON_HEADER \
44 | $DEVICE_URL/wd/hub/source \
45 |
46 | TagHead "Press Home"
47 |
48 | curl -X POST $JSON_HEADER \
49 | $DEVICE_URL/wd/hub/session/$sessionID/homeScreen \
50 |
51 | TagHead "Title"
52 |
53 | curl -X GET $JSON_HEADER \
54 | $DEVICE_URL/wd/hub/session/$sessionID/title \
55 |
56 | TagHead "Check"
57 |
58 | curl -X GET $JSON_HEADER \
59 | $DEVICE_URL/wd/hub/session/$sessionID/title \
60 |
61 | TagHead "Trigger touch event by x & y"
62 |
63 | curl -X POST $JSON_HEADER \
64 | -d "{\"using\":\"xpath\",\"value\":\"//*[@name="Messages"]\"}" \
65 | $DEVICE_URL/wd/hub/session/$sessionID/elements \
66 |
67 | curl -X POST $JSON_HEADER \
68 | -d "{\"using\":\"predicate string\",\"value\":\"label CONTAINS[c] 'Messages'\"}" \
69 | $DEVICE_URL/wd/hub/session/$sessionID/elements \
70 |
71 | echo "\n\ninput the elementID generated:\n"
72 | read elementID
73 |
74 | curl -X POST $JSON_HEADER \
75 | $DEVICE_URL/wd/hub/session/$sessionID/tap/$elementID \
76 |
--------------------------------------------------------------------------------
/XCTestWD-master/XCTestWD/libxml2/libxml2-fuzi.h:
--------------------------------------------------------------------------------
1 | #import
2 | #import
3 | #import
4 | #import
5 | #import
6 |
--------------------------------------------------------------------------------
/XCTestWD-master/index.html:
--------------------------------------------------------------------------------
1 | XCTestWD page coming soon
2 |
--------------------------------------------------------------------------------
/XCTestWD-master/index.js:
--------------------------------------------------------------------------------
1 | 'use strict';
2 |
3 | module.exports = require('./lib/xctest-client');
4 |
--------------------------------------------------------------------------------
/XCTestWD-master/lib/helper.js:
--------------------------------------------------------------------------------
1 | 'use strict';
2 |
3 | const macacaUtils = require('macaca-utils');
4 | const childProcess = require('child_process');
5 |
6 | var _ = macacaUtils.merge({}, macacaUtils);
7 |
8 | _.sleep = function(ms) {
9 | return new Promise(resolve => {
10 | setTimeout(resolve, ms);
11 | });
12 | };
13 |
14 | _.retry = function(func, interval, num) {
15 | return new Promise((resolve, reject) => {
16 | func().then(resolve, err => {
17 | if (num > 0 || typeof num === 'undefined') {
18 | _.sleep(interval).then(() => {
19 | resolve(_.retry(func, interval, num - 1));
20 | });
21 | } else {
22 | reject(err);
23 | }
24 | });
25 | });
26 | };
27 |
28 | _.waitForCondition = function(func, wait/* ms*/, interval/* ms*/) {
29 | wait = wait || 5000;
30 | interval = interval || 500;
31 | let start = Date.now();
32 | let end = start + wait;
33 |
34 | const fn = function() {
35 | return new Promise((resolve, reject) => {
36 | const continuation = (res, rej) => {
37 | let now = Date.now();
38 |
39 | if (now < end) {
40 | res(_.sleep(interval).then(fn));
41 | } else {
42 | rej(`Wait For Condition timeout ${wait}`);
43 | }
44 | };
45 | func().then(isOk => {
46 |
47 | if (isOk) {
48 | resolve();
49 | } else {
50 | continuation(resolve, reject);
51 | }
52 | }).catch(() => {
53 | continuation(resolve, reject);
54 | });
55 | });
56 | };
57 | return fn();
58 | };
59 |
60 | _.escapeString = function(str) {
61 | return str
62 | .replace(/[\\]/g, '\\\\')
63 | .replace(/[\/]/g, '\\/')
64 | .replace(/[\b]/g, '\\b')
65 | .replace(/[\f]/g, '\\f')
66 | .replace(/[\n]/g, '\\n')
67 | .replace(/[\r]/g, '\\r')
68 | .replace(/[\t]/g, '\\t')
69 | .replace(/[\"]/g, '\\"')
70 | .replace(/\\'/g, "\\'");
71 | };
72 |
73 | _.exec = function(cmd, opts) {
74 | return new Promise((resolve, reject) => {
75 | childProcess.exec(cmd, _.merge({
76 | maxBuffer: 1024 * 512,
77 | wrapArgs: false
78 | }, opts || {}), (err, stdout) => {
79 | if (err) {
80 | return reject(err);
81 | }
82 | resolve(_.trim(stdout));
83 | });
84 | });
85 | };
86 |
87 | _.spawn = function() {
88 | var args = Array.prototype.slice.call(arguments);
89 |
90 | return new Promise((resolve, reject) => {
91 | var stdout = '';
92 | var stderr = '';
93 | var child = childProcess.spawn.apply(childProcess, args);
94 |
95 | child.on('error', error => {
96 | reject(error);
97 | });
98 |
99 | child.stdout.on('data', data => {
100 | stdout += data;
101 | });
102 |
103 | child.stderr.on('data', data => {
104 | stderr += data;
105 | });
106 |
107 | child.on('close', code => {
108 | var error;
109 | if (code) {
110 | error = new Error(stderr);
111 | error.code = code;
112 | return reject(error);
113 | }
114 | resolve([stdout, stderr]);
115 | });
116 | });
117 | };
118 |
119 | var Defer = function() {
120 | this._resolve = null;
121 | this._reject = null;
122 | this.promise = new Promise((resolve, reject) => {
123 | this._resolve = resolve;
124 | this._reject = reject;
125 | });
126 | };
127 |
128 | Defer.prototype.resolve = function(data) {
129 | this._resolve(data);
130 | };
131 |
132 | Defer.prototype.reject = function(err) {
133 | this._reject(err);
134 | };
135 |
136 | _.Defer = Defer;
137 |
138 | module.exports = _;
139 |
--------------------------------------------------------------------------------
/XCTestWD-master/lib/logger.js:
--------------------------------------------------------------------------------
1 | 'use strict';
2 |
3 | var logger = require('xlogger');
4 |
5 | module.exports = logger.Logger({
6 | closeFile: true
7 | });
8 |
--------------------------------------------------------------------------------
/XCTestWD-master/lib/proxy.js:
--------------------------------------------------------------------------------
1 | 'use strict';
2 |
3 | const request = require('request');
4 |
5 | const _ = require('./helper');
6 | const logger = require('./logger');
7 |
8 | class XCProxy {
9 | constructor(options) {
10 | Object.assign(this, {
11 | scheme: 'http',
12 | proxyHost: '127.0.0.1',
13 | proxyPort: 8001,
14 | urlBase: 'wd/hub',
15 | sessionId: null,
16 | originSessionId: null
17 | }, options);
18 | }
19 |
20 | handleNewUrl(url) {
21 | const sessionReg = /\/session\/([^\/]+)/;
22 | const wdSessionReg = new RegExp(`${this.urlBase}\/session\/([^\/]+)`);
23 | url = `${this.scheme}://${this.proxyHost}:${this.proxyPort}${url}`;
24 |
25 | if (sessionReg.test(url) && this.sessionId) {
26 | this.originSessionId = url.match(sessionReg)[1];
27 | url = url.replace(wdSessionReg, `${this.urlBase}/session/${this.sessionId}`);
28 | }
29 | return url;
30 | }
31 |
32 | send(url, method, body) {
33 | return new Promise((resolve, reject) => {
34 | method = method.toUpperCase();
35 | const newUrl = this.handleNewUrl(url);
36 | const retryCount = 10;
37 | const retryInterval = 2000;
38 |
39 | const reqOpts = {
40 | url: newUrl,
41 | method: method,
42 | headers: {
43 | 'Content-type': 'application/json;charset=UTF=8'
44 | },
45 | resolveWithFullResponse: true
46 | };
47 |
48 | if (body && (method.toUpperCase() === 'POST' || method.toUpperCase() === 'PUT')) {
49 | if (typeof body !== 'object') {
50 | body = JSON.parse(body);
51 | }
52 | reqOpts.json = body;
53 | }
54 |
55 | logger.debug(`Proxy: ${url}:${method} to ${newUrl}:${method} with body: ${_.truncate(JSON.stringify(body), {
56 | length: 200
57 | })}`);
58 |
59 | _.retry(() => {
60 | return new Promise((_resolve, _reject) => {
61 | request(reqOpts, (error, res, body) => {
62 | if (error) {
63 | logger.debug(`xctest client proxy error with: ${error}`);
64 | return _reject(error);
65 | }
66 |
67 | if (!body) {
68 | logger.debug('xctest client proxy received no data.');
69 | return _reject('No data received from XCTestWD.');
70 | }
71 |
72 | if (typeof body !== 'object') {
73 | try {
74 | body = JSON.parse(body);
75 | } catch (e) {
76 | logger.debug(`Fail to parse body: ${e}`);
77 | }
78 | }
79 |
80 | if (body && body.sessionId) {
81 | this.sessionId = body.sessionId;
82 | body.sessionId = this.originSessionId;
83 | }
84 |
85 | logger.debug(`Got response with status ${res.statusCode}: ${_.truncate(JSON.stringify(body), {
86 | length: 200
87 | })}`);
88 | _resolve(body);
89 | });
90 |
91 | });
92 | }, retryInterval, retryCount).then(resolve, reject);
93 | });
94 | }
95 | }
96 |
97 | module.exports = XCProxy;
98 |
--------------------------------------------------------------------------------
/XCTestWD-master/lib/xctest-client.js:
--------------------------------------------------------------------------------
1 | 'use strict';
2 |
3 | const url = require('url');
4 | const path = require('path');
5 | const iOSUtils = require('ios-utils');
6 | const EventEmitter = require('events');
7 | const childProcess = require('child_process');
8 |
9 | const _ = require('./helper');
10 | const pkg = require('../package');
11 | const XCProxy = require('./proxy');
12 | const logger = require('./logger');
13 | const XCTestWD = require('./xctestwd');
14 |
15 | const {
16 | detectPort
17 | } = _;
18 | const TEST_URL = pkg.site;
19 | const projectPath = XCTestWD.projectPath;
20 | const SERVER_URL_REG = XCTestWD.SERVER_URL_REG;
21 | const simulatorLogFlag = XCTestWD.simulatorLogFlag;
22 |
23 | class XCTest extends EventEmitter {
24 | constructor(options) {
25 | super();
26 | this.proxy = null;
27 | this.capabilities = null;
28 | this.sessionId = null;
29 | this.device = null;
30 | this.deviceLogProc = null;
31 | this.runnerProc = null;
32 | this.iproxyProc = null;
33 | Object.assign(this, {
34 | proxyHost: '127.0.0.1',
35 | proxyPort: 8001,
36 | urlBase: 'wd/hub'
37 | }, options || {});
38 | this.init();
39 | }
40 |
41 | init() {
42 | this.checkProjectPath();
43 | process.on('uncaughtException', (e) => {
44 | logger.error(`Uncaught Exception: ${e.stack}`);
45 | this.stop();
46 | process.exit(1);
47 | });
48 | process.on('exit', () => {
49 | this.stop();
50 | });
51 | }
52 |
53 | checkProjectPath() {
54 | if (_.isExistedDir(projectPath)) {
55 | logger.debug(`project path: ${projectPath}`);
56 | } else {
57 | logger.error('project path not found');
58 | }
59 | }
60 |
61 | configUrl(str) {
62 | const urlObj = url.parse(str);
63 | this.proxyHost = urlObj.hostname;
64 | this.proxyPort = urlObj.port;
65 | }
66 |
67 | initProxy() {
68 | this.proxy = new XCProxy({
69 | proxyHost: this.proxyHost,
70 | proxyPort: this.proxyPort,
71 | urlBase: this.urlBase
72 | });
73 | }
74 |
75 | * startSimLog() {
76 | const logPath = yield this.startBootstrap();
77 | const logDir = path.resolve(logPath);
78 | return _.retry(() => {
79 | return new Promise((resolve, reject) => {
80 | const logTxtFile = path.join(logDir, '..', 'StandardOutputAndStandardError.txt');
81 | logger.info(`Read simulator log at: ${logTxtFile}`);
82 |
83 | if (!_.isExistedFile(logTxtFile)) {
84 | return reject();
85 | }
86 | let args = `-f -n 0 ${logTxtFile}`.split(' ');
87 | var proc = childProcess.spawn('tail', args, {});
88 | this.deviceLogProc = proc;
89 |
90 | proc.stderr.setEncoding('utf8');
91 | proc.stdout.setEncoding('utf8');
92 |
93 | proc.stdout.on('data', data => {
94 |
95 | // avoid logout long data such as bitmap
96 | if (data.length <= 300 && logger.debugMode) {
97 | // logger.debug(data);
98 | }
99 |
100 | let match = SERVER_URL_REG.exec(data);
101 | if (match) {
102 | const url = match[1];
103 | if (url.startsWith('http://')) {
104 | this.configUrl(url);
105 | resolve();
106 | }
107 | }
108 | });
109 |
110 | proc.stderr.on('data', data => {
111 | logger.debug(data);
112 | });
113 |
114 | proc.stdout.on('error', (err) => {
115 | logger.warn(`simulator log process error with ${err}`);
116 | });
117 |
118 | proc.on('exit', (code, signal) => {
119 | logger.warn(`simulator log process exit with code: ${code}, signal: ${signal}`);
120 | reject();
121 | });
122 | });
123 | }, 1000, Infinity);
124 | }
125 |
126 | * startDeviceLog() {
127 | yield this.startBootstrap();
128 | var proc = childProcess.spawn(iOSUtils.devicelog.binPath, [this.device.deviceId], {});
129 | this.deviceLogProc = proc;
130 |
131 | proc.stderr.setEncoding('utf8');
132 | proc.stdout.setEncoding('utf8');
133 |
134 | return new Promise((resolve, reject) => {
135 | proc.stdout.on('data', data => {
136 |
137 | // avoid logout long data such as bitmap
138 | if (data.length <= 300 && logger.debugMode) {
139 | logger.debug(data);
140 | }
141 |
142 | let match = SERVER_URL_REG.exec(data);
143 | if (match) {
144 | const url = match[1];
145 | if (url.startsWith('http://')) {
146 | this.configUrl(url);
147 | resolve();
148 | }
149 | }
150 | });
151 |
152 | proc.stderr.on('data', data => {
153 | logger.debug(data);
154 | });
155 |
156 | proc.stdout.on('error', (err) => {
157 | logger.warn(`devicelog error with ${err}`);
158 | });
159 |
160 | proc.on('exit', (code, signal) => {
161 | logger.warn(`devicelog exit with code: ${code}, signal: ${signal}`);
162 | reject();
163 | });
164 | });
165 | }
166 |
167 | * startBootstrap() {
168 | return new Promise((resolve, reject) => {
169 | logger.info(`XCTestWD version: ${XCTestWD.version}`);
170 |
171 | var args = `clean test -project ${XCTestWD.projectPath} -scheme XCTestWDUITests -destination id=${this.device.deviceId} XCTESTWD_PORT=${this.proxyPort}`.split(' ');
172 | var env = _.merge({}, process.env, {
173 | XCTESTWD_PORT: this.proxyPort
174 | });
175 |
176 | var proc = childProcess.spawn('xcodebuild', args, {
177 | env: env
178 | });
179 | this.runnerProc = proc;
180 | proc.stderr.setEncoding('utf8');
181 | proc.stdout.setEncoding('utf8');
182 |
183 | proc.stdout.on('data', data => {
184 | // logger.debug(data);
185 | });
186 |
187 | proc.stderr.on('data', data => {
188 | // logger.debug(data);
189 |
190 | if (~data.indexOf(simulatorLogFlag)) {
191 | const list = data.split(simulatorLogFlag);
192 | const res = list[1].trim();
193 | resolve(res);
194 | } else {
195 | logger.debug(`please check project: ${projectPath}`);
196 | }
197 | });
198 |
199 | proc.stdout.on('error', (err) => {
200 | logger.warn(`xctest client error with ${err}`);
201 | logger.debug(`please check project: ${projectPath}`);
202 | });
203 |
204 | proc.on('exit', (code, signal) => {
205 | this.stop();
206 | logger.warn(`xctest client exit with code: ${code}, signal: ${signal}`);
207 | });
208 |
209 | });
210 | }
211 |
212 | * startIproxy() {
213 | let args = [this.proxyPort, this.proxyPort, this.device.deviceId];
214 |
215 | const IOS_USBMUXD_IPROXY = 'iproxy';
216 | const binPath = yield _.exec(`which ${IOS_USBMUXD_IPROXY}`);
217 |
218 | var proc = childProcess.spawn(binPath, args);
219 |
220 | this.iproxyProc = proc;
221 | proc.stderr.setEncoding('utf8');
222 | proc.stdout.setEncoding('utf8');
223 |
224 | proc.stdout.on('data', () => {
225 | });
226 |
227 | proc.stderr.on('data', () => {
228 | // logger.debug(data);
229 | });
230 |
231 | proc.stdout.on('error', (err) => {
232 | logger.warn(`${IOS_USBMUXD_IPROXY} error with ${err}`);
233 | });
234 |
235 | proc.on('exit', (code, signal) => {
236 | logger.warn(`${IOS_USBMUXD_IPROXY} exit with code: ${code}, signal: ${signal}`);
237 | });
238 | }
239 |
240 | * start(caps) {
241 | try {
242 | this.proxyPort = yield detectPort(this.proxyPort);
243 |
244 | this.capabilities = caps;
245 | const xcodeVersion = yield iOSUtils.getXcodeVersion();
246 |
247 | logger.debug(`xcode version: ${xcodeVersion}`);
248 |
249 | var deviceInfo = iOSUtils.getDeviceInfo(this.device.deviceId);
250 |
251 | if (deviceInfo.isRealIOS) {
252 | yield this.startDeviceLog();
253 | yield this.startIproxy();
254 | } else {
255 | yield this.startSimLog();
256 | }
257 |
258 | logger.info(`${pkg.name} start with port: ${this.proxyPort}`);
259 |
260 | this.initProxy();
261 |
262 | if (caps.desiredCapabilities.browserName === 'Safari') {
263 | var promise = this.proxy.send(`/${this.urlBase}/session`, 'POST', {
264 | desiredCapabilities: {
265 | bundleId: 'com.apple.mobilesafari'
266 | }
267 | });
268 | return yield Promise.all([this.device.openURL(TEST_URL), promise]);
269 | } else {
270 | return yield this.proxy.send(`/${this.urlBase}/session`, 'POST', caps);
271 | }
272 | } catch (err) {
273 | logger.debug(`Fail to start xctest: ${err}`);
274 | this.stop();
275 | throw err;
276 | }
277 | }
278 |
279 | stop() {
280 | if (this.deviceLogProc) {
281 | logger.debug(`killing deviceLogProc pid: ${this.deviceLogProc.pid}`);
282 | this.deviceLogProc.kill('SIGKILL');
283 | this.deviceLogProc = null;
284 | }
285 | if (this.runnerProc) {
286 | logger.debug(`killing runnerProc pid: ${this.runnerProc.pid}`);
287 | this.runnerProc.kill('SIGKILL');
288 | this.runnerProc = null;
289 | }
290 |
291 | if (this.iproxyProc) {
292 | logger.debug(`killing iproxyProc pid: ${this.iproxyProc.pid}`);
293 | this.iproxyProc.kill('SIGKILL');
294 | this.iproxyProc = null;
295 | }
296 | }
297 |
298 | sendCommand(url, method, body) {
299 | return this.proxy.send(url, method, body);
300 | }
301 | }
302 |
303 | module.exports = XCTest;
304 | module.exports.XCTestWD = XCTestWD;
305 |
--------------------------------------------------------------------------------
/XCTestWD-master/lib/xctestwd.js:
--------------------------------------------------------------------------------
1 | 'use strict';
2 |
3 | var path = require('path');
4 |
5 | exports.SERVER_URL_REG = /XCTestWDSetup->(.*)<-XCTestWDSetup/;
6 | exports.schemeName = 'XCTestWDUITests';
7 | exports.projectPath = process.env.XCTESTWD_PATH || path.join(__dirname, '..', 'XCTestWD', 'XCTestWD.xcodeproj');
8 | exports.version = require('../package').version;
9 | exports.BUNDLE_ID = 'XCTestWD.XCTestWD';
10 | exports.simulatorLogFlag = 'IDETestOperationsObserverDebug: Writing diagnostic log for test session to:';
11 |
--------------------------------------------------------------------------------
/XCTestWD-master/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "xctestwd",
3 | "version": "1.4.5",
4 | "description": "Swift implementation of WebDriver server for iOS that runs on Simulator/iOS devices.",
5 | "keywords": [
6 | "iOS",
7 | "xctest"
8 | ],
9 | "repository": {
10 | "type": "git",
11 | "url": "git://github.com/macacajs/xctestwd.git"
12 | },
13 | "main": "index.js",
14 | "dependencies": {
15 | "ios-utils": "~1.0.0",
16 | "macaca-doctor": "^2.0.4",
17 | "macaca-utils": "^1.0.0",
18 | "request": "~2.69.0",
19 | "shelljs": "^0.7.8",
20 | "webdriver-dfn-error-code": "~1.0.1",
21 | "xcode": "^0.8.9",
22 | "xctestwd-frameworks-93": "^1.0.0",
23 | "xctestwd-frameworks-94": "^1.0.1",
24 | "xctestwd-frameworks": "^1.0.0",
25 | "xlogger": "~1.0.0"
26 | },
27 | "devDependencies": {
28 | "co-mocha": "*",
29 | "eslint": "^4.13.0",
30 | "eslint-plugin-mocha": "^4.11.0",
31 | "git-contributor": "^1.0.7",
32 | "istanbul": "*",
33 | "mocha": "*",
34 | "pre-commit": "*"
35 | },
36 | "pre-commit": [
37 | "lint"
38 | ],
39 | "scripts": {
40 | "test": "mocha",
41 | "lint": "eslint . --fix",
42 | "install": "node ./scripts/install.js",
43 | "contributor": "git-contributor"
44 | },
45 | "site": "https://macacajs.github.io",
46 | "license": "MIT"
47 | }
48 |
--------------------------------------------------------------------------------
/XCTestWD-master/scripts/aggregate.sh:
--------------------------------------------------------------------------------
1 | #!/bin/bash
2 | set -euo pipefail
3 | IFS=$'\n\t'
4 |
5 | # Sets the target folders and the final framework product.
6 | PROJECT_NAME=XCTestWD
7 | FRAMEWORK_CONFIG=Release
8 | BUILD_TARGET=XCTestWD
9 |
10 | # Install dir will be the final output to the framework.
11 | # The following line create it in the root folder of the current project.
12 | INSTALL_DIR="$SRCROOT/Frameworks/$BUILD_TARGET.framework"
13 |
14 | # Working dir will be deleted after the framework creation.
15 | WORK_DIR="$SRCROOT/build"
16 | DEVICE_DIR="$WORK_DIR/${FRAMEWORK_CONFIG}-iphoneos/$BUILD_TARGET.framework"
17 | SIMULATOR_DIR="$WORK_DIR/${FRAMEWORK_CONFIG}-iphonesimulator/$BUILD_TARGET.framework"
18 | rm -rf "$WORK_DIR"
19 |
20 | echo "Building device..."
21 | xcodebuild -configuration "$FRAMEWORK_CONFIG" -target "$BUILD_TARGET" -sdk iphoneos -project "$PROJECT_NAME.xcodeproj" > /dev/null
22 |
23 | echo "Building simulator..."
24 | xcodebuild -configuration "$FRAMEWORK_CONFIG" -target "$BUILD_TARGET" -sdk iphonesimulator -project "$PROJECT_NAME.xcodeproj" > /dev/null
25 |
26 | echo "Preparing directory..."
27 | rm -rf "$INSTALL_DIR"
28 | mkdir -p "$INSTALL_DIR/Headers"
29 | mkdir -p "$INSTALL_DIR/Modules/$BUILD_TARGET.swiftmodule"
30 |
31 | # Regulating Framework Deliverables
32 | echo "Migrating System Headers:"
33 | cp "$SIMULATOR_DIR/Headers/"*.h "$INSTALL_DIR/Headers/"
34 |
35 | echo "Mixing Mutli-Architecture Swift Modules:"
36 | cp "$SIMULATOR_DIR/Modules/module.modulemap" "$INSTALL_DIR/Modules/"
37 | cp "$SIMULATOR_DIR/Modules/$BUILD_TARGET.swiftmodule/"* "$INSTALL_DIR/Modules/$BUILD_TARGET.swiftmodule/"
38 | cp "$DEVICE_DIR/Modules/$BUILD_TARGET.swiftmodule/"* "$INSTALL_DIR/Modules/$BUILD_TARGET.swiftmodule/"
39 | cp "$SIMULATOR_DIR/Info.plist" "$INSTALL_DIR/"
40 |
41 | echo "Combine Fat File"
42 | lipo -create "$DEVICE_DIR/$BUILD_TARGET" "$SIMULATOR_DIR/$BUILD_TARGET" -output "${INSTALL_DIR}/${BUILD_TARGET}"
43 |
44 | # Clean Up Intermediate File
45 | # rm -rf "$WORK_DIR"
46 |
--------------------------------------------------------------------------------
/XCTestWD-master/scripts/install.js:
--------------------------------------------------------------------------------
1 | 'use strict';
2 |
3 | const fs = require('fs');
4 | const path = require('path');
5 | const xcode = require('xcode');
6 | const _ = require('macaca-utils');
7 | const shelljs = require('shelljs');
8 | const hostname = require('os').hostname();
9 | const doctorIOS = require('macaca-doctor/lib/ios');
10 |
11 | if (!_.platform.isOSX) {
12 | return;
13 | }
14 |
15 | const DEVELOPMENT_TEAM = process.env.DEVELOPMENT_TEAM_ID || '';
16 |
17 | const xctestwdFrameworksPrefix = 'xctestwd-frameworks';
18 |
19 | const update = function(project, schemeName, callback) {
20 | const myConfigKey = project.pbxTargetByName(schemeName).buildConfigurationList;
21 | const buildConfig = project.pbxXCConfigurationList()[myConfigKey];
22 | const configArray = buildConfig.buildConfigurations;
23 | const keys = configArray.map(item => item.value);
24 | const pbxXCBuildConfigurationSection = project.pbxXCBuildConfigurationSection();
25 | keys.forEach(key => {
26 | callback(pbxXCBuildConfigurationSection[key].buildSettings);
27 | });
28 | };
29 |
30 | const updateInformation = function() {
31 | try {
32 | const schemeName = 'XCTestWDUITests';
33 | const projectPath = path.join(__dirname, '..', 'XCTestWD', 'XCTestWD.xcodeproj', 'project.pbxproj');
34 | const myProj = xcode.project(projectPath);
35 | myProj.parseSync();
36 |
37 | update(myProj, schemeName, function(buildSettings) {
38 | const newBundleId = process.env.BUNDLE_ID || `XCTestWDRunner.XCTestWDRunner.${hostname}`;
39 | buildSettings.PRODUCT_BUNDLE_IDENTIFIER = newBundleId;
40 | if (DEVELOPMENT_TEAM) {
41 | buildSettings.DEVELOPMENT_TEAM = DEVELOPMENT_TEAM;
42 | }
43 | });
44 |
45 | const projSect = myProj.getFirstProject();
46 | const myRunnerTargetKey = myProj.findTargetKey(schemeName);
47 | const targetAttributes = projSect.firstProject.attributes.TargetAttributes;
48 | const runnerObj = targetAttributes[myRunnerTargetKey];
49 | if (DEVELOPMENT_TEAM) {
50 | runnerObj.DevelopmentTeam = DEVELOPMENT_TEAM;
51 | }
52 |
53 | fs.writeFileSync(projectPath, myProj.writeSync());
54 |
55 | if (DEVELOPMENT_TEAM) {
56 | console.log('Successfully updated Bundle Id and Team Id.');
57 | } else {
58 | console.log(`Successfully updated Bundle Id, but no Team Id was provided. Please update your team id manually in ${projectPath}, or reinstall the module with DEVELOPMENT_TEAM_ID in environment variable.`);
59 | }
60 | process.exit(0);
61 | } catch (e) {
62 | console.log('Failed to update Bundle Id and Team Id: ', e);
63 | }
64 | };
65 |
66 | let version = doctorIOS.getXcodeVersion();
67 | let pkgName = '';
68 |
69 | if (parseFloat(version) >= parseFloat('10.0')) {
70 | version = '';
71 | pkgName = xctestwdFrameworksPrefix;
72 | } else if (parseFloat(version) > parseFloat('9.2')) {
73 | version = version.replace(/\./, '').slice(0, 2);
74 | pkgName = `${xctestwdFrameworksPrefix}-${version}`;
75 | }
76 |
77 | const dir = require.resolve(pkgName);
78 | const originDir = path.join(dir, '..', 'Carthage');
79 | const distDir = path.join(__dirname, '..');
80 | console.log(`start to mv ${_.chalk.gray(originDir)} ${_.chalk.gray(distDir)}`);
81 |
82 | try {
83 | shelljs.mv('-n', originDir, distDir);
84 | } catch (e) {
85 | console.log(e);
86 | }
87 |
88 | const latestDir = path.join(distDir, 'Carthage');
89 |
90 | if (_.isExistedDir(latestDir)) {
91 | console.log(_.chalk.cyan(`Carthage is existed: ${latestDir}`));
92 | } else {
93 | throw _.chalk.red('Carthage is not existed, please reinstall!');
94 | }
95 | updateInformation();
96 |
--------------------------------------------------------------------------------
/XCTestWD-master/scripts/integration-testing.sh:
--------------------------------------------------------------------------------
1 | #!/bin/bash
2 |
3 | brew install nvm > /dev/null 2>&1
4 | source $(brew --prefix nvm)/nvm.sh
5 | nvm install 8
6 |
7 | npm i macaca-scripts -g
8 |
9 | export XCTESTWD_PATH=`pwd`"/XCTestWD/XCTestWD.xcodeproj"
10 |
11 | echo process env XCTESTWD_PATH set to $XCTESTWD_PATH
12 |
13 | macaca-scripts integration-test-ios
14 |
--------------------------------------------------------------------------------
/XCTestWD-master/test/mocha.opts:
--------------------------------------------------------------------------------
1 | --reporter spec
2 |
--------------------------------------------------------------------------------
/XCTestWD-master/test/xctest.test.js:
--------------------------------------------------------------------------------
1 | 'use strict';
2 |
3 | const assert = require('assert');
4 |
5 | const XCTest = require('..');
6 |
7 | describe('test', function() {
8 | it('should be ok', function() {
9 | assert.ok(XCTest);
10 | });
11 | });
12 |
--------------------------------------------------------------------------------