Open In App

Spring - Event Handling

Last Updated : 28 Aug, 2024
Comments
Improve
Suggest changes
Like Article
Like
Report

Event handling in Spring is a powerful mechanism that allows different components of a Spring application to communicate with each other in a loosely coupled manner. This is achieved through the Observer Pattern, where a publisher sends events and multiple listeners react to them.

Event Handling in Spring Boot

Spring Event Handling enables various components of an application to communicate loosely. It utilizes the Observer Design Pattern, involving three main components:

1. Event: The Custom Event Class

The event in Spring represents something significant that has happened in the application. It could range from a user logging in to a file being uploaded. In Spring, custom events are typically subclasses of ApplicationEvent.

Key Points:

  • The event class can hold information related to the event, accessible by listeners.
  • It extends the ApplicationEvent class.
Java
package com.gfg.springeventhandling.event;

import org.springframework.context.ApplicationEvent;

public class CustomSpringEvent extends ApplicationEvent {
    private final String message;

    public CustomSpringEvent(Object source, String message) {
        super(source);
        this.message = message;
    }

    public String getMessage() {
        return message;
    }
}
  • CustomSpringEvent extends ApplicationEvent.
  • It contains a message field to hold event-related information.
  • The constructor accepts the event source and the message.
  • The getMessage() method allows listeners to retrieve the event message.

2. Publisher: Publishing the Event

The publisher generates and broadcasts events to the Spring context. This is usually done using the ApplicationEventPublisher interface, which provides the publishEvent() method.

Key Points:

  • The publisher triggers the event and sends it to all interested listeners.
  • It uses ApplicationEventPublisher to publish events.
Java
package com.gfg.springeventhandling.event;

import org.springframework.context.ApplicationEventPublisher;
import org.springframework.stereotype.Component;

@Component
public class CustomSpringEventPublisher {

    private final ApplicationEventPublisher applicationEventPublisher;

    public CustomSpringEventPublisher(ApplicationEventPublisher applicationEventPublisher) {
        this.applicationEventPublisher = applicationEventPublisher;
    }

    public void publishEvent(final String message) {
        System.out.println("Publishing custom event.");
        CustomSpringEvent customSpringEvent = new CustomSpringEvent(this, message);
        applicationEventPublisher.publishEvent(customSpringEvent);
    }
}
  • CustomSpringEventPublisher is a Spring component that acts as the event publisher.
  • It injects ApplicationEventPublisher through the constructor.
  • The publishEvent() method creates and publishes CustomSpringEvent.

3. Listener: Reacting to the Event

Listeners react to specific events. In Spring, listeners are typically annotated with @EventListener, which registers the method as an event handler for a specific event type.

Key Points:

  • The listener component listens for specific events and executes logic when the event is received.
  • It uses the @EventListener annotation to register the method as the event handler.
Java
package com.gfg.springeventhandling.event;

import org.springframework.context.event.EventListener;
import org.springframework.stereotype.Component;

@Component
public class CustomSpringEventListener {

    @EventListener
    public void handleCustomSpringEvent(CustomSpringEvent event) {
        System.out.println("Received spring custom event - " + event.getMessage());
    }
}
  • CustomSpringEventListener is a Spring component that listens for CustomSpringEvent.
  • The handleCustomSpringEvent() method, annotated with @EventListener, prints the event message to the console.

Implementation of Event Handling in a Spring Boot Application

Step 1: Create a new Spring Boot Project

Create a new Spring Boot project using IntelliJ IDEA. Choose the following options:

Project Metadata

Step 2: Add Dependencies

Add the following dependencies into the Spring Boot project.

Add Dependencies

Project Structure

After project creation done, the folder structure will look like the below image.

Project Folder Structure

Step 3: Configure Application Properties

Update the application.properties file.

spring.application.name=spring-event-handling

# application.properties
spring.main.banner-mode=console

Step 4: Create the CustomSpringEvent Class

Define the event class.

event/CustomSpringEvent.java:

Java
package com.gfg.springeventhandling.event;

import org.springframework.context.ApplicationEvent;

public class CustomSpringEvent extends ApplicationEvent {
    private final String message;

    public CustomSpringEvent(Object source, String message) {
        super(source);
        this.message = message;
    }

    public String getMessage() {
        return message;
    }
}

Step 5: Create the CustomSpringEventListener Class

Create the listener that listens for the custom event and react to it.

event/CustomSpringEventListener.java:

Java
package com.gfg.springeventhandling.event;

import org.springframework.context.event.EventListener;
import org.springframework.stereotype.Component;

@Component
public class CustomSpringEventListener {

    @EventListener
    public void handleCustomSpringEvent(CustomSpringEvent event) {
        System.out.println("Received spring custom event - " + event.getMessage());
    }
}

Step 6: Create the CustomSpringEventPublisher Class

The publisher will use the ApplicationEventPublisher to publish the event.

event/CustomSpringEventPublisher.java:

Java
package com.gfg.springeventhandling.event;

import org.springframework.context.ApplicationEventPublisher;
import org.springframework.stereotype.Component;

@Component
public class CustomSpringEventPublisher {

    private final ApplicationEventPublisher applicationEventPublisher;

    public CustomSpringEventPublisher(ApplicationEventPublisher applicationEventPublisher) {
        this.applicationEventPublisher = applicationEventPublisher;
    }

    public void publishEvent(final String message) {
        System.out.println("Publishing custom event.");
        CustomSpringEvent customSpringEvent = new CustomSpringEvent(this, message);
        applicationEventPublisher.publishEvent(customSpringEvent);
    }
}

Step 7: Create the AppRunner Class

Trigger the event from the command-line runner.

runner/AppRunner.java:

Java
package com.gfg.springeventhandling.runner;

import com.gfg.springeventhandling.event.CustomSpringEventPublisher;
import org.springframework.boot.CommandLineRunner;
import org.springframework.stereotype.Component;

@Component
public class AppRunner implements CommandLineRunner {

    private final CustomSpringEventPublisher publisher;

    public AppRunner(CustomSpringEventPublisher publisher) {
        this.publisher = publisher;
    }

    @Override
    public void run(String... args) throws Exception {
        publisher.publishEvent("Hello, Spring Event!");
    }
}

Step 8: Main Class

No changes are required in the main class.

Java
package com.gfg.springeventhandling;

import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;

@SpringBootApplication
public class SpringEventHandlingApplication {

    public static void main(String[] args) {
        SpringApplication.run(SpringEventHandlingApplication.class, args);
    }
}

pom.xml file:

XML
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>
    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>3.3.2</version>
        <relativePath/> <!-- lookup parent from repository -->
    </parent>
    <groupId>com.gfg</groupId>
    <artifactId>spring-event-handling</artifactId>
    <version>0.0.1-SNAPSHOT</version>
    <name>spring-event-handling</name>
    <description>spring-event-handling</description>
    <url/>
    <licenses>
        <license/>
    </licenses>
    <developers>
        <developer/>
    </developers>
    <scm>
        <connection/>
        <developerConnection/>
        <tag/>
        <url/>
    </scm>
    <properties>
        <java.version>17</java.version>
    </properties>
    <dependencies>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-devtools</artifactId>
            <scope>runtime</scope>
            <optional>true</optional>
        </dependency>
        <dependency>
            <groupId>org.projectlombok</groupId>
            <artifactId>lombok</artifactId>
            <optional>true</optional>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-test</artifactId>
            <scope>test</scope>
        </dependency>
    </dependencies>

    <build>
        <plugins>
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
                <configuration>
                    <excludes>
                        <exclude>
                            <groupId>org.projectlombok</groupId>
                            <artifactId>lombok</artifactId>
                        </exclude>
                    </excludes>
                </configuration>
            </plugin>
        </plugins>
    </build>

</project>

Step 9: Run the Application

Start the application and it will run on port 8080.

Application Starts

This example project provides clear and practical demonstration of the Spring Event Handling of the Spring Boot application.

How These Components Work Together

  • Event Creation: The event class, CustomSpringEvent, can be defined to represent the event in the application.
  • Event Publishing: The publisher component, CustomSpringEventPublisher, is responsible for creating and publishing this event to the Spring context. The event is typically published in response to some application logic.
  • Event Listening: The listener component, CustomSpringEventListener, is registered to listen for the specific event type, CustomSpringEvent. When the event is published, the listener's method is triggered, allowing the application to respond to the event.

Advantages of Using Event Handling in Spring

  • Loose Coupling: Publishers and listeners do not need to know about each other. They can communicate through events, making the system more modular and easier to maintain.
  • Scalability: New listeners can be easily added without modifying the existing publishing logic.
  • Flexibility: Different listeners can handle the same event in different ways, allowing for a variety of reactions to a single event.

Conclusion

Spring's event handling mechanism provides a flexible way to manage communication between different components of an application. By using custom events, publishers, and listeners, you can create a robust and loosely-coupled architecture. This approach enhances the maintainability and scalability of your Spring Boot applications.


Next Article
Article Tags :

Similar Reads