web-dev-qa-db-ja.com

Spring TestRestTemplateを構成する方法

JUnitテストでテストしたいREST(spring-hateoas)サーバーがあるので、自動注入されたTestRestTemplateを使用しています。

しかし、この事前構成されたTestRestTemplateに構成を追加するにはどうすればよいですか? rootURIを構成してインターセプターを追加する必要があります。

これは私のJUnit Testクラスです:

@RunWith(SpringRunner.class)
@ActiveProfiles("test")
@SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT)      

public class RestEndpointTests {
  private Logger log = LoggerFactory.getLogger(this.getClass());

  @LocalServerPort
  int localServerPort;

  @Value(value = "${spring.data.rest.base-path}")   // Nice trick to get basePath from application.properties
  String basePath;

  @Autowired
  TestRestTemplate client;    //  how to configure client?

  [... here are my @Test methods that use client ...]
}

ドキュメントは静的@TestConfigurationクラスを使用できます。 しかし、その静的クラス内ではlocalServerPortまたはbasePathにアクセスできません。

  @TestConfiguration
  static class Config {

    @Bean
    public RestTemplateBuilder restTemplateBuilder() {
      String rootUri = "http://localhost:"+localServerPort+basePath;    // <=== DOES NOT WORK
      log.trace("Creating and configuring RestTemplate for "+rootUri);
      return new RestTemplateBuilder()
        .basicAuthorization(TestFixtures.USER1_EMAIL, TestFixtures.USER1_PWD)
        .errorHandler(new LiquidoTestErrorHandler())
        .requestFactory(new HttpComponentsClientHttpRequestFactory())
        .additionalInterceptors(new LogRequestInterceptor())
        .rootUri(rootUri);
    }

  }

私の最も重要な質問:なぜTestRestTemplate服用しないspring.data.rest.base-pathからapplication.propertiesそもそも考慮に入れていますか?このラッパークラスのユースケース全体で、完全に事前構成されているという考えではありませんか?

ドクサイス

@SpringBootTestアノテーションを使用している場合、TestRestTemplateが自動的に使用可能になり、@ Autowiredを使用してテストできます。カスタマイズが必要な場合(追加のメッセージコンバーターの追加など)、RestTemplateBuilder @Beanを使用します。

完全なJavaコード例では、それはどのように見えますか?

11
Robert

私はこれが古い質問であることを知っています。おそらくあなたはおそらくこれまでに別の解決策を見つけたでしょう。しかし、私はとにかく私がそれにつまずく他の人のためにとにかく答えています。同様の問題があり、@ TestConfigurationを使用する代わりに、好みに合わせて構成されたTestRestTemplateを作成するために、テストクラスで@PostConstructを使用することになりました。

    @RunWith(SpringJUnit4ClassRunner.class)
    @EnableAutoConfiguration
    @SpringBootTest(classes = {BackendApplication.class}, webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT)
    public class MyCookieClientTest {
        @LocalServerPort
        int localPort;

        @Autowired
        RestTemplateBuilder restTemplateBuilder;

        private TestRestTemplate template;

        @PostConstruct
        public void initialize() {
            RestTemplate customTemplate = restTemplateBuilder
                .rootUri("http://localhost:"+localPort)
                ....
                .build();
            this.template = new TestRestTemplate(customTemplate,
                 null, null, //I don't use basic auth, if you do you can set user, pass here
                 HttpClientOption.ENABLE_COOKIES); // I needed cookie support in this particular test, you may not have this need
        }
    }
12
joensson

TestRestTemplateを構成するために、公式の documentation は、以下の例に示すように(たとえば、基本認証を追加するために)TestRestTemplateを使用することを提案します。

public class YourEndpointClassTest {
    private static final Logger logger = LoggerFactory.getLogger(YourEndpointClassTest.class);  

    private static final String BASE_URL = "/your/base/url";

    @TestConfiguration
    static class TestRestTemplateAuthenticationConfiguration {

        @Value("${spring.security.user.name}")
        private String userName;

        @Value("${spring.security.user.password}")
        private String password;

        @Bean
        public RestTemplateBuilder restTemplateBuilder() {
            return new RestTemplateBuilder().basicAuthentication(userName, password);
        }
    }


    @Autowired
    private TestRestTemplate restTemplate;

//here add your tests...
3
dcormar

テスト環境でリモートサーバーのRESTエンドポイントにアクセスするためにTestRestTemplateを使用する必要がある場合に、テストでSpring Bootアプリケーションが起動しなかったため、リモートエンドポイントに接続してRESTサービスをそこから消費しただけでなく、テストの構成はより単純で、複雑なSpring(Boot)コンテキストを構築しなかったため、実行はより高速でした。ここでは私の設定からの抜粋です:

@RunWith(SpringRunner.class)
public class RemoteRestTestAbstract {

protected TestRestTemplate restTemplate;
private static RestTemplateBuilder restTemplateBuilder;


@BeforeClass
public static void setUpClass() {
    restTemplateBuilder = new RestTemplateBuilder()
        .rootUri("http://my-remote-test-server.my-domain.com:8080/");
}

@Before
public void init() {
    restTemplate = new TestRestTemplate(restTemplateBuilder);
    login();
}

//...

}
0
tanacsg