一、两种技术的比较
XCode的自动化测试包括:UnitTests与UITests,即:单元测试与界面测试。EarlGrey是Google在UnitTests的基础上开发的界面测试库,与UITests相似,同时具有一定的优势。具体如下:
二、UITests使用教程
Quick Start
1、新建项目,在以下界面勾选Unit Tests与UI Tests。
2、如果是老项目:点击菜单-Editor-Add Target,并在以下界面选择iOS UI Testing Bundle
3、给新的Target起名
4、在项目可以看到新添加的Target与对应的文件夹
5、查看自动生成的UITests代码,本例为UITestsSample.swift。默认生成testExample测试方法。注:所有待测试的方法均以test开头
6、编写测试代码,详见下方说明
7、点击Test Navigator,这里将所有Target、其下测试类、以及测试方法列了出来,是按字母排序的。点击右侧的三角形按钮即开始测试,可对指定方法、指定类、指定Target进行测试。按Command+U则依次测试所有Target
8、测试完成后,在以下界面会显示测试结果,绿勾表示成功或红叉表示失败
9、下图为报告,左侧列出了所有测试报告列表(也包括每次的编译报告),右侧为某次测试报告详情。具体每一个测试步骤的情况(时间、截图等)均会显示。
UITests核心类介绍
1、XCUIApplication:对应UIApplication,对App进行操作。主要方法有:
init() / init(bundleID):得到当前App实例,也可通过bundleID得到其他App实例,如:模拟打开微信时需要用到。
launch():启动App
activate():激活App
terminate():中止App
state: runningForeground/runningBackground/notRunning:得到App状态
wait(for state: XCUIApplication.State, timeout: TimeInterval) -> Bool:等待App状态变为某值时,并设置了超时时间
2、XCUIElement:对应界面上的元素。主要方法有:
exists:判断元素是否存在
waitForExistence(timeout:) -> Bool:等待元素出现
children(matching: ElementType) -> XCUIElementQuery:获取一级子元素
descendants(matching: XCUIElement.ElementType) -> XCUIElementQuery:获取所有子元素
typeText(String):模拟键盘输入,并填入文本框中
tap() / doubleTap() / press(forDuration:) / press(forDuration: thenDragTo:) / twoFingerTap() / swipeLeft/Right/Up/Down() / pinch() / rotate():各类操作
3、XCUIElementQuery:查找元素的规则。主要方法有:
allElementsBoundByIndex: [XCUIElement]:返回该规划对应的所有元素集合
count: Int:返回该规划对应的所有元素数量
element: XCUIElement:返回该规划对应的单个元素
element(boundBy: Int) -> XCUIElement:按下标返回该规划对应的元素。boundBy貌似是根据各元素的x、y坐标排序的。(类似先上后下、先左后右,具体排序规则未知)
element(matching: XCUIElement.ElementType, identifier: String?) -> XCUIElement:按元素类型、id返回
children(matching: ElementType) -> XCUIElementQuery:返回指定类型的子元素查询规则
descendants(matching: XCUIElement.ElementType) -> XCUIElementQuery:返回指定类型的后代元素查询规则
4、其他重要类
XCUIScreen:对屏幕的操作,如截屏等
XCTAttachment:附件类,如需要将截屏包装成Attachment才能添加到测试报告中
XCTActivity:上下文,如添加Attachment的方法就在其中
Asynchronous:对异步操作的捕获
XCTKVOExpectation:对KVO值changed的捕获
XCTNSNotificationExpectation:对通知的捕获
Assert functions:各种断言方法,如下:
UITests代码实例说明
```
importXCTest
classUITestsSample:XCTestCase{
//自动生成的代码,所有testXXX执行前均会执行它
overridefuncsetUp() {
//出错后是否继续
continueAfterFailure = false
XCUIApplication().launch()
}
//自动生成的代码,所有testXXX执行后均会执行它
overridefunctearDown() {
}
//测试打开微信
functestWeixin() {
letapp =XCUIApplication(bundleIdentifier:"com.tencent.xin")
app.activate()
//模拟点击“我”tab
app.tabBars.buttons["我"].tap()
//模拟点击“支付”菜单
app.tables.staticTexts["支付"].tap()
}
functestLoginPerformance() {
//对sampleFun方法进行性能测试,系统会尝试多次(约10次),并生成性能报告。测试完后,self.measure代码左侧会出现一个灰色按钮,点击查看报告
self.measure{
sampleFun()
}
}
functestAddReminder() {
sampleFun()
}
funcsampleFun() {
letapp =XCUIApplication()
//查找accessibilityIdentifier=login的按钮,并点击它。注:accessibilityIdentifier需要在App主代码中设置
app.buttons["login"].tap()
//查找日期按钮并点击
app.datePickers["date"].tap()
//按静态文本查找
app.staticTexts["登录"].tap()
//查找第1个UITableView
app.tables.element(boundBy:0)
//是否存在静态文本为“注册”的视图
ifapp.staticTexts["注册"].exists{
}
//等待“注册”出现,最多等10秒,如果出现了就返回true
ifapp.staticTexts["注册"].waitForExistence(timeout:10) {
}
//层层查找。注:这种方法不可靠,主App代码变动会导致视图结构变动
app.children(matching: .table).children(matching: .button)
//判断“注册“是否存在,不存在则认为异常,抛出异常信息
XCTAssertTrue(app.staticTexts["注册"].exists,"注册按钮不存在")
}
}
```