同期使用

WebClient は、結果の最後でブロックすることにより、同期スタイルで使用できます。

  • Java

  • Kotlin

Person person = client.get().uri("/person/{id}", i).retrieve()
	.bodyToMono(Person.class)
	.block();

List<Person> persons = client.get().uri("/persons").retrieve()
	.bodyToFlux(Person.class)
	.collectList()
	.block();
val person = runBlocking {
	client.get().uri("/person/{id}", i).retrieve()
			.awaitBody<Person>()
}

val persons = runBlocking {
	client.get().uri("/persons").retrieve()
			.bodyToFlow<Person>()
			.toList()
}

ただし、複数の呼び出しを行う必要がある場合は、各レスポンスを個別にブロックするのを避け、代わりに結合された結果を待つ方が効率的です。

  • Java

  • Kotlin

Mono<Person> personMono = client.get().uri("/person/{id}", personId)
		.retrieve().bodyToMono(Person.class);

Mono<List<Hobby>> hobbiesMono = client.get().uri("/person/{id}/hobbies", personId)
		.retrieve().bodyToFlux(Hobby.class).collectList();

Map<String, Object> data = Mono.zip(personMono, hobbiesMono, (person, hobbies) -> {
			Map<String, String> map = new LinkedHashMap<>();
			map.put("person", person);
			map.put("hobbies", hobbies);
			return map;
		})
		.block();
val data = runBlocking {
		val personDeferred = async {
			client.get().uri("/person/{id}", personId)
					.retrieve().awaitBody<Person>()
		}

		val hobbiesDeferred = async {
			client.get().uri("/person/{id}/hobbies", personId)
					.retrieve().bodyToFlow<Hobby>().toList()
		}

		mapOf("person" to personDeferred.await(), "hobbies" to hobbiesDeferred.await())
	}

上記はほんの一例です。最後までブロックすることなく、多くの リモート呼び出しを行うリアクティブパイプラインをまとめるパターンや演算子は他にもたくさんあります。

Flux または Mono を使用すると、Spring MVC または Spring WebFlux コントローラーでブロックする必要はありません。コントローラーメソッドから結果のリアクティブ型を返すだけです。同じ原則が Kotlin コルーチンと Spring WebFlux に適用されます。コントローラーメソッドで一時停止関数を使用するか、Flow を返すだけです。