Using CompletableFuture.supplyAsync for Asynchronous REST API Calls in Spring Boot
Using CompletableFuture.supplyAsync
for Asynchronous REST API Calls in Spring Boot
In modern web applications, performance and responsiveness are crucial. One way to enhance these aspects is by using asynchronous processing. In a Spring Boot application, you can leverage CompletableFuture
to perform non-blocking operations. This article will demonstrate how to use CompletableFuture.supplyAsync
for making asynchronous REST API calls.
1. Introduction to CompletableFuture
CompletableFuture
is a part of the java.util.concurrent
package and is designed for asynchronous programming in Java. It represents a future result of an asynchronous computation and allows you to write non-blocking code more easily. The supplyAsync
method is a key feature that enables you to execute a task asynchronously.
2. Setting Up Your Spring Boot Project
First, ensure you have a Spring Boot project. You can create one using Spring Initializr or your preferred IDE. Include the necessary dependencies, such as spring-boot-starter-web
for building RESTful APIs.
Here's an example pom.xml
setup if you're using Maven:
xml<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter</artifactId>
</dependency>
</dependencies>
3. Making Asynchronous API Calls
Let's create a simple example where we make asynchronous REST API calls using CompletableFuture.supplyAsync
.
- Define a REST Controller
Create a REST controller that will handle incoming requests and use CompletableFuture
to call another REST service asynchronously.
javaimport org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import java.util.concurrent.CompletableFuture;
import java.util.concurrent.CompletionStage;
@RestController
@RequestMapping("/api")
public class MyController {
@Autowired
private ApiService apiService;
@GetMapping("/async-call")
public CompletableFuture<String> asyncCall() {
return CompletableFuture.supplyAsync(() -> apiService.callExternalApi());
}
}
- Create a Service for API Calls
In this service class, we will simulate an external API call. You can use RestTemplate
or WebClient
from Spring for making actual HTTP requests. Here, we'll use RestTemplate
for simplicity.
javaimport org.springframework.stereotype.Service;
import org.springframework.web.client.RestTemplate;
@Service
public class ApiService {
private final RestTemplate restTemplate = new RestTemplate();
public String callExternalApi() {
// Simulate a REST API call
String url = "https://jsonplaceholder.typicode.com/posts/1";
return restTemplate.getForObject(url, String.class);
}
}
- Configure
RestTemplate
Bean (Optional)
You can also define a RestTemplate
bean in your configuration class for better testability and configuration.
javaimport org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.client.RestTemplate;
@Configuration
public class AppConfig {
@Bean
public RestTemplate restTemplate() {
return new RestTemplate();
}
}
4. Testing the Application
Run your Spring Boot application and navigate to http://localhost:8080/api/async-call
in your browser or API client. You should see the JSON response from the external API.
5. Explanation
CompletableFuture.supplyAsync
: This method runs the providedSupplier
function asynchronously. It returns aCompletableFuture
that will complete with the result of the function once it is done.callExternalApi
: This method simulates making an external API call. In a real-world scenario, you might handle more complex logic, error handling, and timeouts.
6. Conclusion
Using CompletableFuture.supplyAsync
allows you to perform REST API calls asynchronously in a Spring Boot application. This approach improves the responsiveness of your application by not blocking the main thread while waiting for external API responses.
Feel free to expand on this example by integrating more complex logic, error handling, and configuring RestTemplate
or WebClient
to suit your needs.
Comments
Post a Comment