Swift 测试是否已显示UIAlertController
我有一个允许ViewController显示警报的协议Swift 测试是否已显示UIAlertController,swift,xctest,uialertcontroller,Swift,Xctest,Uialertcontroller,我有一个允许ViewController显示警报的协议 导入UIKit 结构AlertableAction{ 变量标题:字符串 变量样式:UIAlertAction.style var结果:Bool } 协议警报{ func presentAlert(标题:字符串?,消息:字符串?,操作:[AlertableAction],完成:((Bool)->Void)?) } 扩展可报警,其中Self:UIViewController{ func presentAlert(标题:字符串?,消息:字符串?,
导入UIKit
结构AlertableAction{
变量标题:字符串
变量样式:UIAlertAction.style
var结果:Bool
}
协议警报{
func presentAlert(标题:字符串?,消息:字符串?,操作:[AlertableAction],完成:((Bool)->Void)?)
}
扩展可报警,其中Self:UIViewController{
func presentAlert(标题:字符串?,消息:字符串?,操作:[AlertableAction],完成:((Bool)->Void)?){
let生成器=反馈生成器(样式:。中等)
生成器
让alertController=UIAlertController(标题:标题,消息:消息,首选样式:。警报)
actions.forEach{中的操作
addAction(UIAlertAction(标题:action.title,样式:action.style,处理程序:{正在完成?(action.result)}))
}
存在(alertController,动画:真,完成:无)
}
}
我把这叫做
@objc private func didTapLogout(){
展示员(
标题:无,消息:“您确定要注销吗?”,
行动:[
AlertableAction(标题:“否”,样式:。取消,结果:false),
AlertableAction(标题:“是”,样式:。破坏性,结果:真),
],
完成:{[弱自我]导致
保护结果else{return}
self?.presenter.logout()
}
)
}
我想编写一个单元测试来断言当调用它时,显示的视图控制器是UIAlertController
我试过类似的东西,但没有通过
func测试呈现警报控制器(){
sut.show()
XCTASERTNOTNIL(sut.presentedViewController)
}
类MockViewController:UIViewController,可报警{
var PresentViewController目标:UIViewController?
func show(){
presentAlert(标题:nil,消息:“您确定要注销吗?”,操作:
[AlertableAction(标题:“否”,样式:。取消,结果:false)],
完成日期:无
)
self.presentViewControllerTarget=self.presentdviewcontroller
}
}
在运行断言之前,需要等待UIAlertController
完全可见
退房
请尝试以下方法:
let nav = UINavigationController.init(rootViewController: sut)
sut.show()
let exp = expectation(description: "Test after 1.5 second wait")
let result = XCTWaiter.wait(for: [exp], timeout: 1.5)
if result == XCTWaiter.Result.timedOut {
XCTAssertNotNil(nav.visibleViewController is UIAlertController)
} else {
XCTFail("Delay interrupted")
}
通过捕获用于显示警报的信息而不实际显示任何警报,避免了缓慢、不稳定的单元测试。您只需创建一个AlertVerifier,然后调用显示警报的任何内容:
let alertVerifier = AlertVerifier()
sut.show()
alertVerifier.verify(
title: nil,
message: "Are you sure you want to logout?",
animated: true,
presentingViewController: sut,
actions: [
.cancel("No"),
.destructive("Yes"),
]
)
此验证方法检查:
- 这一警报以动画形式呈现
- 显示视图控制器是正在测试的系统
- 警报标题
- 警报消息
- UIAlertController.style的首选样式(
默认).alert
- 每个动作的标题和风格
try alertVerifier.executeAction(forButton: "Yes")
(将测试标记为抛出
。如果没有具有给定名称的按钮,测试将失败。)
试试看它与1.5秒超时相比有多快。还要比较你能测试多少