【问题标题】:Using inline preprocessor macros in Swift在 Swift 中使用内联预处理器宏
【发布时间】:2015-11-10 20:19:31
【问题描述】:

背景:我想用 XCTest 测试私有方法,所以我正在寻找一个优雅的解决方案来向我的 XCTestCase 类公开私有方法。

免责声明:有些人认为测试类的内部是根本错误的。在实践中我不同意,因为当测试中断时,测试 private 可以更容易地追踪问题。

Swift 的私有函数对文件来说是私有的,而私有真正的意思是私有的,因此没有办法将私有函数暴露给其他文件。使用预处理器宏,可以通过公共函数公开私有功能,仅用于一个构建配置。例如,我为我的测试配置设置了一个TEST 编译标志,我的测试方案使用它。

到目前为止,这是我拥有的最佳解决方案,但它需要为每个需要测试的私有函数提供烦人的样板:

在 ClassThatNeedsTesting.swift 中:

class ClassThatNeedsTesting {
   #if TEST
   func publicAccessToPrivateFunctionThatNeedsTesting() -> Bool {
      return self.privateFunctionThatNeedsTesting()
   }
   #endif

   private func privateFunctionThatNeedsTesting() -> Bool {
      return true;
   }
}

在 TestClass.swift 中:

class TestClass: XCTestCase {
   func testExample() {
      XCTAssert(ClassThatNeedsTesting().publicAccessToPrivateFunctionThatNeedsTesting());
   }
}

但是有没有办法使用内联预处理器宏来简化这一点?这就是我想要的,但它没有编译,因此我问:

在 ClassThatNeedsTesting.swift 中:

class ClassThatNeedsTesting {
   #if TEST private #endif func privateFunctionThatNeedsTesting() -> Bool {
      return true;
   }
}

在 TestClass.swift 中:

class TestClass: XCTestCase {
   func testExample() {
      XCTAssert(ClassThatNeedsTesting().privateFunctionThatNeedsTesting());
   }
}

如果没有办法做到这一点,也许有更简单的解决方案?

【问题讨论】:

    标签: xcode swift unit-testing testing


    【解决方案1】:

    使用@testable,Swift 2.0 中的新功能:

    @testable import MyModule
    
    class TestClass: XCTestCase {
       func testExample() {
          XCTAssert(ClassThatNeedsTesting().privateFunctionThatNeedsTesting());
       }
    }
    

    来自Xcode 7 Release Notes

    可测试性。借助可测试性,您现在可以编写 Swift 2.0 框架和应用程序的测试,而无需公开所有内部例程。在您的测试源代码中使用 @testable import {ModuleName} 以使所有公共和内部例程可由 XCTest 目标使用,但不能由其他框架和应用目标使用。

    是否应该测试私有方法是一个热门话题。见讨论hereherehere

    【讨论】:

    • 这不起作用。您引用的 Apple 文档指出“在您的测试源代码中使用 @testable import {ModuleName} 以使 XCTest 目标可以使用所有公共和内部例程。” @testable 仅适用于公共和内部例程,不适用于私有例程。
    • 只是添加与 kev 的协议,因为我遇到了同样的问题。在我的测试中,调用私有方法时出现以下错误:使用未解析的标识符“PrivateMethodNameHere”。请注意,如果这是 Obj-C,您可以调用私有方法,并在此处讨论:stackoverflow.com/questions/12353795/…
    • 你会如何在objective-c中使用@testable?而且,您可以将您的应用程序作为模块导入到 Objective-c 中吗?请原谅我的无知 - 很难找到关于这个主题的好信息!
    猜你喜欢
    • 2016-09-02
    • 2010-11-11
    • 2015-02-26
    • 1970-01-01
    • 2021-12-29
    • 2015-04-15
    • 2019-10-03
    相关资源
    最近更新 更多