クライアントアプリケーションのテスト
クライアント側のテストを使用して、RestTemplate
を内部的に使用するコードをテストできます。予想されるリクエストを宣言し、「スタブ」レスポンスを提供することにより、コードの分離テスト(サーバーを実行せずに)に集中できるようになります。次の例は、その方法を示しています。
Java
Kotlin
RestTemplate restTemplate = new RestTemplate();
MockRestServiceServer mockServer = MockRestServiceServer.bindTo(restTemplate).build();
mockServer.expect(requestTo("/greeting")).andRespond(withSuccess());
// Test code that uses the above RestTemplate ...
mockServer.verify();
val restTemplate = RestTemplate()
val mockServer = MockRestServiceServer.bindTo(restTemplate).build()
mockServer.expect(requestTo("/greeting")).andRespond(withSuccess())
// Test code that uses the above RestTemplate ...
mockServer.verify()
上記の例では、MockRestServiceServer
(クライアント側の REST テストの中心クラス)は、RestTemplate
を、期待に反して実際のリクエストをアサートし、「スタブ」レスポンスを返すカスタム ClientHttpRequestFactory
で構成します。この場合、/greeting
へのリクエストが予想され、text/plain
コンテンツを含む 200 レスポンスを返します。必要に応じて、追加の予想リクエストとスタブレスポンスを定義できます。予想されるリクエストとスタブレスポンスを定義する場合、RestTemplate
は通常どおりクライアント側のコードで使用できます。テストの最後に、mockServer.verify()
を使用して、すべての期待が満たされていることを確認できます。
デフォルトでは、リクエストは予想が宣言された順序で予想されます。サーバーの構築時に ignoreExpectOrder
オプションを設定できます。この場合、すべての期待値が(順番に)チェックされ、特定のリクエストに一致するものが見つかります。つまり、リクエストは任意の順序で送信できます。次の例では、ignoreExpectOrder
を使用しています。
Java
Kotlin
server = MockRestServiceServer.bindTo(restTemplate).ignoreExpectOrder(true).build();
server = MockRestServiceServer.bindTo(restTemplate).ignoreExpectOrder(true).build()
デフォルトでは、順序付けされていないリクエストでも、各リクエストは一度だけ実行できます。expect
メソッドは、カウント範囲を指定する ExpectedCount
引数を受け入れるオーバーロードされたバリアントを提供します(たとえば、once
、manyTimes
、max
、min
、between
など)。次の例では times
を使用しています。
Java
Kotlin
RestTemplate restTemplate = new RestTemplate();
MockRestServiceServer mockServer = MockRestServiceServer.bindTo(restTemplate).build();
mockServer.expect(times(2), requestTo("/something")).andRespond(withSuccess());
mockServer.expect(times(3), requestTo("/somewhere")).andRespond(withSuccess());
// ...
mockServer.verify();
val restTemplate = RestTemplate()
val mockServer = MockRestServiceServer.bindTo(restTemplate).build()
mockServer.expect(times(2), requestTo("/something")).andRespond(withSuccess())
mockServer.expect(times(3), requestTo("/somewhere")).andRespond(withSuccess())
// ...
mockServer.verify()
ignoreExpectOrder
が設定されていない場合(デフォルト)、リクエストは宣言の順序で予期される場合、その順序は予期されるリクエストの最初のものにのみ適用されることに注意してください。たとえば、"/something" が 2 回、続いて "/somewhere" が 3 回予想される場合、"/somewhere" へのリクエストがある前に "/something" へのリクエストがあるはずですが、その後の "/something" と "/somewhere" を除いて、リクエストはいつでも来ることができます。
上記のすべての代替として、クライアント側のテストサポートは、RestTemplate
に構成して MockMvc
インスタンスにバインドできる ClientHttpRequestFactory
実装も提供します。これにより、サーバーを実行せずに、実際のサーバー側ロジックを使用してリクエストを処理できます。次の例は、その方法を示しています。
Java
Kotlin
MockMvc mockMvc = MockMvcBuilders.webAppContextSetup(this.wac).build();
this.restTemplate = new RestTemplate(new MockMvcClientHttpRequestFactory(mockMvc));
// Test code that uses the above RestTemplate ...
val mockMvc = MockMvcBuilders.webAppContextSetup(this.wac).build()
restTemplate = RestTemplate(MockMvcClientHttpRequestFactory(mockMvc))
// Test code that uses the above RestTemplate ...
場合によっては、レスポンスをモックする代わりに、リモートサービスへの実際の呼び出しを実行する必要があります。次の例は、ExecutingResponseCreator
を介してそれを行う方法を示しています。
Java
Kotlin
RestTemplate restTemplate = new RestTemplate();
// Create ExecutingResponseCreator with the original request factory
ExecutingResponseCreator withActualResponse = new ExecutingResponseCreator(restTemplate.getRequestFactory());
MockRestServiceServer mockServer = MockRestServiceServer.bindTo(restTemplate).build();
mockServer.expect(requestTo("/profile")).andRespond(withSuccess());
mockServer.expect(requestTo("/quoteOfTheDay")).andRespond(withActualResponse);
// Test code that uses the above RestTemplate ...
mockServer.verify();
val restTemplate = RestTemplate()
// Create ExecutingResponseCreator with the original request factory
val withActualResponse = new ExecutingResponseCreator(restTemplate.getRequestFactory())
val mockServer = MockRestServiceServer.bindTo(restTemplate).build()
mockServer.expect(requestTo("/profile")).andRespond(withSuccess())
mockServer.expect(requestTo("/quoteOfTheDay")).andRespond(withActualResponse)
// Test code that uses the above RestTemplate ...
mockServer.verify()
前の例では、MockRestServiceServer
がレスポンスをモックする別のものに置き換える前に、RestTemplate
の ClientHttpRequestFactory
を使用して ExecutingResponseCreator
を作成します。次に、2 種類のレスポンスで期待値を定義します。
/profile
エンドポイントのスタブ200
レスポンス (実際のリクエストは実行されません)/quoteOfTheDay
エンドポイントへの呼び出しによって取得されたレスポンス
2 番目のケースでは、以前にキャプチャーされた ClientHttpRequestFactory
を介してリクエストが実行されます。これにより、たとえば次のようなレスポンスが生成されます。RestTemplate
が最初に構成された方法に応じて、実際の リモートサーバーから取得されます。
静的インポート
サーバー側のテストと同様に、クライアント側のテスト用の流れるような API には、いくつかの静的インポートが必要です。それらは MockRest*
を検索することで簡単に見つけることができます。Eclipse ユーザーは、MockRestRequestMatchers.*
および MockRestResponseCreators.*
を "Java" →「エディター」→「コンテンツアシスト」→「お気に入り」の Eclipse 設定で「お気に入りの静的メンバー」として追加する必要があります。これにより、静的メソッド名の最初の文字を入力した後にコンテンツアシストを使用できます。他の IDE(IntelliJ など)は、追加の構成を必要としない場合があります。静的メンバーでのコード補完のサポートを確認してください。
クライアント側の REST テストのその他の例
Spring MVC Test 独自のテストには、クライアント側の REST テストのサンプルテストが含 [GitHub] (英語) まれています。