无法覆盖Swift XCTestCase中的init()函数

Bri*_*ley 7 xcode ios swift xcode-ui-testing

由于某些原因,我想在UI测试中覆盖XCTestCase的init函数:

  • 要在setUp()之外启动应用程序,这样就无需为每个测试重新启动应用程序(这很繁琐,而且会降低测试速度)
  • 要初始化提供通过应用程序的常规导航的其他类,必须使用测试用例(self)进行初始化。

我现在看起来像这样:

import XCTest

class UITest: XCTestCase {

    let app = XCUIApplication()

    // Helper packages
    var helper: UITestHelper!

    override func setUp() {
        super.setUp()

        // Helper package instantiation
        helper = UITestHelper(withTestCase: self, forApp: app)

        continueAfterFailure = false
        app.launch()
    }

... tearDown(), tests ....
Run Code Online (Sandbox Code Playgroud)

当我打电话时:

override init() {
    super.init()
    foo()
}
Run Code Online (Sandbox Code Playgroud)

我懂了 Thread 1: EXC_BAD_INSTRUCTION (code=EXC_I386_INVOP, subcode=0x0)

Rob*_*ier 7

init不是的指定初始值设定项XCTestCase。指定的初始值设定项是initWithInvocation:。这需要一个NSInvocation,这在Swift中不可用。做您要描述的唯一方法是在ObjC中。

由于不支持,因此未记录。可能可以实现您所描述的内容,但是可能会以微妙的方式破坏,您应该探索解决问题的其他方法。

崩溃是ObjC初始化语义的副产品。每个ObjC类都必须响应init(因为它是从继承的NSObject)。但是,有很多ObjC对象在init调用时无法正确初始化。(NSError此问题有些出名。)唯一的了解方法是通过文档。更复杂的Swift初始化系统是对ObjC初始化系统中的问题进行补救的尝试。

我会将您的更深层次的目标分解为单独的问题,并询问如何解决这些问题(您还应该清楚地表明您正在谈论UI测试;而您的代码指出了这一点,但从文本中还不清楚)。确保您所描述的内容不会破坏Xcode 10的新并行测试功能以及对订购的更改。

  • 它会破坏一件事的测试并行化,并使一个测试依赖套件中的其他测试,这通常是一件坏事。 (2认同)