如何在GraphQL-SPQR中设置标头变量

时间:2019-11-26 21:24:38

标签: spring-boot kotlin graphql graphql-java graphql-spqr

我正在使用GraphQL-SPQR和Spring Boot运行GraphQL API。

此刻,我抛出RuntimeException来返回GraphQL错误。我有一个实现customExceptionHandler的{​​{1}},它以正确的格式返回错误,如下所示:

DataFetcherExceptionHandler

我在我的主应用程序类中按如下方式使用class CustomExceptionHandler : DataFetcherExceptionHandler { override fun onException(handlerParameters: DataFetcherExceptionHandlerParameters?): DataFetcherExceptionHandlerResult { // get exception var exception = handlerParameters?.exception val locations = listOf(handlerParameters?.sourceLocation) val path = listOf(handlerParameters?.path?.segmentName) // create a GraphQLError from your exception if (exception !is GraphQLError) { exception = CustomGraphQLError(exception?.localizedMessage, locations, path) } // cast to GraphQLError exception as CustomGraphQLError exception.locations = locations exception.path = path val errors = listOf<GraphQLError>(exception) return DataFetcherExceptionHandlerResult.Builder().errors(errors).build() } }

CustomExceptionHandler

出于日志目的,我想为与异常对应的UUID设置标头变量。我该怎么办?

更好的是,是否可以创建一个Spring Bean,以便将UUID放在所有查询和突变的标头中?

谢谢!

1 个答案:

答案 0 :(得分:1)

使用Spring Boot时,有两种选择:

  • 您正在使用spring boot graphql spqr启动器(它带有自己的控制器来处理所有graphQL请求)
  • 您使用的是普通的graphql-spqr,并且拥有自己的控制器来处理GraphQL请求

无论如何,您都有一些选择:

使CustomExceptionHandler成为Spring Bean并自动装配HttpServletResponse

这可能是最简单的方法-在任何情况下都可能起作用:您可以简单地将CustomExceptionHandler设置为Spring bean,并使其自动装配HttpServletRequest-在handler方法中,然后可以将其设置为任何值你想成为那样。这是Java中的一些伪代码(对不起,我对Kotlin不够熟练):

@Component
class CustomExceptionHandler implements DataFetcherExceptionHandler {
    private final HttpServletResponse response; 

    public CustomExceptionHandler(HttpServletResponse response) {
        this.response = response; 
    }

    @Override
    public DataFetcherExceptionHandlerResult onException(DataFetcherExceptionHandlerParameters handlerParameters) {
        response.setHeader("X-Request-ID", UUID.randomUUID().toString());
        // ... your actual error handling code
    }
}

这将起作用,因为spring会意识到HttpServletRequest对于每个请求都是不同的。因此,它将向错误处理程序中注入一个动态代理,该代理将指向每个请求的实际HttpServletResponse实例。

我会争辩说,这不是最优雅的方法,但肯定会解决您的问题。

对于graphql-spqr弹簧启动启动器

在使用该启动器的项目中有一个default controller implementation。该控制器将处理您收到的每个graphql请求。您可以通过实现自己的GraphQLExecutor并将其制成Spring bean来对其进行自定义。该执行程序负责调用GraphQL引擎,传递参数并输出响应。这是the default implementation,您可能希望以此为基础。

类似于先前的解决方案,您可以在该类中自动连接HttpServletResponse并设置HTTP Response标头。

通过该解决方案,您可以决定是要在所有情况下还是仅在特定错误情况下设置请求ID。 (graphql.execute返回一个对象,如果有错误以及存在什么错误,您可以从中获取信息)

在不使用spring boot starter的情况下使用graphql-spqr时

找到您的GraphQL控制器,向该类型的HttpServletRequest方法添加一个参数-然后根据需要向其添加标头(请参见上一节中的一些更具体的建议)