UriComponents

UriComponentsBuilder ΠΏΠΎΠΌΠΎΠ³Π°Π΅Ρ‚ ΡΠΎΠ·Π΄Π°Π²Π°Ρ‚ΡŒ URI-ΠΈΠ΄Π΅Π½Ρ‚ΠΈΡ„ΠΈΠΊΠ°Ρ‚ΠΎΡ€Ρ‹ ΠΈΠ· URI-шаблонов с ΠΏΠ΅Ρ€Π΅ΠΌΠ΅Π½Π½Ρ‹ΠΌΠΈ, ΠΊΠ°ΠΊ ΠΏΠΎΠΊΠ°Π·Π°Π½ΠΎ Π² ΡΠ»Π΅Π΄ΡƒΡŽΡ‰Π΅ΠΌ ΠΏΡ€ΠΈΠΌΠ΅Ρ€Π΅:

Java
UriComponents uriComponents = UriComponentsBuilder
.fromUriString("https://example.com/hotels/{hotel}")
.queryParam("q", "{q}")
.encode()
.build();
URI uri = uriComponents.expand("Westin", "123").toUri();
  1. БтатичСский Ρ„Π°Π±Ρ€ΠΈΡ‡Π½Ρ‹ΠΉ ΠΌΠ΅Ρ‚ΠΎΠ΄ с URI-шаблоном.
  2. ДобавляСм ΠΈΠ»ΠΈ замСняСм URI-ΠΊΠΎΠΌΠΏΠΎΠ½Π΅Π½Ρ‚Ρ‹.
  3. Запрос Π½Π° ΠΊΠΎΠ΄ΠΈΡ€ΠΎΠ²Π°Π½ΠΈΠ΅ URI-шаблона ΠΈ URI-ΠΏΠ΅Ρ€Π΅ΠΌΠ΅Π½Π½Ρ‹Ρ….
  4. Π‘ΠΎΠ±ΠΈΡ€Π°Π΅ΠΌ UriComponents.
  5. Π Π°ΡΡˆΠΈΡ€ΡΠ΅ΠΌ ΠΏΠ΅Ρ€Π΅ΠΌΠ΅Π½Π½Ρ‹Π΅ ΠΈ ΠΏΠΎΠ»ΡƒΡ‡Π°Π΅ΠΌ URI.
Kotlin
val uriComponents = UriComponentsBuilder
.fromUriString("https://example.com/hotels/{hotel}")
.queryParam("q", "{q}")
.encode()
.build()
val uri = uriComponents.expand("Westin", "123").toUri()
  1. БтатичСский Ρ„Π°Π±Ρ€ΠΈΡ‡Π½Ρ‹ΠΉ ΠΌΠ΅Ρ‚ΠΎΠ΄ с URI-шаблоном.
  2. ДобавляСм ΠΈΠ»ΠΈ замСняСм URI-ΠΊΠΎΠΌΠΏΠΎΠ½Π΅Π½Ρ‚Ρ‹.
  3. Запрос Π½Π° ΠΊΠΎΠ΄ΠΈΡ€ΠΎΠ²Π°Π½ΠΈΠ΅ URI-шаблона ΠΈ URI-ΠΏΠ΅Ρ€Π΅ΠΌΠ΅Π½Π½Ρ‹Ρ….
  4. Π‘ΠΎΠ±ΠΈΡ€Π°Π΅ΠΌ UriComponents.
  5. Π Π°ΡΡˆΠΈΡ€ΡΠ΅ΠΌ ΠΏΠ΅Ρ€Π΅ΠΌΠ΅Π½Π½Ρ‹Π΅ ΠΈ ΠΏΠΎΠ»ΡƒΡ‡Π°Π΅ΠΌ URI.

Код ΠΈΠ· ΠΏΡ€Π΅Π΄Ρ‹Π΄ΡƒΡ‰Π΅Π³ΠΎ ΠΏΡ€ΠΈΠΌΠ΅Ρ€Π° ΠΌΠΎΠΆΠ½ΠΎ ΠΎΠ±ΡŠΠ΅Π΄ΠΈΠ½ΠΈΡ‚ΡŒ Π² ΠΎΠ΄Π½Ρƒ Ρ†Π΅ΠΏΠΎΡ‡ΠΊΡƒ ΠΈ ΡΠΎΠΊΡ€Π°Ρ‚ΠΈΡ‚ΡŒ с ΠΏΠΎΠΌΠΎΡ‰ΡŒΡŽ buildAndExpand, ΠΊΠ°ΠΊ ΠΏΠΎΠΊΠ°Π·Π°Π½ΠΎ Π² ΡΠ»Π΅Π΄ΡƒΡŽΡ‰Π΅ΠΌ ΠΏΡ€ΠΈΠΌΠ΅Ρ€Π΅:

Java
URI uri = UriComponentsBuilder
.fromUriString("https://example.com/hotels/{hotel}")
.queryParam("q", "{q}")
.encode()
.buildAndExpand("Westin", "123")
.toUri();
Kotlin
val uri = UriComponentsBuilder
.fromUriString("https://example.com/hotels/{hotel}")
.queryParam("q", "{q}")
.encode()
.buildAndExpand("Westin", "123")
.toUri()

МоТно ΡΠΎΠΊΡ€Π°Ρ‚ΠΈΡ‚ΡŒ Π΅Π³ΠΎ Π΅Ρ‰Π΅ большС ΠΏΡƒΡ‚Π΅ΠΌ нСпосрСдствСнного ΠΏΠ΅Ρ€Π΅Ρ…ΠΎΠ΄Π° ΠΊ URI-ΠΈΠ΄Π΅Π½Ρ‚ΠΈΡ„ΠΈΠΊΠ°Ρ‚ΠΎΡ€Ρƒ (Ρ‡Ρ‚ΠΎ ΠΏΠΎΠ΄Ρ€Π°Π·ΡƒΠΌΠ΅Π²Π°Π΅Ρ‚ ΠΊΠΎΠ΄ΠΈΡ€ΠΎΠ²ΠΊΡƒ), ΠΊΠ°ΠΊ ΠΏΠΎΠΊΠ°Π·Π°Π½ΠΎ Π² ΡΠ»Π΅Π΄ΡƒΡŽΡ‰Π΅ΠΌ ΠΏΡ€ΠΈΠΌΠ΅Ρ€Π΅:

Java
URI uri = UriComponentsBuilder
.fromUriString("https://example.com/hotels/{hotel}")
.queryParam("q", "{q}")
.build("Westin", "123");
Kotlin
val uri = UriComponentsBuilder
.fromUriString("https://example.com/hotels/{hotel}")
.queryParam("q", "{q}")
.build("Westin", "123")

МоТно ΡΠΎΠΊΡ€Π°Ρ‚ΠΈΡ‚ΡŒ Π΅Π³ΠΎ Π΄Π°ΠΆΠ΅ Π΅Ρ‰Π΅ большС с ΠΏΠΎΠΌΠΎΡ‰ΡŒΡŽ ΠΏΠΎΠ»Π½ΠΎΠ³ΠΎ URI-шаблона, ΠΊΠ°ΠΊ ΠΏΠΎΠΊΠ°Π·Π°Π½ΠΎ Π² ΡΠ»Π΅Π΄ΡƒΡŽΡ‰Π΅ΠΌ ΠΏΡ€ΠΈΠΌΠ΅Ρ€Π΅:

Java
URI uri = UriComponentsBuilder
.fromUriString("https://example.com/hotels/{hotel}?q={q}")
.build("Westin", "123");
Kotlin
val uri = UriComponentsBuilder
.fromUriString("https://example.com/hotels/{hotel}?q={q}")
.build("Westin", "123")

UriBuilder

UriComponentsBuilder Ρ€Π΅Π°Π»ΠΈΠ·ΡƒΠ΅Ρ‚ UriBuilder. Π’ свою ΠΎΡ‡Π΅Ρ€Π΅Π΄ΡŒ, ΠΌΠΎΠΆΠ½ΠΎ ΡΠΎΠ·Π΄Π°Ρ‚ΡŒ UriBuilder с ΠΏΠΎΠΌΠΎΡ‰ΡŒΡŽ UriBuilderFactory. ВмСстС UriBuilderFactory ΠΈ UriBuilder ΠΏΡ€Π΅Π΄ΠΎΡΡ‚Π°Π²Π»ΡΡŽΡ‚ ΠΏΠΎΠ΄ΠΊΠ»ΡŽΡ‡Π°Π΅ΠΌΡ‹ΠΉ ΠΌΠ΅Ρ…Π°Π½ΠΈΠ·ΠΌ для создания URI-ΠΈΠ΄Π΅Π½Ρ‚ΠΈΡ„ΠΈΠΊΠ°Ρ‚ΠΎΡ€ΠΎΠ² ΠΈΠ· URI-шаблонов Π½Π° основС ΠΎΠ±Ρ‰Π΅ΠΉ ΠΊΠΎΠ½Ρ„ΠΈΠ³ΡƒΡ€Π°Ρ†ΠΈΠΈ, Ρ‚Π°ΠΊΠΎΠΉ ΠΊΠ°ΠΊ Π±Π°Π·ΠΎΠ²Ρ‹ΠΉ URL-адрСс, ΠΏΠ°Ρ€Π°ΠΌΠ΅Ρ‚Ρ€Ρ‹ ΠΊΠΎΠ΄ΠΈΡ€ΠΎΠ²ΠΊΠΈ ΠΈ Π΄Ρ€ΡƒΠ³ΠΈΠ΅ Π΄Π΅Ρ‚Π°Π»ΠΈ.

МоТно ΡΠΊΠΎΠ½Ρ„ΠΈΠ³ΡƒΡ€ΠΈΡ€ΠΎΠ²Π°Ρ‚ΡŒ RestTemplate ΠΈ WebClient с ΠΏΠΎΠΌΠΎΡ‰ΡŒΡŽ UriBuilderFactory, Ρ‡Ρ‚ΠΎΠ±Ρ‹ Π½Π°ΡΡ‚Ρ€ΠΎΠΈΡ‚ΡŒ ΠΏΠΎΠ΄Π³ΠΎΡ‚ΠΎΠ²ΠΊΡƒ URI-ΠΈΠ΄Π΅Π½Ρ‚ΠΈΡ„ΠΈΠΊΠ°Ρ‚ΠΎΡ€ΠΎΠ². DefaultUriBuilderFactory - это рСализация UriBuilderFactory ΠΏΠΎ ΡƒΠΌΠΎΠ»Ρ‡Π°Π½ΠΈΡŽ, которая ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΠ΅Ρ‚ UriComponentsBuilder Π½Π° Π²Π½ΡƒΡ‚Ρ€Π΅Π½Π½Π΅ΠΌ ΡƒΡ€ΠΎΠ²Π½Π΅ ΠΈ ΠΎΡ‚ΠΊΡ€Ρ‹Π²Π°Π΅Ρ‚ ΠΎΠ±Ρ‰ΠΈΠ΅ ΠΏΠ°Ρ€Π°ΠΌΠ΅Ρ‚Ρ€Ρ‹ ΠΊΠΎΠ½Ρ„ΠΈΠ³ΡƒΡ€Π°Ρ†ΠΈΠΈ.

Π’ ΡΠ»Π΅Π΄ΡƒΡŽΡ‰Π΅ΠΌ ΠΏΡ€ΠΈΠΌΠ΅Ρ€Π΅ ΠΏΠΎΠΊΠ°Π·Π°Π½ΠΎ, ΠΊΠ°ΠΊ ΡΠΊΠΎΠ½Ρ„ΠΈΠ³ΡƒΡ€ΠΈΡ€ΠΎΠ²Π°Ρ‚ΡŒ Ρ‚Π°ΠΊΠΎΠΉ Π±ΠΈΠ½:

Java
// import org.springframework.web.util.DefaultUriBuilderFactory.EncodingMode;
String baseUrl = "https://example.org";
DefaultUriBuilderFactory factory = new DefaultUriBuilderFactory(baseUrl);
factory.setEncodingMode(EncodingMode.TEMPLATE_AND_VALUES);
RestTemplate restTemplate = new RestTemplate();
restTemplate.setUriTemplateHandler(factory);
Kotlin
// import org.springframework.web.util.DefaultUriBuilderFactory.EncodingMode
val baseUrl = "https://example.org"
val factory = DefaultUriBuilderFactory(baseUrl)
factory.encodingMode = EncodingMode.TEMPLATE_AND_VALUES
val restTemplate = RestTemplate()
restTemplate.uriTemplateHandler = factory

Π’ ΡΠ»Π΅Π΄ΡƒΡŽΡ‰Π΅ΠΌ ΠΏΡ€ΠΈΠΌΠ΅Ρ€Π΅ конфигурируСтся WebClient:

Java
// import org.springframework.web.util.DefaultUriBuilderFactory.EncodingMode;
String baseUrl = "https://example.org";
DefaultUriBuilderFactory factory = new DefaultUriBuilderFactory(baseUrl);
factory.setEncodingMode(EncodingMode.TEMPLATE_AND_VALUES);
WebClient client = WebClient.builder().uriBuilderFactory(factory).build();
Kotlin
// import org.springframework.web.util.DefaultUriBuilderFactory.EncodingMode
val baseUrl = "https://example.org"
val factory = DefaultUriBuilderFactory(baseUrl)
factory.encodingMode = EncodingMode.TEMPLATE_AND_VALUES
val client = WebClient.builder().uriBuilderFactory(factory).build()

ΠšΡ€ΠΎΠΌΠ΅ Ρ‚ΠΎΠ³ΠΎ, ΠΌΠΎΠΆΠ½ΠΎ ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΠΎΠ²Π°Ρ‚ΡŒ DefaultUriBuilderFactory Π½Π°ΠΏΡ€ΡΠΌΡƒΡŽ. Π­Ρ‚ΠΎ ΠΏΠΎΡ…ΠΎΠΆΠ΅ Π½Π° использованиС UriComponentsBuilder, Π½ΠΎ вмСсто статичСских Ρ„Π°Π±Ρ€ΠΈΡ‡Π½Ρ‹Ρ… ΠΌΠ΅Ρ‚ΠΎΠ΄ΠΎΠ², это Ρ€Π΅Π°Π»ΡŒΠ½Ρ‹ΠΉ экзСмпляр, ΠΊΠΎΡ‚ΠΎΡ€Ρ‹ΠΉ Ρ…Ρ€Π°Π½ΠΈΡ‚ ΠΊΠΎΠ½Ρ„ΠΈΠ³ΡƒΡ€Π°Ρ†ΠΈΡŽ ΠΈ ΠΏΠ°Ρ€Π°ΠΌΠ΅Ρ‚Ρ€Ρ‹, ΠΊΠ°ΠΊ ΠΏΠΎΠΊΠ°Π·Π°Π½ΠΎ Π² ΡΠ»Π΅Π΄ΡƒΡŽΡ‰Π΅ΠΌ ΠΏΡ€ΠΈΠΌΠ΅Ρ€Π΅:

Java
String baseUrl = "https://example.com";
DefaultUriBuilderFactory uriBuilderFactory = new DefaultUriBuilderFactory(baseUrl);
URI uri = uriBuilderFactory.uriString("/hotels/{hotel}")
.queryParam("q", "{q}")
.build("Westin", "123");
Kotlin
val baseUrl = "https://example.com"
val uriBuilderFactory = DefaultUriBuilderFactory(baseUrl)
val uri = uriBuilderFactory.uriString("/hotels/{hotel}")
.queryParam("q", "{q}")
.build("Westin", "123")

ΠšΠΎΠ΄ΠΈΡ€ΠΎΠ²Π°Π½ΠΈΠ΅ URI

UriComponentsBuilder ΠΎΡ‚ΠΊΡ€Ρ‹Π²Π°Π΅Ρ‚ ΠΎΠΏΡ†ΠΈΠΈ кодирования Π½Π° Π΄Π²ΡƒΡ… уровнях:

  • UriComponentsBuilder#encode(): Π‘Π½Π°Ρ‡Π°Π»Π° ΠΏΡ€Π΅Π΄Π²Π°Ρ€ΠΈΡ‚Π΅Π»ΡŒΠ½ΠΎ ΠΊΠΎΠ΄ΠΈΡ€ΡƒΠ΅Ρ‚ URI-шаблон, Π° Π·Π°Ρ‚Π΅ΠΌ строго ΠΊΠΎΠ΄ΠΈΡ€ΡƒΠ΅Ρ‚ URI-ΠΏΠ΅Ρ€Π΅ΠΌΠ΅Π½Π½Ρ‹Π΅ ΠΏΡ€ΠΈ Ρ€Π°ΡΡˆΠΈΡ€Π΅Π½ΠΈΠΈ.

  • UriComponents#encode(): ΠšΠΎΠ΄ΠΈΡ€ΡƒΠ΅Ρ‚ URI-ΠΊΠΎΠΌΠΏΠΎΠ½Π΅Π½Ρ‚Ρ‹ послС Ρ€Π°ΡΡˆΠΈΡ€Π΅Π½ΠΈΡ URI-ΠΏΠ΅Ρ€Π΅ΠΌΠ΅Π½Π½Ρ‹Ρ….

ОбС ΠΎΠΏΡ†ΠΈΠΈ Π·Π°ΠΌΠ΅Π½ΡΡŽΡ‚ символы, Π½Π΅ относящиСся ΠΊ стандарту ASCII, ΠΈ нСдопустимыС символы Π½Π° экранированныС ΠΎΠΊΡ‚Π΅Ρ‚Ρ‹. Однако ΠΏΠ΅Ρ€Π²Ρ‹ΠΉ Π²Π°Ρ€ΠΈΠ°Π½Ρ‚ Ρ‚Π°ΠΊΠΆΠ΅ замСняСт символы с Π·Π°Ρ€Π΅Π·Π΅Ρ€Π²ΠΈΡ€ΠΎΠ²Π°Π½Π½Ρ‹ΠΌ Π·Π½Π°Ρ‡Π΅Π½ΠΈΠ΅ΠΌ, ΠΊΠΎΡ‚ΠΎΡ€Ρ‹Π΅ ΠΏΠΎΡΠ²Π»ΡΡŽΡ‚ΡΡ Π² ΠΏΠ΅Ρ€Π΅ΠΌΠ΅Π½Π½Ρ‹Ρ….

Рассмотрим ";", ΠΊΠΎΡ‚ΠΎΡ€Ρ‹ΠΉ являСтся допустимым Π² ΠΏΡƒΡ‚ΠΈ, Π½ΠΎ ΠΈΠΌΠ΅Π΅Ρ‚ Π·Π°Ρ€Π΅Π·Π΅Ρ€Π²ΠΈΡ€ΠΎΠ²Π°Π½Π½ΠΎΠ΅ Π·Π½Π°Ρ‡Π΅Π½ΠΈΠ΅. ΠŸΠ΅Ρ€Π²Ρ‹ΠΉ Π²Π°Ρ€ΠΈΠ°Π½Ρ‚ замСняСт ";" Π½Π° "%3B" Π² ΠΏΠ΅Ρ€Π΅ΠΌΠ΅Π½Π½Ρ‹Ρ…, Π½ΠΎ Π½Π΅ Π² URI-шаблонС. Π’ ΠΎΡ‚Π»ΠΈΡ‡ΠΈΠ΅ ΠΎΡ‚ этого, Π²Ρ‚ΠΎΡ€ΠΎΠΉ Π²Π°Ρ€ΠΈΠ°Π½Ρ‚ Π½ΠΈΠΊΠΎΠ³Π΄Π° Π½Π΅ замСняСт ";", ΠΏΠΎΡΠΊΠΎΠ»ΡŒΠΊΡƒ ΠΎΠ½ являСтся допустимым символом Π² ΠΏΡƒΡ‚ΠΈ.

Π’ Π±ΠΎΠ»ΡŒΡˆΠΈΠ½ΡΡ‚Π²Π΅ случаСв ΠΏΠ΅Ρ€Π²Ρ‹ΠΉ Π²Π°Ρ€ΠΈΠ°Π½Ρ‚, скорСС всСго, даст ΠΎΠΆΠΈΠ΄Π°Π΅ΠΌΡ‹ΠΉ Ρ€Π΅Π·ΡƒΠ»ΡŒΡ‚Π°Ρ‚, ΠΏΠΎΡΠΊΠΎΠ»ΡŒΠΊΡƒ ΠΎΠ½ ΡƒΡ‡ΠΈΡ‚Ρ‹Π²Π°Π΅Ρ‚ URI-ΠΏΠ΅Ρ€Π΅ΠΌΠ΅Π½Π½Ρ‹Π΅ ΠΊΠ°ΠΊ Π½Π΅ΠΏΡ€ΠΎΠ·Ρ€Π°Ρ‡Π½Ρ‹Π΅ Π΄Π°Π½Π½Ρ‹Π΅, ΠΊΠΎΡ‚ΠΎΡ€Ρ‹Π΅ Π΄ΠΎΠ»ΠΆΠ½Ρ‹ Π±Ρ‹Ρ‚ΡŒ ΠΏΠΎΠ»Π½ΠΎΡΡ‚ΡŒΡŽ Π·Π°ΠΊΠΎΠ΄ΠΈΡ€ΠΎΠ²Π°Π½Ρ‹, Π² Ρ‚ΠΎ врСмя ΠΊΠ°ΠΊ Π²Ρ‚ΠΎΡ€ΠΎΠΉ Π²Π°Ρ€ΠΈΠ°Π½Ρ‚ ΠΏΠΎΠ»Π΅Π·Π΅Π½, Ссли URI-ΠΏΠ΅Ρ€Π΅ΠΌΠ΅Π½Π½Ρ‹Π΅ Π½Π°ΠΌΠ΅Ρ€Π΅Π½Π½ΠΎ содСрТат Π·Π°Ρ€Π΅Π·Π΅Ρ€Π²ΠΈΡ€ΠΎΠ²Π°Π½Π½Ρ‹Π΅ символы. Π’Ρ‚ΠΎΡ€ΠΎΠΉ Π²Π°Ρ€ΠΈΠ°Π½Ρ‚ Ρ‚Π°ΠΊΠΆΠ΅ Ρ€Π°Π±ΠΎΡ‚Π°Π΅Ρ‚, Ссли Π½Π΅ Ρ€Π°ΡΡˆΠΈΡ€ΡΡ‚ΡŒ URI-ΠΏΠ΅Ρ€Π΅ΠΌΠ΅Π½Π½Ρ‹Π΅ Π²ΠΎΠΎΠ±Ρ‰Π΅, ΠΏΠΎΡΠΊΠΎΠ»ΡŒΠΊΡƒ Π² этом случаС кодируСтся всС, Ρ‡Ρ‚ΠΎ случайным ΠΎΠ±Ρ€Π°Π·ΠΎΠΌ Π±ΡƒΠ΄Π΅Ρ‚ ΠΏΠΎΡ…ΠΎΠΆΠ΅ Π½Π° URI-ΠΏΠ΅Ρ€Π΅ΠΌΠ΅Π½Π½ΡƒΡŽ.

Π’ ΡΠ»Π΅Π΄ΡƒΡŽΡ‰Π΅ΠΌ ΠΏΡ€ΠΈΠΌΠ΅Ρ€Π΅ ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΠ΅Ρ‚ΡΡ ΠΏΠ΅Ρ€Π²Ρ‹ΠΉ Π²Π°Ρ€ΠΈΠ°Π½Ρ‚:

Java
URI uri = UriComponentsBuilder.fromPath("/hotel list/{city}")
.queryParam("q", "{q}")
.encode()
.buildAndExpand("New York", "foo+bar")
.toUri();
// Π Π΅Π·ΡƒΠ»ΡŒΡ‚Π°Ρ‚ "/hotel%20list/New%20York?q=foo%2Bbar"
Kotlin
val uri = UriComponentsBuilder.fromPath("/hotel list/{city}")
.queryParam("q", "{q}")
.encode()
.buildAndExpand("New York", "foo+bar")
.toUri()
// Π Π΅Π·ΡƒΠ»ΡŒΡ‚Π°Ρ‚ "/hotel%20list/New%20York?q=foo%2Bbar"

МоТно ΡΠΎΠΊΡ€Π°Ρ‚ΠΈΡ‚ΡŒ ΠΊΠΎΠ΄ Π² ΠΏΡ€Π΅Π΄Ρ‹Π΄ΡƒΡ‰Π΅ΠΌ ΠΏΡ€ΠΈΠΌΠ΅Ρ€Π΅ ΠΏΡƒΡ‚Π΅ΠΌ нСпосрСдствСнного ΠΏΠ΅Ρ€Π΅Ρ…ΠΎΠ΄Π° ΠΊ URI-ΠΈΠ΄Π΅Π½Ρ‚ΠΈΡ„ΠΈΠΊΠ°Ρ‚ΠΎΡ€Ρƒ (Ρ‡Ρ‚ΠΎ ΠΏΠΎΠ΄Ρ€Π°Π·ΡƒΠΌΠ΅Π²Π°Π΅Ρ‚ ΠΊΠΎΠ΄ΠΈΡ€ΠΎΠ²ΠΊΡƒ), ΠΊΠ°ΠΊ ΠΏΠΎΠΊΠ°Π·Π°Π½ΠΎ Π² ΡΠ»Π΅Π΄ΡƒΡŽΡ‰Π΅ΠΌ ΠΏΡ€ΠΈΠΌΠ΅Ρ€Π΅:

Java
URI uri = UriComponentsBuilder.fromPath("/hotel list/{city}")
.queryParam("q", "{q}")
.build("New York", "foo+bar");
Kotlin
val uri = UriComponentsBuilder.fromPath("/hotel list/{city}")
.queryParam("q", "{q}")
.build("New York", "foo+bar")

МоТно ΡΠΎΠΊΡ€Π°Ρ‚ΠΈΡ‚ΡŒ Π΅Π³ΠΎ Π΄Π°ΠΆΠ΅ Π΅Ρ‰Π΅ большС с ΠΏΠΎΠΌΠΎΡ‰ΡŒΡŽ ΠΏΠΎΠ»Π½ΠΎΠ³ΠΎ URI-шаблона, ΠΊΠ°ΠΊ ΠΏΠΎΠΊΠ°Π·Π°Π½ΠΎ Π² ΡΠ»Π΅Π΄ΡƒΡŽΡ‰Π΅ΠΌ ΠΏΡ€ΠΈΠΌΠ΅Ρ€Π΅:

Java
URI uri = UriComponentsBuilder.fromUriString("/hotel list/{city}?q={q}")
.build("New York", "foo+bar");
Kotlin
val uri = UriComponentsBuilder.fromUriString("/hotel list/{city}?q={q}")
.build("New York", "foo+bar")

WebClient ΠΈ RestTemplate Ρ€Π°ΡΡˆΠΈΡ€ΡΡŽΡ‚ ΠΈ ΠΊΠΎΠ΄ΠΈΡ€ΡƒΡŽΡ‚ URI-ΡˆΠ°Π±Π»ΠΎΠ½Ρ‹ Π½Π° Π²Π½ΡƒΡ‚Ρ€Π΅Π½Π½Π΅ΠΌ ΡƒΡ€ΠΎΠ²Π½Π΅ с ΠΏΠΎΠΌΠΎΡ‰ΡŒΡŽ стратСгии UriBuilderFactory. Оба Π²Π°Ρ€ΠΈΠ°Π½Ρ‚Π° ΠΌΠΎΠΆΠ½ΠΎ ΡΠΊΠΎΠ½Ρ„ΠΈΠ³ΡƒΡ€ΠΈΡ€ΠΎΠ²Π°Ρ‚ΡŒ с ΠΏΠΎΠΌΠΎΡ‰ΡŒΡŽ кастомной стратСгии, ΠΊΠ°ΠΊ ΠΏΠΎΠΊΠ°Π·Π°Π½ΠΎ Π² ΡΠ»Π΅Π΄ΡƒΡŽΡ‰Π΅ΠΌ ΠΏΡ€ΠΈΠΌΠ΅Ρ€Π΅:

Java
String baseUrl = "https://example.com";
DefaultUriBuilderFactory factory = new DefaultUriBuilderFactory(baseUrl)
factory.setEncodingMode(EncodingMode.TEMPLATE_AND_VALUES);
// НастраиваСм RestTemplate...
RestTemplate restTemplate = new RestTemplate();
restTemplate.setUriTemplateHandler(factory);
// НастраиваСм WebClient...
WebClient client = WebClient.builder().uriBuilderFactory(factory).build();
Kotlin
val baseUrl = "https://example.com"
val factory = DefaultUriBuilderFactory(baseUrl).apply {
encodingMode = EncodingMode.TEMPLATE_AND_VALUES
}
// НастраиваСм RestTemplate...
val restTemplate = RestTemplate().apply {
uriTemplateHandler = factory
}
// НастраиваСм WebClient...
val client = WebClient.builder().uriBuilderFactory(factory).build()

РСализация DefaultUriBuilderFactory ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΠ΅Ρ‚ UriComponentsBuilder Π½Π° Π²Π½ΡƒΡ‚Ρ€Π΅Π½Π½Π΅ΠΌ ΡƒΡ€ΠΎΠ²Π½Π΅ для Ρ€Π°ΡΡˆΠΈΡ€Π΅Π½ΠΈΡ ΠΈ кодирования URI-шаблонов. Как Ρ„Π°Π±Ρ€ΠΈΠΊΠ°, ΠΎΠ½Π° прСдоставляСт Π΅Π΄ΠΈΠ½ΠΎΠ΅ мСсто для конфигурирования ΠΏΠΎΠ΄Ρ…ΠΎΠ΄Π° ΠΊ ΠΊΠΎΠ΄ΠΈΡ€ΠΎΠ²Π°Π½ΠΈΡŽ, основанного Π½Π° ΠΎΠ΄Π½ΠΎΠΌ ΠΈΠ· пСрСчислСнных Π½ΠΈΠΆΠ΅ Ρ€Π΅ΠΆΠΈΠΌΠΎΠ² кодирования:

  • TEMPLATE_AND_VALUES: Π˜ΡΠΏΠΎΠ»ΡŒΠ·ΡƒΠ΅Ρ‚ UriComponentsBuilder#encode (), ΡΠΎΠΎΡ‚Π²Π΅Ρ‚ΡΡ‚Π²ΡƒΡŽΡ‰ΠΈΠΉ ΠΏΠ΅Ρ€Π²ΠΎΠΉ ΠΎΠΏΡ†ΠΈΠΈ Π² ΠΏΡ€Π΅Π΄Ρ‹Π΄ΡƒΡ‰Π΅ΠΌ спискС, для ΠΏΡ€Π΅Π΄Π²Π°Ρ€ΠΈΡ‚Π΅Π»ΡŒΠ½ΠΎΠ³ΠΎ кодирования URI-шаблона ΠΈ строгого кодирования ΠΏΠ΅Ρ€Π΅ΠΌΠ΅Π½Π½Ρ‹Ρ… ΠΏΡ€ΠΈ Ρ€Π°ΡΡˆΠΈΡ€Π΅Π½ΠΈΠΈ.

  • VALUES_ONLY: НС ΠΊΠΎΠ΄ΠΈΡ€ΡƒΠ΅Ρ‚ URI-шаблон ΠΈ, вмСсто этого, примСняСт строгоС ΠΊΠΎΠ΄ΠΈΡ€ΠΎΠ²Π°Π½ΠΈΠ΅ ΠΊ ΠΏΠ΅Ρ€Π΅ΠΌΠ΅Π½Π½Ρ‹ΠΌ URI-ΠΈΠ΄Π΅Π½Ρ‚ΠΈΡ„ΠΈΠΊΠ°Ρ‚ΠΎΡ€ΠΎΠ² Ρ‡Π΅Ρ€Π΅Π· UriUtils#encodeUriVariables ΠΏΠ΅Ρ€Π΅Π΄ Ρ‚Π΅ΠΌ, ΠΊΠ°ΠΊ Ρ€Π°ΡΡˆΠΈΡ€ΠΈΡ‚ΡŒ ΠΈΡ… Π² шаблон.

  • URI_COMPONENT: Π˜ΡΠΏΠΎΠ»ΡŒΠ·ΡƒΠ΅Ρ‚ UriComponents#encode(), ΡΠΎΠΎΡ‚Π²Π΅Ρ‚ΡΡ‚Π²ΡƒΡŽΡ‰ΠΈΠΉ Π²Ρ‚ΠΎΡ€ΠΎΠΌΡƒ Π²Π°Ρ€ΠΈΠ°Π½Ρ‚Ρƒ Π² ΠΏΡ€Π΅Π΄Ρ‹Π΄ΡƒΡ‰Π΅ΠΌ спискС, для кодирования значСния ΠΊΠΎΠΌΠΏΠΎΠ½Π΅Π½Ρ‚Π° URI-ΠΈΠ΄Π΅Π½Ρ‚ΠΈΡ„ΠΈΠΊΠ°Ρ‚ΠΎΡ€Π° послС Ρ€Π°ΡΡˆΠΈΡ€Π΅Π½ΠΈΡ URI-ΠΏΠ΅Ρ€Π΅ΠΌΠ΅Π½Π½Ρ‹Ρ….

  • NONE ΠšΠΎΠ΄ΠΈΡ€ΠΎΠ²Π°Π½ΠΈΠ΅ Π½Π΅ примСняСтся.

RestTemplate установлСн Π² EncodingMode.URI_COMPONENT ΠΏΠΎ историчСским ΠΏΡ€ΠΈΡ‡ΠΈΠ½Π°ΠΌ ΠΈ для ΠΎΠ±Ρ€Π°Ρ‚Π½ΠΎΠΉ совмСстимости. WebClient обращаСтся ΠΊ Π·Π½Π°Ρ‡Π΅Π½ΠΈΡŽ ΠΏΠΎ ΡƒΠΌΠΎΠ»Ρ‡Π°Π½ΠΈΡŽ Π² DefaultUriBuilderFactory, ΠΊΠΎΡ‚ΠΎΡ€ΠΎΠ΅ Π±Ρ‹Π»ΠΎ ΠΈΠ·ΠΌΠ΅Π½Π΅Π½ΠΎ с EncodingMode.URI_COMPONENT Π² 5.0.x Π½Π° EncodingMode.TEMPLATE_AND_VALUES Π² 5.1.