从 Swift 包中测试故事板

Testing storyboard from within Swift Package

在将应用程序的代码分解到 swift 程序包和 运行 到一个奇怪的问题的过程中,同时添加了测试覆盖率。

我在下面的方法中引用了应用程序的主要情节提要,我已经将其移入 swift 包中...

    /// This method decorates self by setting backgroundColor and adding SKLabelNode with text derived
    /// from `model` parameter. After 3 seconds, the method exits sprite scene to return to view controller
    /// for high scores scene.
    ///
    /// - parameter model: Game Over data model used to derive SKLabelNode text.
    func decorateGameOverScene(from model: GameEndData) {
        backgroundColor = .black
        
        let label = createGameOverLabel(from: model)
        label.run(
            SKAction.sequence([
                                SKAction.wait(forDuration: 3.0),
            SKAction.removeFromParent()]),
            withKey: "FadeoutAction")
        addChild(label)

        DispatchQueue.main.asyncAfter(deadline: .now() + 2.6) { [weak self] in
            let storyboard = UIStoryboard(name: "Main", bundle: nil)
            let vc: UIViewController
            let id = "HighScoreViewController"
            if #available(iOS 13.0, *) {
                vc = storyboard.instantiateViewController(identifier: id)
            } else {
                vc = storyboard.instantiateViewController(withIdentifier: id)
            }

            self?.switchFromSpriteKit(to: vc)
        }
    }

现在,当我 运行 应用程序时,这会按预期工作。

当我开始添加测试覆盖率时,我在访问情节提要时遇到了问题,因为应用程序没有包的目标,而当我尝试将情节提要添加到包时,我没有看到如何定位它。

为了解决这个问题,我在单元测试中使用@testable 来引用应用程序本身。这种方法行之有效,因为当我 运行 仅在该文件中进行单元测试时,一切都很好并通过了。

但是,当我 运行 整组单元测试我设置的期望等待时(实际上只是在另一个线程中暂停,以便在加载视图时允许一定的时间过去在主线程上),在尝试引用故事板时因错误而挂断。

    func waitToFire() {
        let expectation = XCTestExpectation()
        let q = DispatchQueue(label: "Test Queue")
        q.asyncAfter(deadline: .now() + 1.0) {
            expectation.fulfill()
        }
        wait(for: [expectation], timeout: 2.0)
    }

Thread 1: "Could not find a storyboard named 'Main' in bundle NSBundle </Applications/Xcode.app/Contents/Developer/Platforms/iPhoneSimulator.platform/Developer/Library/Xcode/Agents> (loaded)"

可能我需要将故事板移动到包中,或者制作一个具有相同标识符的测试,但真正让我困惑的是 为什么只有当整套单元测试是运行?

我现在正在查找如何将情节提要添加到 swift 包中,但不明白为什么当他们的测试用例是 运行 时测试可以通过,但当全部单元测试正在进行 运行...我一次检查了每个测试文件,它们都通过了,以防有另一个问题导致问题,并且 none 挂起。调度队列也是该方法所独有的。

当有多个测试时 运行 他们可能会尝试并行引用情节提要,这可能会导致 类 在实例化时出现问题。