使用 OkHttp 调用 Spring Boot API

OkHttp 在处理棘手的网络情况时非常聪明。它会悄悄地从常见的连接中断中恢复过来,如果第一次尝试不起作用,甚至会尝试不同的地址。当您处理同时使用 IPv4 和 IPv6 的情况或当您的服务设置在备份数据中心时,这一点变得至关重要。在本文中,您将探索如何在 Spring Boot 应用程序中使用 OkHttp。

OkHttp 作为默认优先考虑效率的 HTTP 客户端脱颖而出:

  • HTTP/2 支持:允许对同一主机的多个请求共享一个套接字,从而提高性能。
  • 连接池:减少请求延迟,在 HTTP/2 不可用的情况下特别有用。
  • 透明 GZIP:通过 GZIP 无缝压缩下载大小,有助于优化数据传输。
  • 响应缓存:绕过网络重复请求,提高效率。
  • 弹性:OkHttp 能够熟练地管理具有挑战性的网络条件,默默地从常见的连接问题中恢复。如果初始连接失败,它会智能地尝试备用地址,这对于 IPv4+IPv6 和冗余数据中心的服务至关重要。
  • 现代 TLS 支持:OkHttp 配备了现代 TLS 功能,包括 TLS 1.3、ALPN 和证书固定。它提供了多功能连接的配置选项。

使用 OkHttp 非常简单。其请求/响应 API 采用流畅的构建器和不变性,从而提高了易用性。无论您喜欢同步阻塞调用还是带回调的异步调用,OkHttp 都能无缝适应这两种风格。

添加OkHttp依赖

<dependency>
      <groupId>com.squareup.okhttp3</groupId>
    <artifactId>okhttp</artifactId>
    <version>4.9.1</version>
</dependency>

首先,创建一个服务类,负责使用 OkHttp 处理 API 调用。例如,创建一个名为 ApiService 的类,并在类中编写以下代码。

import okhttp3.*; 

import java.io.IOException; 

@Service
public class ApiService { 

    private final OkHttpClient client = new OkHttpClient(); 
    
    // Get Request 
    public String makeGetRequest(String apiUrl) throws IOException { 
        Request request = new Request.Builder().url(apiUrl).build(); 

        try (Response response = client.newCall(request).execute()) { 
            if (response.isSuccessful()) { 
                return response.body().string(); 
            } else
                throw new IOException(
"Unexpected response: " + response.code()); 
            } 
        } 
    } 
    
    
// Post Request 
    public String makePostRequest(String apiUrl, String requestBody) throws IOException { 
        RequestBody body = RequestBody.create(requestBody, MediaType.parse(
"application/json")); 
        Request request = new Request.Builder().url(apiUrl).post(body).build(); 

        try (Response response = client.newCall(request).execute()) { 
            if (response.isSuccessful()) { 
                return response.body().string(); 
            } else
                throw new IOException(
"Unexpected response: " + response.code()); 
            } 
        } 
    } 

该文件包括两个服务方法:

  • makeGetRequest(String apiUrl) - makeGetRequest(String) 方法使用 OkHttp 处理 GET 请求 API 调用。
  • makePostRequest(String apiUrl, String requestBody) - 该方法使用 OkHttp 处理 POST 请求 API 调用,并将数据发送到服务器。

创建一个 Spring MVC 控制器,用于暴露触发 API 调用的端点。例如,创建一个名为 ApiController 的类。在本文中,我们使用 https://jsonplaceholder.typicode.com 虚拟 API。


import okhttp3.*; 
  
import java.io.IOException; 
@RestController
@RequestMapping("/api"
public class ApiController { 
  
    @Autowired
    private ApiService apiService; 
  
     
// End-point for GET Request 
    @GetMapping(
"/get-example"
    public String getExample() { 
        String apiUrl =
"https://jsonplaceholder.typicode.com/posts/1"
  
        try
            String apiResponse = apiService.makeGetRequest(apiUrl); 
            return
"GET Response: " + apiResponse; 
        } catch (IOException e) { 
            e.printStackTrace(); 
            return
"While making GET request, getting Error: " + e.getMessage(); 
        } 
    } 
  
     
// End-point for POST Request 
    @PostMapping(
"/post-example"
    public String postExample() { 
        String apiUrl =
"https://jsonplaceholder.typicode.com/posts"
        
         
// This is the request body 
        String requestBody =
"{\'title\': \'foo\',\'body\': \'bar\',\'userId\': 1}"
  
        try
            String apiResponse = apiService.makePostRequest(apiUrl, requestBody); 
            return
"POST Response: " + apiResponse; 
        } catch (IOException e) { 
            e.printStackTrace(); 
            return
"While making POST request, getting Error: " + e.getMessage(); 
        } 
    } 
}

在上述代码中,有两个方法:

  • getExample() - 当 /api/get-example 端点的 GET 请求被触发时,将调用 getExample() 方法。
  • postExample() - 当 /api/post-example 端点发出 POST 请求时,将调用该方法。在该方法中,有一个名为 requestBody 的字符串类型变量,在该变量中定义了与请求一起发送的请求正文。

最后,要测试 API 调用,可以使用浏览器、cURL 或 Postman 等工具向端点发出 GET/POST 和其他请求。你应该能看到 API 响应或错误信息。

让我们测试一下 /api/get-example 端点:
打开 Postman,然后输入 URL(如 http://localhost:8080/api/get-example),并从左侧下拉菜单中选择 GET 请求,最后点击发送按钮,现在就会生成一个响应。

记住,要将示例 URL 替换为要调用的 API 的实际 URL。