Backend Development 10 min read

Introduction to Spring WebFlux and Reactive Programming

This article introduces Spring WebFlux, explains reactive programming concepts, compares it with Spring MVC, and provides practical code examples demonstrating how to build a reactive web application using Spring Boot, Reactor's Mono and Flux, and functional routing.

Java Architect Essentials
Java Architect Essentials
Java Architect Essentials
Introduction to Spring WebFlux and Reactive Programming

Spring WebFlux Overview

spring-webflux is a reactive‑style web development framework introduced in Spring 5.0. It builds on spring-framework and Spring MVC and can run on Netty, Undertow, or any Servlet 3.1+ container.

You may use spring-webmvc and spring-webflux together in the same project, or choose only one of them.

What Is "Reactive"?

Reactive programming means that when an API call is made, the thread is not blocked waiting for the response; instead, the system is notified when data arrives, allowing the CPU to perform other work and improving overall throughput.

Reactive programming provides a standard for asynchronous, non‑blocking stream processing. Java 8 streams are an example of this style, and the standard also defines requirements for the runtime environment (JVM, JavaScript) and network protocols.

Spring WebFlux Reactive API

The framework is built on the open‑source Reactor project, which offers two core types: Mono (for a single value) and Flux (for multiple values).

// Mono generally works with a single object
Mono
person = personDao.getPerson(personId);
// Flux generally works with multiple objects
Flux
people = personDao.listAllPeople();

Although WebFlux is based on Reactor, it can also interoperate with other reactive libraries such as RxJava.

Choosing Spring MVC or Spring WebFlux

If your existing project already uses Spring-webmvc and works well, you may keep it; most third‑party libraries are still blocking.

WebFlux offers many deployment options (Netty, Tomcat, Jetty, Undertow, Servlet 3.1+). You can define controllers with @Controller or use functional routing, and you may choose Reactor, RxJava, or another library for the programming model.

If you prefer Java 8 lambda expressions and a lightweight functional style, WebFlux is a good fit, especially for simple micro‑services.

In a micro‑service architecture, MVC and WebFlux can be mixed; both support @Controller for easier reuse.

Evaluate whether the project uses many blocking APIs (e.g., JDBC). Heavy use of blocking calls makes WebFlux less suitable.

If a MVC project makes many external calls, consider using the reactive WebClient to return reactive results from controller methods.

Learning reactive programming has a steep curve; using WebClient is a practical way to get started.

Spring-webflux can run on traditional Servlet containers as well as on non‑Servlet servers like Netty and Undertow. When you create a Spring Boot WebFlux application, Netty is used by default because it is non‑blocking.

Concurrency Model

Spring MVC is a Servlet‑based, blocking‑IO framework that creates a thread pool (e.g., 10 threads) to handle each request, limiting throughput by the number of threads.

WebFlux, built on NIO servers such as Netty, uses a small number of event‑loop workers to handle many requests concurrently, improving CPU utilization and overall throughput.

WebFlux does not make the code run faster; it simply enables higher concurrent request handling.

WebFlux Code Example

Talk is cheap, show me the code

Adding the WebFlux starter dependency to a Spring Boot project is enough to start:

<dependency>
  <groupId>org.springframework.boot</groupId>
  <artifactId>spring-boot-starter-webflux</artifactId>
</dependency>

Define a simple POJO:

public class Person {
    private Integer id;
    private Integer age;
    private String name;
}

Use functional routing instead of @RequestMapping :

@Configuration
public class PersonRouter {
    @Resource
    private PersonHandler personHandler;

    @Bean
    public RouterFunction
personRoutes() {
        return RouterFunctions.route()
            .GET("/person/{id}", RequestPredicates.accept(MediaType.APPLICATION_JSON), personHandler::getPerson)
            .GET("/person", RequestPredicates.accept(MediaType.APPLICATION_JSON), personHandler::listPeople)
            .POST("/person", personHandler::createPerson)
            .build();
    }
}

Handler implementation (similar to a service layer):

@Component
public class PersonHandler {
    @Resource
    private PersonRepository personDao;

    public Mono
listPeople(ServerRequest request) {
        Flux
people = personDao.listAllPeople();
        return ServerResponse.ok()
            .contentType(MediaType.APPLICATION_JSON)
            .body(people, Person.class);
    }

    public Mono
createPerson(ServerRequest request) {
        Mono
person = request.bodyToMono(Person.class);
        return ServerResponse.ok().build(personDao.savePerson(person));
    }

    public Mono
getPerson(ServerRequest request) {
        int personId = Integer.parseInt(request.pathVariable("id"));
        return personDao.getPerson(personId)
            .flatMap(p -> ServerResponse.ok().contentType(MediaType.APPLICATION_JSON).bodyValue(p))
            .switchIfEmpty(ServerResponse.notFound().build());
    }
}

When the application starts, Spring Boot uses Netty to provide the HTTP service. Accessing http://localhost:8080/person/1 confirms that the WebFlux endpoint works.

javabackend developmentReactive ProgrammingReactorFluxMonoSpring WebFlux
Java Architect Essentials
Written by

Java Architect Essentials

Committed to sharing quality articles and tutorials to help Java programmers progress from junior to mid-level to senior architect. We curate high-quality learning resources, interview questions, videos, and projects from across the internet to help you systematically improve your Java architecture skills. Follow and reply '1024' to get Java programming resources. Learn together, grow together.

0 followers
Reader feedback

How this landed with the community

login Sign in to like

Rate this article

Was this worth your time?

Sign in to rate
Discussion

0 Comments

Thoughtful readers leave field notes, pushback, and hard-won operational detail here.