Spring WebFlux-Filter

Spring WebFlux Filter

1. Überblick

Die Verwendung von Filtern ist in Webanwendungen weit verbreitet, da sie uns die Möglichkeit bieten, eine Anforderung oder Antwort zu ändern, ohne unsere Endpunkte zu ändern.

In diesem kurzen Tutorial werden mögliche Möglichkeiten zur Implementierung mit dem WebFlux Framework beschrieben.

Da wir nicht auf Details zum WebFlux-Framework selbst eingehen, sollten Siethis article für weitere Details überprüfen.

2. Maven-Abhängigkeit

Zunächst deklarieren wir die WebFlux Maven-Abhängigkeit:


    org.springframework.boot
    spring-boot-starter-webflux

3. Endpunkte

Wir müssen zuerst einige Endpunkte erstellen. Eine für jede Methode: annotationsbasiert und funktionsbasiert.

Beginnen wir mit dem annotationsbasierten Controller:

@GetMapping(path = "/users/{name}")
public Mono getName(@PathVariable String name) {
    return Mono.just(name);
}

Für den funktionalen Endpunkt müssen wir zuerst einen Handler erstellen:

@Component
public class PlayerHandler {
    public Mono getName(ServerRequest request) {
        Mono name = Mono.just(request.pathVariable("name"));
        return ok().body(name, String.class);
    }
}

Und auch ein Router-Konfigurations-Mapping:

@Bean
public RouterFunction route(PlayerHandler playerHandler) {
    return RouterFunctions
      .route(GET("/players/{name}"), playerHandler::getName)
      .filter(new ExampleHandlerFilterFunction());
}

4. Arten von WebFlux-Filtern

Das WebFlux-Framework bietet zwei Arten von Filtern:WebFilters undHandlerFilterFunctions.

Der Hauptunterschied zwischen ihnen besteht darin, dassWebFilter implementations work for all endpoints und HandlerFilterFunction implementations will only work for Router-based ones.

4.1. WebFilter

Wir implementieren einWebFilter, um der Antwort einen neuen Header hinzuzufügen. Folglich sollten alle Antworten das folgende Verhalten aufweisen:

@Component
public class ExampleWebFilter implements WebFilter {

    @Override
    public Mono filter(ServerWebExchange serverWebExchange,
      WebFilterChain webFilterChain) {

        serverWebExchange.getResponse()
          .getHeaders().add("web-filter", "web-filter-test");
        return webFilterChain.filter(serverWebExchange);
    }
}

4.2. HandlerFilterFunction

In diesem Fall implementieren wir eine Logik, die den HTTP-Status aufFORBIDDEN setzt, wenn der Parameter "name" gleich "test" ist.

public class ExampleHandlerFilterFunction
  implements HandlerFilterFunction {

    @Override
    public Mono filter(ServerRequest serverRequest,
      HandlerFunction handlerFunction) {
        if (serverRequest.pathVariable("name").equalsIgnoreCase("test")) {
            return ServerResponse.status(FORBIDDEN).build();
        }
        return handlerFunction.handle(serverRequest);
    }
}

5. Testen

In WebFlux Framework gibt es eine einfache Möglichkeit, unsere Filter zu testen:WebTestClient. Damit können wir HTTP-Aufrufe an unsere Endpunkte testen.

Hier sind Beispiele für den auf Anmerkungen basierenden Endpunkt:

@Test
public void whenUserNameIsexample_thenWebFilterIsApplied() {
    EntityExchangeResult result = webTestClient.get()
      .uri("/users/example")
      .exchange()
      .expectStatus().isOk()
      .expectBody(String.class)
      .returnResult();

    assertEquals(result.getResponseBody(), "example");
    assertEquals(
      result.getResponseHeaders().getFirst("web-filter"),
      "web-filter-test");
}

@Test
public void whenUserNameIsTest_thenHandlerFilterFunctionIsNotApplied() {
    webTestClient.get().uri("/users/test")
      .exchange()
      .expectStatus().isOk();
}

Und für den funktionalen Endpunkt:

@Test
public void whenPlayerNameIsexample_thenWebFilterIsApplied() {
    EntityExchangeResult result = webTestClient.get()
      .uri("/players/example")
      .exchange()
      .expectStatus().isOk()
      .expectBody(String.class)
      .returnResult();

    assertEquals(result.getResponseBody(), "example");
    assertEquals(
      result.getResponseHeaders().getFirst("web-filter"),
      "web-filter-test");
}

@Test
public void whenPlayerNameIsTest_thenHandlerFilterFunctionIsApplied() {
    webTestClient.get().uri("/players/test")
      .exchange()
      .expectStatus().isForbidden();
}

6. Fazit

Wir haben in diesem Lernprogramm beide Arten von WebFlux-Filtern behandelt und uns einige Codebeispiele angesehen.

Weitere Informationen zum WebFlux Framework finden Sie unterdocumentation.

Wie immer finden Sie den vollständigen Quellcode für die Beispiele inover on GitHub.