spring mvc中的单元测试

Posted

技术标签:

【中文标题】spring mvc中的单元测试【英文标题】:Unit testing in spring mvc 【发布时间】:2015-10-17 00:02:13 【问题描述】:

如果我想在 spring 中对我的 dao 类进行单元测试,我是只调用我的服务方法并对其进行测试,还是将服务方法与实际的 dao 方法分开测试?

我还应该模拟 dao 调用还是实际使用像 H2 这样的内存数据库?我认为这更像是一个集成测试,尽管一些教程会这样做,或者标准方法是使用模拟数据库对象进行服务测试并在测试 dao 调用时使用 H2?

最后.. 我的应用程序有一个使用 Spring REST 模板从 Web 前端调用的 REST API,因此只有 API Web 应用程序可以访问数据库。

我是否会使用模拟对象测试每个 Web 应用程序中的其余方法,然后启动一个 tomcat 实例并在两个应用程序之间进行集成测试?如果我使用 tomcat 并在应用程序之间运行集成测试,是否会在 API 应用程序中连接数据库或模拟对象?

测试来自 Web 应用程序的其余调用实际上取决于 API 应用程序的 rest 方法如何响应,所以这甚至值得单独测试吗?

我发现单元测试相当混乱,因为其中一些似乎几乎是集成测试。

如果您在内存中针对 H2 运行集成测试,但实际上我会使用 mysql,这有关系吗?

【问题讨论】:

我个人只会使用 Spring Data 而完全避免实现和测试我自己的 DAO 类。 @chrylis:这是一个相当大的假设,即 Spring Data 适合 OP 用例。 【参考方案1】:

尝试按照提问的顺序回答您的问题...

对于 DAO 方法的单元测试,您应该使用处于已知状态的数据库直接测试实际的 DAO 类。 H2 非常适合这一点,因为您可以在不为每个测试设置 MySQL 的情况下运行它。使用带有@Before 注释的设置方法非常适合确保数据库将以预期的方式响应。

对于单元测试服务类,您应该模拟 DAO 类,以便它们始终以预期的方式运行。如果您将服务和 DAO 类与实际数据一起使用,那么您现在正在通过同时测试多个层来运行集成测试。两者都有其价值,但通常最好在集成测试之前进行单元测试,以确保每个组件都正常运行。

测试您的控制器也是如此,您应该对其进行单元测试并模拟服务类,然后使用模拟请求执行集成测试以测试请求/响应场景。同样,使用此测试设置,您现在可以同时测试多个层和类。这很棒,因为它可以让您很好地了解应用程序在现实中的运行方式,但对于隔离错误没有用处。

H2 和 MySQL 显然不一样,并且不共享所有相同的功能,因此您不能 100% 确信 H2 测试会在 MySQL 中通过,但如果您只是测试标准 CRUD 操作,它应该可以解决问题。

【讨论】:

谢谢,这真的很有用。它几乎可以回答所有问题,您对作为独立 maven 模块的 Web 应用程序之间的集成测试有何看法,是否值得在测试中启动一个 tomcat?流程将是 web 应用控制器 >> web 应用服务 (restTemplate) >> web API 控制器 >> web API 服务 >> Web API DAO >> hibernate。是否值得自动化测试从 Web 前端到 API 后端的调用,这将一次性测试多个层?我会将您的答案标记为答案,因为这正是我需要知道的。 恕我直言,您可以同时测试的层数越多越好,如果可能的话,包括将 Tomcat 投入其中。它让您更好地了解应用程序将如何运行 IRL。不过,这不应该替代单元测试。

以上是关于spring mvc中的单元测试的主要内容,如果未能解决你的问题,请参考以下文章

Spring MVC 单元测试Demo

spring mvc 单元测试示例

spring mvc+spring + hibernate 整合

高手如何给 Spring MVC 做单元测试?

高手都这么给 Spring MVC 做单元测试!

使用 Spring-Test-MVC 单元测试 Spring-Security - 集成 FilterChain / ServletFilter