我正在使用两个应用程序开发项目:android app(客户端)和rest service(服务器)。我的Android应用程序使用我的休息服务。
两个应用程序都是单独测试的,以确保它们按预期开展业务。 在服务器测试期间,我准备请求并检查服务器响应 在客户端测试期间,我设置了一个简单的http模拟服务器,并针对不同的模拟响应测试客户端的请求。
现在,这项技术非常有效。它给了我一种我喜欢的灵活性。我可以使用不同的测试框架和持续集成环境。但有一个弱点。在(客户端和服务器)测试用例中,我指定了相同的api。我认为,例如
GET /foo-list.json
将使用json
返回HTTP 200[{
id: 1,
name: foo1,
}, {
id: 2,
name: foo2
}]
所以我重复一遍。如果我更改响应格式,我的客户端测试不会失败。
我的问题是关于测试这种情况的良好做法。如何在不牺牲独立测试灵活性的情况下进行真正的集成测试。 我应该使用模拟服务器或我的休息服务的真实实例来测试客户端吗?
请分享您的专业经验。
答案 0 :(得分:8)
在您的场景中,您应该继续编写单元测试来测试单个类,并使用集成测试来测试多个应用程序层(例如业务层和数据库层)之间的互操作。
你问:
“如何在不牺牲独立测试灵活性的情况下进行真正的集成测试”
您的所有代码都应该使用抽象,这样您就可以使用依赖注入来使用模拟依赖项完全隔离单元测试类。模拟的使用将确保这些测试将保持独立,即不与任何其他类别耦合。因此采用这种方法,使用最终具体类的集成测试不会影响使用模拟类的单元测试。
此外:
“我应该使用模拟服务器或我的休息服务的真实实例来测试客户端吗?”
除了单元和集成测试之外,您还应执行客户端 - 服务器集成测试;我使用自动验收测试来做到这一点。使用诸如Cucumber之类的测试框架(也可以查看专门为测试移动应用程序而编写的calaba.sh),您可以编写测试,测试将与客户端(您的Android应用程序)和服务器交互的特定功能和方案(您的RESTful服务)。这些客户端 - 服务器集成测试将启动并停止客户端和服务器的具体实例。
答案 1 :(得分:4)
模拟用于单元测试。您对模拟测试的描述正是如此。您将客户端和服务器作为单独的单元进行测试。
集成测试测试单元是否可以很好地协同工作。由于接口是一个REST接口,因此模拟没有意义,你必须通过HTTP测试真实的东西。
另见What is the difference between integration and unit tests?
答案 2 :(得分:1)
如果您的服务基于Java,我强烈建议您查看Spock框架,以模拟可能来自客户端的任何类型的调用。由于Spock只是jUnit的扩展,你也可以将它用于Android(不过,公平地说,我从未做过Android开发)
我说你想做两件事。集成测试和单元测试。集成测试会尝试启动Android应用程序并使其进行服务调用,确保上下文彼此友好地互动。
然而,在你的常规提交中,我建议进行单元测试,除了被测试的课程外,它们都会嘲笑。 Spock使这很容易做到,因为它建立在jUnit之上所有它需要一个jar。
答案 3 :(得分:1)
没有理由不能使用真实服务实例运行自动端到端测试。您可以在用于运行单元测试的同一测试计算机上运行实际服务实例,可能在同一容器中。您可以设置配置以使用服务器实例的不同URL来运行自动端到端测试。
如果您可以针对真实服务运行模拟服务,为什么还要进行额外的创建模拟服务呢?
如果服务是我无法控制的外部服务,我只会创建一个模拟服务!