简体   繁体   English

是否可以在不自动装配被测类的情况下从 application.properties 检索值?

[英]Is it possible to retrieve value from application.properties without autowiring the class under test?

I have a test class that is annotated with @Spy and @InjectMocks and tested using Mockito.我有一个使用@Spy@InjectMocks注释并使用Mockito 进行测试的测试类。 The class under test has a value (url) that is retrieved from the application.properties file.被测类有一个从application.properties文件中检索的值 (url)。 I'd like to test whether this url is being set correctly within the method that uses it.我想测试这个 url 是否在使用它的方法中正确设置。 I can do this if I remove the @Spy and @InjectMocks annotations and use @Autowire and @SpringBootTest .如果我删除@Spy@InjectMocks注释并使用@Autowire@SpringBootTest ,我可以做到这一点。 However, that breaks other tests that use the spy functionality, so I'm just wondering if there's any way we can keep the spy working and test all our methods inside the same file, maybe without the need to bring in the @SpringBootTest annotation and the autowiring?但是,这会破坏使用间谍功能的其他测试,所以我只是想知道是否有任何方法可以保持间谍工作并在同一个文件中测试我们的所有方法,也许不需要引入@SpringBootTest注释和自动接线? The workaround we're using for now is to have two files, one that uses the spy and the other that tests the specific method to do with the properties file and that requires the full context to load, but not sure that's the best solution here?我们现在使用的解决方法是有两个文件,一个使用间谍,另一个测试使用属性文件的特定方法,并且需要加载完整的上下文,但不确定这是最好的解决方案?

Here is the test with the spy:这是对间谍的测试:

@ExtendWith(MockitoExtension.class)
class ProviderHelperServiceTest {

    @Spy
    @InjectMocks
    ProviderHelperService providerHelperService;
    
    @Value("${viaduct-url}")
    String viaductUrl;
    
    @Test
    void testGetRequestBodyUriSpec() {
        WebClient.RequestBodyUriSpec requestBodyUriSpec = providerHelperService.getRequestBodyUriSpec("sifToken");
        
        final String[] url = new String[1];
        requestBodyUriSpec.attributes(httpHeaders -> {
            url[0] = (String) httpHeaders.get("org.springframework.web.reactive.function.client.WebClient.uriTemplate");
        });

        // Fails as url[0] comes back as null. Disabled and moved to another file.
        assertEquals(viaductUrl, url[0]);
    }
@SpringBootTest
class ProviderHelperService2Test {

    @Autowired
    ProviderHelperService providerHelperService;

    @Value("${viaduct-url}")
    String viaductUrl;

    @Test
    void testGetRequestBodyUriSpec() {

        WebClient.RequestBodyUriSpec requestBodyUriSpec = providerHelperService.getRequestBodyUriSpec("sifToken");
        
        final String[] url = new String[1];
        requestBodyUriSpec.attributes(httpHeaders -> {
            url[0] = (String) httpHeaders.get("org.springframework.web.reactive.function.client.WebClient.uriTemplate");
        });

       assertEquals(viaductUrl, url[0]);
    }
}

And here is the method under test:这是正在测试的方法:

public class ProviderHelperService {

    @Value("${viaduct-url}")
    String viaductUrl;
    
    
    public WebClient.RequestBodyUriSpec getRequestBodyUriSpec(String sifToken) {
        WebClient.RequestBodyUriSpec requestBodyUriSpec = WebClient.create().post();
        requestBodyUriSpec.header("Authorization", sifToken);
        requestBodyUriSpec.uri(viaductUrl);
        return requestBodyUriSpec;
    }

}

The cleanest way to perform such tests is to replace field injection with constructor injection, and then you can quite easily confirm that the value that's passed into the class comes back out the service call.执行此类测试的最简洁方法是将字段注入替换为构造函数注入,然后您可以很容易地确认传递给类的值是否从服务调用中返回。

If you're using Boot, it's usually best to replace use of @Value with @ConfigurationProperties .如果您使用的是 Boot,通常最好将@Value的使用替换为@ConfigurationProperties Depending on the specifics, you can either pass the whole properties object to the service's constructor or write an @Bean configuration method that unpacks the relevant properties and passes them as plain constructor parameters with new .根据具体情况,您可以将整个属性对象传递给服务的构造函数,也可以编写一个@Bean配置方法来解包相关属性并将它们作为普通构造函数参数传递给new

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

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