Table of contents
1.
Introduction
2.
Key Advantages
3.
How Does It Work?
4.
How to Use FeignClient in Spring Boot Application?
5.
Annotations and Their Roles
5.1.
1. @FeignClient
5.2.
2. @GetMapping, @PostMapping, @PutMapping, @DeleteMapping
5.3.
3. @RequestParam
5.4.
4. @Headers
5.5.
5. @RequestMapping
6.
Complete Example
7.
Example Project
7.1.
Developing Employee-Service Step by Step
7.2.
Developing Address-Service Step by Step
8.
Microservices Communication Using FeignClient
8.1.
Simplifying Feign Client Logging
8.2.
Tips for Effective Logging
9.
Advanced Features and Best Practices
10.
Frequently Asked Questions
10.1.
What is a Feign Client in Spring Boot? 
10.2.
How do you enable logging in Feign? 
10.3.
Can Feign Client handle load balancing? 
11.
Conclusion
Last Updated: Jan 19, 2025
Medium

Feign Client in Spring Boot

Author Pallavi singh
0 upvote
Career growth poll
Do you think IIT Guwahati certified course can help you in your career?

Introduction

Feign Client is a declarative web service client used in Spring Boot applications. It simplifies the process of making HTTP requests to other services by allowing you to define HTTP clients in a more readable way, eliminating the need for complex code. With Feign, you can call RESTful APIs in a clean and concise manner, making it a popular choice for microservices architectures.

Feign Client in Spring Boot

In this article, we will discuss how Feign Client works, how to use it in a Spring Boot application, and guides to implement it.

Key Advantages

  1. Declarative REST Clients: Feign allows you to define REST clients using interfaces. You only need to declare methods and annotate them with REST-specific information like endpoints and HTTP methods.
     
  2. Less Boilerplate Code: It eliminates the need to manually create HTTP connections and handle JSON parsing, making code more readable and maintainable.
     
  3. Seamless Integration with Spring Boot: Feign integrates easily with Spring Boot, leveraging annotations like @FeignClient and supporting configurations like timeouts and retries.
     
  4. Support for Load Balancing: Feign works well with Ribbon or Spring Cloud LoadBalancer to distribute requests across multiple service instances.
     
  5. Improved Testability: Using Feign simplifies testing by providing a clean abstraction over HTTP communication.

How Does It Work?

Feign is a declarative web service client. Developers define an interface, annotate it with Feign annotations, and the library automatically generates the implementation at runtime. Feign uses the HTTP client underneath to execute requests and process responses. Here is a simple workflow:

  1. Define a Service Interface: Use the @FeignClient annotation to declare an interface for REST communication.
     
  2. Annotate Methods: Define methods for each API endpoint using annotations like @GetMapping or @PostMapping.
     
  3. Inject the Feign Client: Autowire or inject the Feign client into your application to call the defined methods.

How to Use FeignClient in Spring Boot Application?

Add the necessary dependencies to your pom.xml file:

<dependency>
    <groupId>org.springframework.cloud</groupId>
    <artifactId>spring-cloud-starter-openfeign</artifactId>
</dependency>


Enable Feign Clients in your Spring Boot application by adding the @EnableFeignClients annotation to the main application class:

@SpringBootApplication
@EnableFeignClients
public class FeignExampleApplication {
    public static void main(String[] args) {
        SpringApplication.run(FeignExampleApplication.class, args);
    }
}


Define the Feign Client interface:

@FeignClient(name = "user-service", url = "http://localhost:8081")
public interface UserServiceClient {

    @GetMapping("/users/{id}")
    User getUserById(@PathVariable("id") Long id);
}


Inject the Feign Client where needed:

@Service
public class UserService {

   private final UserServiceClient userServiceClient;

    public UserService(UserServiceClient userServiceClient) {
        this.userServiceClient = userServiceClient;
    }

    public User fetchUser(Long id) {
        return userServiceClient.getUserById(id);
    }
}

Annotations and Their Roles

Feign Client relies heavily on annotations to define how HTTP requests should be made. These annotations make it easy to configure & use Feign in your Spring Boot application. Let’s take a look at the most important annotations & their roles:

1. @FeignClient

This is the core annotation used to declare a Feign Client. It tells Spring Boot that this interface is a Feign Client & specifies the name of the service it will communicate with. Let’s see how it works:

@FeignClient(name = "user-service", url = "http://localhost:8080")
public interface UserServiceClient {
    @GetMapping("/users/{id}")
    User getUserById(@PathVariable("id") Long id);
}

 

  • `name`: Specifies the name of the service. This is useful when working with service discovery tools like Eureka.
     
  • `url`: Defines the base URL of the service if service discovery is not used.
     
  • The interface methods (like `getUserById`) define the HTTP endpoints to call.

2. @GetMapping, @PostMapping, @PutMapping, @DeleteMapping

These annotations define the type of HTTP request (GET, POST, PUT, DELETE) & the endpoint to call. They work the same way as in Spring MVC. For example:

@PostMapping("/users")


User createUser(@RequestBody User user);

  • `@RequestBody`: Used to send data in the request body (e.g., for POST or PUT requests).
     
  • `@PathVariable`: Used to pass variables in the URL (e.g., `/users/{id}`).

3. @RequestParam

This annotation is used to pass query parameters in the URL. For example:

@GetMapping("/users")
List<User> getUsersByRole(@RequestParam("role") String role);


The above method will call the endpoint `/users?role=ADMIN` if `role` is passed as `"ADMIN"`.

4. @Headers

This annotation allows you to add custom headers to your HTTP requests. For example:

@Headers("Content-Type: application/json")
@PostMapping("/users")
User createUser(@RequestBody User user);


This ensures that the `Content-Type` header is set to `application/json` for the request.

5. @RequestMapping

This annotation can be used at the class level to define a base path for all methods in the Feign Client interface. For example:

@FeignClient(name = "user-service", url = "http://localhost:8080")
@RequestMapping("/api/v1")
public interface UserServiceClient {
    @GetMapping("/users/{id}")
    User getUserById(@PathVariable("id") Long id);
}


All requests will now start with `/api/v1`.

Complete Example

Let’s take a look at the complete example of a Feign Client interface:

@FeignClient(name = "user-service", url = "http://localhost:8080")
@RequestMapping("/api/v1")
public interface UserServiceClient {

    @GetMapping("/users/{id}")
    User getUserById(@PathVariable("id") Long id);

    @PostMapping("/users")
    User createUser(@RequestBody User user);

    @GetMapping("/users")
    List<User> getUsersByRole(@RequestParam("role") String role);

    @Headers("Content-Type: application/json")
    @PutMapping("/users/{id}")
    User updateUser(@PathVariable("id") Long id, @RequestBody User user);

    @DeleteMapping("/users/{id}")
    void deleteUser(@PathVariable("id") Long id);
}


This interface defines methods to perform CRUD operations on a `User` resource.

In this Code

1. `@FeignClient`: Declares this interface as a Feign Client & specifies the service URL.
 

2. `@RequestMapping`: Sets a base path for all endpoints.
 

3. HTTP Methods: Each method is annotated with the appropriate HTTP method (`@GetMapping`, `@PostMapping`, etc.).
 

4. Parameters: Annotations like `@PathVariable` & `@RequestParam` are used to pass data in the URL.
 

5. Headers: Custom headers can be added using `@Headers`.

Example Project

Developing Employee-Service Step by Step

  1. Set up a Spring Boot project: Add dependencies for Spring Web and Spring Boot DevTools.
     
  2. Create the Employee Entity:
@Entity
public class Employee {
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;
    private String name;
    private String department;
    // Getters and setters
}


Build the Controller:

@RestController
@RequestMapping("/employees")
public class EmployeeController {
    @GetMapping("/{id}")
    public Employee getEmployee(@PathVariable Long id) {
        return new Employee(id, "John Doe", "Engineering");
    }
}

Developing Address-Service Step by Step

  1. Set up a Spring Boot project: Add similar dependencies as in the Employee-Service.
     
  2. Create the Address Entity:
@Entity
public class Address {
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;
    private String city;
    private String country;


    // Getters and setters
}


Build the Controller:

@RestController
@RequestMapping("/addresses")
public class AddressController {
    @GetMapping("/{id}")
    public Address getAddress(@PathVariable Long id) {
        return new Address(id, "New York", "USA");
    }
}

Microservices Communication Using FeignClient

To connect Employee-Service and Address-Service:

Create Feign Client in Employee-Service:

@FeignClient(name = "address-service", url = "http://localhost:8082")
public interface AddressServiceClient {
    @GetMapping("/addresses/{id}")
    Address getAddressById(@PathVariable("id") Long id);
}


Modify Employee Service to include Address:

@Service
public class EmployeeService {

    private final AddressServiceClient addressServiceClient;

    public EmployeeService(AddressServiceClient addressServiceClient) {
        this.addressServiceClient = addressServiceClient;
    }

    public EmployeeDetails getEmployeeWithAddress(Long id) {
        Employee employee = getEmployee(id);
        Address address = addressServiceClient.getAddressById(employee.getId());
        return new EmployeeDetails(employee, address);
    }
}

Simplifying Feign Client Logging

Feign provides a logging feature that helps in debugging HTTP requests and responses:

Enable Logging: Add the following property to application.properties:

logging.level.feign.client=DEBUG


Custom Logger Configuration:

@Configuration
public class FeignConfig {
    @Bean
    Logger.Level feignLoggerLevel() {
        return Logger.Level.FULL;
    }
}

Tips for Effective Logging

  • Use Appropriate Log Levels: Set log levels to INFO for production and DEBUG for debugging.
     
  • Filter Sensitive Data: Avoid logging sensitive information like passwords or tokens.
     
  • Monitor Performance: Keep an eye on the overhead caused by excessive logging.
     
  • Log Request and Response Details: Include headers, body, and status codes for better debugging.

Advanced Features and Best Practices


1. Error Handling  

Feign allows you to implement custom error handling using an error decoder. This helps you handle different HTTP status codes & exceptions gracefully, ensuring your application can recover from errors.


2. Retry Mechanism  

Feign supports a retry mechanism for failed requests. You can configure the number of retries & the delay between retries to improve the reliability of your service calls.


3. Logging  

Feign provides built-in logging to help you debug requests & responses. You can set the logging level to `BASIC`, `HEADERS`, or `FULL` depending on how much detail you need.


4. Interceptors  

Request interceptors allow you to modify outgoing requests before they are sent. This is useful for adding headers, logging, or performing other pre-processing tasks.


5. Load Balancing  

When used with service discovery tools like Eureka, Feign can automatically load balance requests across multiple instances of a service, improving performance & reliability.


6. Timeouts  

Configure timeouts for Feign clients to prevent long waits for unresponsive services. This ensures your application remains responsive even if a downstream service is slow.


7. Compression  

Enable request & response compression to reduce the size of data transferred over the network, improving performance for large payloads.


Best Practices: Always use meaningful names for Feign clients, keep your interfaces clean, & avoid hardcoding URLs. Use configuration files to manage service URLs & other settings.

Frequently Asked Questions

What is a Feign Client in Spring Boot? 

Feign Client is a declarative REST client that simplifies HTTP communication between microservices by eliminating boilerplate code.

How do you enable logging in Feign? 

Logging can be enabled by setting the log level in application.properties and configuring a logger bean.

Can Feign Client handle load balancing? 

Yes, it integrates with tools like Ribbon or Spring Cloud LoadBalancer for distributed requests.

Conclusion

In this article, we discussed the Feign Client in Spring Boot, its advantages, and how to implement it step by step. By using Feign, you can simplify microservices, improve code maintainability, and enhance productivity. With proper logging and configuration, it can help in debugging and monitoring microservices.

Live masterclass