问题
I am trying to create some authentication mechanism for my spring-boot/graphQL/SPQR-project. I managed to do it on a single service method via @GraphQLRootContext annotation:
@GraphQLMutation(name = "createProblem")
public Problem createProblem(
@GraphQLRootContext DefaultGlobalContext<Object> context,
@GraphQLArgument(name = "problemInput") @Valid Problem problemInput)
{
WebRequest request = (WebRequest) context.getNativeRequest();
String token = request.getHeader("token");
}
here I can extract a JWT token and verify/validate it. However, I want to do that on a global level without having to add the context parameter to all of my methods. I am trying to implement a ResolverInterceptor as described here.
However, I don't know how to register this Interceptor with the spring application, so that it is invoked properly. Can anyone help me?
Thanks in advance, Matthias
回答1:
I'd whole-heartedly suggest you use existing Spring features for handling security instead of rolling out your own, as it already has everything you need to process JWT. Since SPQR will invoke Spring-managed beans, all Spring features will work normally.
If that's for some reason not an option, yes, ResolverInterceptor
is the way to go, as it can intercept any resolver invocation and inspect the root context.
For your case, if you want a ResolverInterceptor
that is applicable globally (to all resolvers), you can use GlobalResolverInterceptorFactory
:
@Bean
public ExtensionProvider<GeneratorConfiguration, ResolverInterceptorFactory> customInterceptors() {
return (config, interceptors) -> interceptors.append(new GlobalResolverInterceptorFactory(customGlobalInterceptors);
}
If you want to optimize a bit and intercept some resolvers only e.g. based on an annotation, you can provide a custom ResolverInterceptorFactory
like:
public class AuthInterceptorFactory implements ResolverInterceptorFactory {
List<ResolverInterceptor> authInterceptor = Collections.singletonList(new AuthInterceptor());
@Override
public List<ResolverInterceptor> getInterceptors(ResolverInterceptorFactoryParams params) {
return params.getResolver().getTypedElement().isAnnotationPresent(Auth.class) ? authInterceptor : Collections.emptyList();
}
}
Inside of your ResolverInterceptor
if the token in missing or invalid, you want to throw an AbortExecutionException
to prevent further execution.
来源:https://stackoverflow.com/questions/57234905/how-to-register-resolverinterceptors-with-spqr-and-spring