diff --git a/spring-graphql-docs/src/docs/asciidoc/index.adoc b/spring-graphql-docs/src/docs/asciidoc/index.adoc index 2d282d7d..5d564f1d 100644 --- a/spring-graphql-docs/src/docs/asciidoc/index.adoc +++ b/spring-graphql-docs/src/docs/asciidoc/index.adoc @@ -155,30 +155,40 @@ public class GraphQlRSocketController { [[server-interception]] === Interception -Transport handlers for <> and <> delegate to a -`WebGraphQlInterceptor` chain with an `ExecutionGraphQlService` at the end which calls -the GraphQL Java engine. Use this to access HTTP request details and customize the -`ExecutionInput` for GraphQL Java. +Server transports allow intercepting requests before and after the GraphQL Java engine is +called to process a request. -For example, to extract HTTP request values and pass them to data fetchers: + +[[server-interception-web]] +==== `WebGraphQlInterceptor` + +<> and <> transports invoke a chain of +0 or more `WebGraphQlInterceptor`, followed by an `ExecutionGraphQlService` that calls +the GraphQL Java engine. `WebGraphQlInterceptor` allows an application to intercept +incoming requests and do one of the following: + +- Check HTTP request details +- Customize the `graphql.ExecutionInput` +- Add HTTP response headers +- Customize the `graphql.ExecutionResult` + +For example, an interceptor can pass an HTTP request header to a `DataFetcher`: [source,java,indent=0,subs="verbatim,quotes"] ---- -class HeaderInterceptor implements WebGraphQlInterceptor { +class HeaderInterceptor implements WebGraphQlInterceptor { <1> @Override public Mono intercept(WebGraphQlRequest request, Chain chain) { - List values = request.getHeaders().get("headerName"); + String value = request.getHeaders().getFirst("myHeader"); request.configureExecutionInput((executionInput, builder) -> - builder.graphQLContext(Collections.singletonMap("headerName", values)).build()); + builder.graphQLContext(Collections.singletonMap("myHeader", value)).build()); return chain.next(request); } } -// Subsequent access from a controller - @Controller -class MyController { +class MyController { <2> @QueryMapping Person person(@ContextValue String myHeader) { @@ -186,8 +196,10 @@ class MyController { } } ---- +<1> Interceptor adds HTTP request header value into GraphQLContext +<2> Data controller method accesses the value -Or reversely, add values to the `GraphQLContext` and use them to update the HTTP response: +Reversely, an interceptor can access values added to the `GraphQLContext` by a controller: [source,java,indent=0,subs="verbatim,quotes"] ---- @@ -195,7 +207,7 @@ Or reversely, add values to the `GraphQLContext` and use them to update the HTTP class MyController { @QueryMapping - Person person(GraphQLContext context) { + Person person(GraphQLContext context) { <1> context.put("cookieName", "123"); } } @@ -205,7 +217,7 @@ class MyController { class HeaderInterceptor implements WebGraphQlInterceptor { @Override - public Mono intercept(WebGraphQlRequest request, Chain chain) { + public Mono intercept(WebGraphQlRequest request, Chain chain) { <2> return chain.next(request).doOnNext(response -> { String value = response.getExecutionInput().getGraphQLContext().get("cookieName"); ResponseCookie cookie = ResponseCookie.from("cookieName", value).build(); @@ -214,13 +226,20 @@ class HeaderInterceptor implements WebGraphQlInterceptor { } } ---- +<1> Controller adds value to the `GraphQLContext` +<2> Interceptor uses the value to add an HTTP response header -The `WebGraphQlInterceptor` chain can be updated through the `WebGraphQlHandler` builder, -and the Boot starter uses this, see Boot's section on +You can add a `WebGraphQlInterceptor` through `WebGraphQlHandler` builder. The Boot starter +supports this, see {spring-boot-ref-docs}/web.html#web.graphql.transports.http-websocket[Web Endpoints]. -The <> transport handler delegates to a similar `GraphQlInterceptor` -chain that you can use to intercept GraphQL over RSocket requests. + +[[server-interception-rsocket]] +==== `RSocketQlInterceptor` + +Similar to <>, an `RSocketQlInterceptor` allows intercepting +GraphQL over RSocket requests before and after GraphQL Java engine execution. You can use +this to customize the `graphql.ExecutionInput` and the `graphql.ExecutionResult`.