简体   繁体   English

如何模拟 RestTemplate 的新实例?

[英]How to mock new instance of RestTemplate?

Im writing a unit test for my legacy code which is something like:我为我的遗留代码编写了一个单元测试,类似于:

public class SomeClass {
public SomeResponse logToServer() {
    SomeResponse response = null;
    try{ 
        RestTemplate restTemplate = new RestTemplate();
        SomeRequestBean request = new SomeRequestBean();
        response = restTemplate.postForEntity("http://someUrl", request, SomeResponse.class);
        System.out.println(response.toString());
    } catch(Exception e) {
        e.printStackTrace();
    } 
    return response;
}

} }

I know I can move RestTemplate above and annotate it as @AutoWire and declare it as bean class or use power mockito to mock the new instance creation.我知道我可以在上面移动 RestTemplate 并将其注释为@AutoWire并将其声明为 bean 类或使用 power mockito 来模拟新实例的创建。 But I don't wanna change this legacy code and I'm avoiding using power Mockito at all cost because just for one test I don't wanna add a whole new dependency to my pom.xml .但我不想改变这个遗留代码,我不惜一切代价避免使用强大的 Mockito,因为仅仅为了一个测试,我不想向我的pom.xml添加一个全新的依赖项。 So just wondering is there any way using which I can mock this restTemplate ?所以只是想知道有什么方法可以模拟这个restTemplate吗?

To answer you question, no under the restrictions you've posted there is no way to mock RestTemplate and unit test it.为了回答您的问题,在您发布的限制下,无法模拟 RestTemplate 并对其进行单元测试

I do think that you can slightly change the legacy code because this change is not functional and in this case it might worth it.我确实认为您可以稍微更改遗留代码,因为此更改不起作用,在这种情况下可能值得。 But I'll stick with you that you can't.但我会坚持你,你不能。

Regarding power mock and power mockito.关于 power mock 和 power mockito。 Although I agree that these tools should be avoided but not for a reason that you've posted.虽然我同意应该避免使用这些工具,但不是出于您发布的原因。 Note, that this dependency is of test scope, it won't reach the production anyway even for legacy envrionments.请注意,此依赖项属于测试范围,即使对于遗留环境,它也不会到达生产环境。 So if the priority is to not change the legacy code, then introducing PowerMock is the "least evil".因此,如果优先考虑的是不更改遗留代码,那么引入 PowerMock 是“最不邪恶的”。

If we're talking specifically about the rest template though, you can take advantage of some facts about spring rest template specifically that can be used for testing it anyway.不过,如果我们专门讨论 rest 模板,您可以利用一些有关 spring rest 模板的事实,这些事实无论如何都可用于测试它。

Option 1选项1

The first technique (if the environment permits) is using @RestClientTest annotation.第一种技术(如果环境允许)是使用@RestClientTest注释。 It will allow specifying the service under test and will provide a mock implemetation of something called MockRestServiceServer that will represent the server you're trying to connect to in the mocked environment.它将允许指定被测试的服务,并将提供一个名为MockRestServiceServer的模拟实现,该模拟实现将代表您在模拟环境中尝试连接的服务器。 Then you'll be able to specify the expectations from this server and hopefully the code will run.然后,您将能够指定该服务器的期望值,并希望代码能够运行。 Caution: this is not a unit test - this is an integration test that starts spring context, so it will much heavier/slower than regular unit test.注意:这不是单元测试 - 这是一个启动 spring 上下文的集成测试,因此它比常规单元测试更重/更慢。

Here you can find a working example of this approach, check out this article it contains also other techniques.在这里你可以找到这个方法的一个工作示例,查看这篇文章它也包含其他技术。

Option 2选项 2

The idea behind the second technique is that RestTemplate is actually a wrapper above client libraries, it doesn't do any http intercommunication by itself.第二种技术背后的想法是RestTemplate实际上是客户端库之上的包装器,它本身不进行任何 http 互通。

It can be configured to work with HttpClient of apache, OkHttpClient, by default it works with URLConnection opening connection for each request.它可以配置为与 apache 的 HttpClient、OkHttpClient 一起使用,默认情况下它与 URLConnection 一起为每个请求打开连接。 So You could create a test that would configure the rest client to run with some particular engine of your interest/choice and then check out how to test code that uses this engine directly.因此,您可以创建一个测试,将其余客户端配置为使用您感兴趣/选择的某些特定引擎运行,然后查看如何直接测试使用该引擎的代码。 The solutions will be different depending on the actual engine used in the project.根据项目中使用的实际引擎,解决方案会有所不同。

So just wondering is there any way using which i can mock this restTemplate ? 所以,我只是想知道有什么方法可以模拟我的restTemplate吗?

Short Answer: No 简短答案:

Based on stated restrictions, 根据规定的限制,

But I don't wanna change this legacy code and im avoiding using power Mockito at all cost because just for one test i dont wanna add a whole new dependency to my pom.xml 但是我不想更改此遗留代码,并且我不惜一切代价避免使用Power Mockito,因为我只想为一个测试添加新的依赖项到pom.xml中

there is likely no other way to mock the restTemplate . 可能没有其他方法可以模拟restTemplate

The subject code is tightly coupled to implementation details/concerns that make testing it in isolation difficult without the use of external dependencies/tools or refactoring the code to make it testable. 主题代码与实现细节/关注紧密耦合,这使得在不使用外部依赖项/工具或不重构代码以使其无法测试的情况下,很难单独进行测试。

This is a case of technical debt calling in its loan. 这是技术债务要求其贷款的情况。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM