Post

java.net.http.HttpClient

java.net.http.HttpClient

๐Ÿ”” HttpClient ๊ฐœ์š”
๐Ÿ”” HttpClient ๊ฐœ์„  ๊ณผ์ •
๐Ÿ”” ๋‹ค๋ฅธ ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ ๋น„๊ต

What? Why?

์ž๋ฐ”์—์„œ HTTP ์š”์ฒญ์„ ์ƒ์„ฑํ•˜๊ณ , ์„œ๋ฒ„์™€ ํ†ต์‹ ํ•˜๋ฉฐ, ์‘๋‹ต์„ ์ฒ˜๋ฆฌํ•˜๊ธฐ ์œ„ํ•œ API
Java 11์—์„œ ํ‘œ์ค€ ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ๋กœ ๋„์ž…๋˜์—ˆ์œผ๋ฉฐ, ์ด์ „์˜ HttpURLConnection๋ณด๋‹ค ์‚ฌ์šฉํ•˜๊ธฐ ์‰ฝ๊ณ  ๊ธฐ๋Šฅ์ด ํ’๋ถ€ํ•˜๋‹ค.

  • ๋นŒ๋” ํŒจํ„ด ๋„์ž…: HttpRequest.newBuilder()
  • ์—ญํ•  ๋ถ„๋ฆฌ: HttpClient, HttpRequest, HttpResponse
  • ๋น„๋™๊ธฐ ์ฒ˜๋ฆฌ ์ง€์›: HttpClient.sendAsync()

์ฃผ์š” ํด๋ž˜์Šค

  • HttpClient: HTTP ์š”์ฒญ์„ ๋ณด๋‚ด๊ธฐ ์œ„ํ•œ ํด๋ผ์ด์–ธํŠธ ๊ฐ์ฒด๋ฅผ ์ƒ์„ฑ
  • HttpRequest: HTTP ์š”์ฒญ์˜ ์„ธ๋ถ€ ์‚ฌํ•ญ(URI, ๋ฉ”์„œ๋“œ, ํ—ค๋” ๋“ฑ)
  • HttpResponse: ์„œ๋ฒ„๋กœ๋ถ€ํ„ฐ ๋ฐ›์€ HTTP ์‘๋‹ต

์ฃผ์š” ๋ฉ”์„œ๋“œ

  • HttpClient.newHttpClient()

    ๊ธฐ๋ณธ ์„ค์ •์„ ์‚ฌ์šฉํ•œ HttpClient ์ธ์Šคํ„ด์Šค๋ฅผ ์ƒ์„ฑ
    - ์š”์ฒญ(GET), ํ”„๋กœํ† ์ฝœ(HTTP/2), ๋ฆฌ๋‹ค์ด๋ ‰ํŠธ(NEVER), SSL(Default)

    1
    
    HttpClient client = HttpClient.newHttpClient();
    
  • HttpRequest.newBuilder()

    ์ƒˆ๋กœ์šด HttpRequest ๋นŒ๋”๋ฅผ ์ƒ์„ฑ

    1
    2
    3
    4
    5
    6
    
    HttpRequest request = HttpRequest.newBuilder()
          .uri(URI.create("https://foo.com/"))
          .timeout(Duration.ofMinutes(2))
          .header("Content-Type", "application/json")
          .POST(BodyPublishers.ofFile(Paths.get("file.json")))
          .build();
    
  • client.send(request, HttpResponse.BodyHandlers.ofString())

    ๋™๊ธฐ์ ์œผ๋กœ HTTP ์š”์ฒญ์„ ๋ณด๋‚ด๊ณ , ์‘๋‹ต์„ ๋ฌธ์ž์—ด๋กœ ๋ฐ›์Œ

    1
    2
    3
    
    HttpResponse<String> response = client.send(request, HttpResponse.BodyHandlers.ofString());
    System.out.println(response.statusCode());
    System.out.println(response.body());  
    
  • client.sendAsync(request, HttpResponse.BodyHandlers.ofString())

    ๋น„๋™๊ธฐ์ ์œผ๋กœ HTTP ์š”์ฒญ์„ ๋ณด๋‚ด๊ณ , ์‘๋‹ต์„ CompletableFuture๋กœ ๋ฐ›์Œ

    1
    2
    3
    
    client.sendAsync(request, BodyHandlers.ofString())
          .thenApply(HttpResponse::body)
          .thenAccept(System.out::println);
    

๊ธฐ๋Šฅ ์—…๋ฐ์ดํŠธ ์š”์•ฝ

  • java 11: HttpClient ๋„์ž…
  • java 14: TLS 1.3 ์ง€์›
  • java 15: OAuth2 ๋“ฑ ๋‹ค์–‘ํ•œ ์ธ์ฆ ๋ฐฉ์‹์„ ์ง€์›ํ•˜๋Š” ๊ธฐ๋Šฅ์ด ์ถ”๊ฐ€
  • java 17: ์ปค๋„ฅ์…˜ ํ’€ ๊ด€๋ฆฌ ๊ธฐ๋Šฅ์ด ํ–ฅ์ƒ
  • java 18~21: HTTP/3์˜ ์ •์‹ ์ง€์›์ด ์ถ”๊ฐ€, ๋ณด์•ˆ ๊ฐ•ํ™”

๋‹ค๋ฅธ HTTP ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ

RestTemplate

  • ๋™๊ธฐ ๋ฐฉ์‹
  • ๊ฐ„๋‹จํ•œ ์‚ฌ์šฉ๋ฒ•: ๊ฐ„๋‹จํ•œ REST ํ˜ธ์ถœ์— ์ ํ•ฉ
  • ์ œํ•œ ์‚ฌํ•ญ: ๋น„๋™๊ธฐ๋‚˜ ๋ฐ˜์‘ํ˜• ํ”„๋กœ๊ทธ๋ž˜๋ฐ์„ ์ง€์›ํ•˜์ง€ ์•Š์œผ๋ฉฐ, ๊ธฐ๋Šฅ์ด ์ œํ•œ์ 
1
2
3
4
5
6
7
8
9
import org.springframework.web.client.RestTemplate;

public class RestTemplateExample {
    public static void main(String[] args) {
        RestTemplate restTemplate = new RestTemplate();
        String response = restTemplate.getForObject("https://api.example.com/data", String.class);
        System.out.println(response);
    }
}

WebClient

  • ๋น„๋™๊ธฐ ๋ฐ ๋ฐ˜์‘ํ˜• ์ง€์›: ๋น„๋™๊ธฐ ํ˜ธ์ถœ๊ณผ ๋ฆฌ์•กํ‹ฐ๋ธŒ ์ŠคํŠธ๋ฆผ์„ ์ง€์›
  • ์œ ์—ฐ์„ฑ: ๋‹ค์–‘ํ•œ HTTP ์š”์ฒญ๊ณผ ์‘๋‹ต ์ฒ˜๋ฆฌ๋ฅผ ์œ ์—ฐํ•˜๊ฒŒ ์ง€์›
  • ๋ชจ๋˜ํ•œ ์‚ฌ์šฉ๋ฒ•: ํ˜„๋Œ€์ ์ธ ์›น ์• ํ”Œ๋ฆฌ์ผ€์ด์…˜์— ์ ํ•ฉ
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
import org.springframework.web.reactive.function.client.WebClient;
import reactor.core.publisher.Mono;

public class WebClientExample {
    public static void main(String[] args) {
        WebClient client = WebClient.create("https://api.example.com");

        Mono<String> response = client.get()
                .uri("/data")
                .retrieve()
                .bodyToMono(String.class);

        response.subscribe(System.out::println);
    }
}

๋น„๊ต

DifferenceHttpClient

์ถœ์ฒ˜

Oracle
OpenJDK
ChatGPT

This post is licensed under CC BY 4.0 by the author.