post-image

WebClient trong Spring Boot là gì ?

Tổng quan

Ở bài viết trước mình đã giới thiệu cho các bạn về khái niệm RestTemplate trong Spring. Bài viết này mình sẽ giới thiệu tới các bạn một interface có chức năng tương tự như RestTemplate nhưng mới hơn đó là WebClient.

WebClient là gì ?

  • WebClient có thể hiểu đơn giản là một interface đại diện cho một entry point chính thực hiện các request.
  • Nó được tạo ra như là một phần của module Spring Web Reactive và thay thế cho class RestTemplate cũ.
  • Nó là interface chỉ có duy nhất một triển khai đó là class DefaultWebClient và đây cũng là class mà chúng ta sẽ sử dụng.

Cấu hình thư viện

Sử dụng Maven

Thêm các thư viện sau vào trong file porm.xml

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-webflux</artifactId>
</dependency>
<dependency>
    <groupId>org.projectreactor</groupId>
    <artifactId>reactor-spring</artifactId>
    <version>1.0.1.RELEASE</version>
</dependency>Code language: HTML, XML (xml)

Sử dụng Gradle

Với Gradle chúng ta thêm thư viện vào trong file build.gradle

dependencies {
    compile 'org.springframework.boot:spring-boot-starter-webflux'
    compile 'org.projectreactor:reactor-spring:1.0.1.RELEASE'
}Code language: JavaScript (javascript)

Làm thế nào để sử dụng WebClient ?

Để sử dụng được WebClient chúng ta cần biết những cái như sau:

  • Cách để tạo ra một thể hiện
  • Cách tạo ra một request
  • Cách xử lý một response

Tạo một thể hiện của WebClient

Chúng ta sẽ có ba lựa chọn để tạo ra một thể hiện của WebClient đó là

  • Tạo ra một đối tượng WebClient với cấu hình mặc định:
WebClient client1 = WebClient.create();
  • Tạo một đối tượng WebClient với tham số URI:
WebClient client2 = WebClient.create("http://localhost:8080");
Code language: JavaScript (javascript)
  • Cuối cùng đó là chúng ta tạo ra một đối tượng WebClient bằng cách sử dụng class DefaultWebClientBuilder như sau:
	WebClient client3 = WebClient
  .builder()
    .baseUrl("http://localhost:8080")
    .defaultCookie("cookieKey", "cookieValue")
    .defaultHeader(HttpHeaders.CONTENT_TYPE, MediaType.APPLICATION_JSON_VALUE) 
    .defaultUriVariables(Collections.singletonMap("url", "http://localhost:8080"))
  .build();Code language: JavaScript (javascript)

Tạo một thể hiện của WebClient với Timeout

Thông thường, thời gian chờ HTTP mặc định là 30 giây quá chậm so với nhu cầu sử dụng của chúng ta, vì vậy hãy cùng tìm hiểu cách cấu hình lại chúng cho đối tượng WebClient. Chúng ta sẽ sử dụng class TcpClient như sau:

TcpClient tcpClient = TcpClient
  .create()
  .option(ChannelOption.CONNECT_TIMEOUT_MILLIS, 5000)
  .doOnConnected(connection -> {
      connection.addHandlerLast(new ReadTimeoutHandler(5000, TimeUnit.MILLISECONDS));
      connection.addHandlerLast(new WriteTimeoutHandler(5000, TimeUnit.MILLISECONDS));
  });
 
WebClient client = WebClient.builder()
  .clientConnector(new ReactorClientHttpConnector(HttpClient.from(tcpClient)))
  .build();Code language: JavaScript (javascript)

Ở trên chúng ta có thể cài đặt lại thời gian chờ thông qua giá trị Channel.Option.CONNECT_TIMEOUT_MILLIS. Và chúng ta cũng có thể đọc và ghi lại giá trị Timeout bằng cách sử dụng ReadTimeoutHandlerWriteTimeoutHandler.

Chuẩn bị một request

  • Đầu tiên, chúng ta sẽ cần chỉ định ra một phương thức HTTP của một request bằng cách gọi phương thức HttpMethod:
WebClient.UriSpec<WebClient.RequestBodySpec> request1 = client3.method(HttpMethod.POST);
WebClient.UriSpec<WebClient.RequestBodySpec> request2 = client3.post();Code language: HTML, XML (xml)
  • Tiếp theo chúng ta sẽ cung cấp đường dẫn URL
	WebClient.RequestBodySpec uri1 = client3
  .method(HttpMethod.POST)
  .uri("/resource");
 
WebClient.RequestBodySpec uri2 = client3
  .post()
  .uri(URI.create("/resource"));Code language: JavaScript (javascript)
  • Sau đó chúng ta sẽ cài đặt phần response body, content type, header, …
WebClient.RequestHeadersSpec requestSpec1 = WebClient
  .create()
  .method(HttpMethod.POST)
  .uri("/resource")
  .body(BodyInserters.fromPublisher(Mono.just("data")), String.class);
 
WebClient.RequestHeadersSpec<?> requestSpec2 = WebClient
  .create("http://localhost:8080")
  .post()
  .uri(URI.create("/resource"))
  .body(BodyInserters.fromObject("data"));Code language: JavaScript (javascript)

BodyInserter là một interface được sử dụng để đưa vào phần thân ReactiveHttpOutputMessage với một thông báo đầu ra nhất định.

  • Sau khi cài đặt xong phần body, chúng ta có thể cài đặt phần header, cookies, …
	WebClient.ResponseSpec response1 = uri1
  .body(inserter3)
    .header(HttpHeaders.CONTENT_TYPE, MediaType.APPLICATION_JSON_VALUE)
    .accept(MediaType.APPLICATION_JSON, MediaType.APPLICATION_XML)
    .acceptCharset(Charset.forName("UTF-8"))
    .ifNoneMatch("*")
    .ifModifiedSince(ZonedDateTime.now())
  .retrieve();Code language: JavaScript (javascript)

Nhận về một response

Giai đoạn cuối cùng là gửi yêu cầu và nhận một request. Điều này có thể được thực hiện bằng phương thức exchange() hoặc phương thức retrieve().

String response2 = request1.exchange()
  .block()
  .bodyToMono(String.class)
  .block();
String response3 = request2
  .retrieve()
  .bodyToMono(String.class)
  .block();Code language: JavaScript (javascript)

Kết luận

Vậy là mình đã giới thiệu xong về khái niệm WebClient trong Spring Boot hi vọng bài viết này sẽ có ich với mọi người ^^.

Leave a Reply

Your email address will not be published. Required fields are marked *