Ios Swift中私有变量的单元测试

Ios Swift中私有变量的单元测试,ios,swift,unit-testing,private,Ios,Swift,Unit Testing,Private,我很难掌握如何在一个所有字段都是私有的类中实现单元测试 该类正在使用BLE和CoreLocation计算用户的位置-这并不重要。我有一个协议,当发现一个新的位置时,我会调用它,所有符合该协议的类都会收到一个房间id和房间名称。这意味着我的类中的所有字段都是私有的,因为是的,没有理由任何外部类都应该访问它们,对吗?但这也意味着我可以在这个类中测试任何东西,即使有相当多的函数我想测试。我的意思是,我可以将变量设置为内部变量,而不是私有变量,但是仅仅为了单元测试而这样做似乎是错误的。我听说过依赖注入,

我很难掌握如何在一个所有字段都是私有的类中实现单元测试

该类正在使用BLE和CoreLocation计算用户的位置-这并不重要。我有一个协议,当发现一个新的位置时,我会调用它,所有符合该协议的类都会收到一个房间id和房间名称。这意味着我的类中的所有字段都是私有的,因为是的,没有理由任何外部类都应该访问它们,对吗?但这也意味着我可以在这个类中测试任何东西,即使有相当多的函数我想测试。我的意思是,我可以将变量设置为内部变量,而不是私有变量,但是仅仅为了单元测试而这样做似乎是错误的。我听说过依赖注入,但它似乎太费劲了

例如,我有以下功能:


private var beacons: [AppBeacon] = []
private var serverBeacons:[Beacon] = []

private func addBeacons(serverBeacons: [Beacon]){
        for beacon in serverBeacons {
            let beacon = AppBeacon(id: beacon.id, uuid: beacon.uuid, building: beacon.building, name: beacon.name)
            beacons.append(beacon)
       }
   }
例如,我无法测试信标阵列是否按照我的意愿被填满。我的类的公共特性基本上是一个名为startocating的函数,结果是房间id和名称,我知道在黑盒测试中哪些单元测试是模仿的(对吗?),我不应该关心中间步骤,但老实说,有这么多功能,我应该说,没关系吗?假设我用我选择的一些rssi值填充了信标,实际的定位算法是在node.js服务器上执行的,所以我真的不知道测试客户端什么

这是经典的MVC,在截止日期之前我无法改变它的架构,所以我不知道从这里开始最好的方式是什么?只是不测试功能?是否将字段设置为内部字段而不是私有字段?我们在服务器端对算法本身进行测试,因此测试房间id是否是预期的房间id已经过测试

我在另一篇帖子上读到如下内容:

“根据定义,单元测试是黑盒测试,这意味着您不关心您测试的单元的内部。您主要感兴趣的是根据您在单元测试中给出的输入来查看单元输出是什么。 现在,通过输出,我们可以断言以下几点:

  • 方法的结果
  • 作用于对象后的对象状态
  • 与对象具有的依赖项的交互
在所有情况下,我们只对公共接口感兴趣,因为它是与世界其他地方进行通信的接口。 私有的东西不需要单元测试,因为任何私有的项目都被公共的项目间接使用。诀窍是编写足够的测试来锻炼公共成员,这样私有的项目就被完全覆盖了

另外,需要记住的一件重要事情是,单元测试应该验证单元规范,而不是它的实现。验证实现细节会在单元测试代码和被测试代码之间增加紧密耦合,这有一个很大的缺点:如果被测试的实现细节发生变化,那么单元很可能测试也需要更改,这降低了对这段代码进行单元测试的好处。”


<>和我从本质上理解的是,我不应该对这个单元进行测试。

首先,你所引用的“单元测试”的定义是非常不寻常的:我所知道的所有文献的定义都考虑单元测试一个玻璃盒/白盒测试方法。更准确地说,单元测试本身实际上既不是黑盒也不是白盒——是设计测试用例的方法造成了差异。但没有理由不将白盒测试设计技术应用于单元测试。事实上,一些白盒测试设计技术只有在应用于单元测试时才有意义。例如,当您调查单元测试时,您将遇到许多关于不同代码覆盖率标准的讨论,如语句覆盖率、分支覆盖率、条件覆盖率、,MC/DC -对于所有这些都有必要知道代码的实现细节,并在测试用例设计期间考虑这些实现细节。 但是,即使考虑到这一点,对于您的特定情况也不会有太大的变化:代码中的变量仍然是私有的:-)但是,您以一种过于严格的方式处理测试问题:您尝试为自己测试函数

addBeacons
,甚至与该组件中的其他功能完全隔离


要测试
addBeacons
,您的测试用例不仅应该包含对
addBeacons
的调用,还应该包含一些其他函数调用,其结果将显示对
addBeacons
的调用是否成功。例如,如果您还有一个按名称或位置查找信标的函数,则首先调用
addBeacon
,若要检查此操作是否成功,请调用其中一个函数以查看是否会找到添加的信标。这两个调用将是同一测试用例的一部分。

如果您有一个
私有var
可以帮助您编写单元测试,请将其更改为
私有(设置)var
,以便可以读取(但不更改)


暴露内脏可能会让你烦恼。如果是这样,则可能有另一种类型正在等待从视图控制器中提取。

通常,您有使用/读取属性的函数,因此您可以对它们进行单元测试。测试
信标
属性的示例您测试一个使用该属性的函数,并在调用该函数进行测试之前通过调用
addBeacons
对其进行设置。是的,但假设我调用addBeacons,我不能只说:
addBeacons()
xctasertequal(beacons.first.id,“id”)
因为beacons是私有的,所以我根本无法访问属性。这根本不是我说的,您必须编写一个单元测试来测试从