AuthenticationPrincipal is empty when using EnableWebSecurity

后端 未结 4 840
挽巷
挽巷 2021-01-13 03:25

As of Spring Security doc: 34.1 @EnableWebMvcSecurity states, the @EnableWebMvcSecurity was replaced by @EnableWebSecurity.

But when I try

4条回答
  •  执笔经年
    2021-01-13 03:41

    I met the same problem. I had to make my own HandlerMethodArgumentResolver and annotation. The following code have been tested and works

    First create the annotation

    @Target({ ElementType.PARAMETER, ElementType.ANNOTATION_TYPE })
    @Retention(RetentionPolicy.RUNTIME)
    public @interface CurrentUser{}
    

    And a simple config

    @Configuration
    @EnableWebMvc
    @ComponentScan(basePackages = "x.x.x")
    public class ApplicationConfiguration extends WebMvcConfigurerAdapter{
    
        @Override
        public void addArgumentResolvers(List argumentResolvers) {
            argumentResolvers.add(new HandlerMethodArgumentResolver() {
    
                public boolean supportsParameter(MethodParameter parameter) {
                    return findMethodAnnotation(CurrentUser.class, parameter) != null;
                }
    
                public Object resolveArgument(
                        MethodParameter parameter,
                        ModelAndViewContainer mavContainer,
                        NativeWebRequest webRequest,
                        WebDataBinderFactory binderFactory) throws Exception
                {
                    Authentication authentication = SecurityContextHolder.getContext().getAuthentication();
                    Object principal = authentication.getPrincipal();
    
                    if(principal != null && !parameter.getParameterType().isAssignableFrom(principal.getClass()))
                        throw new ClassCastException(principal + " is not assignable to " + parameter.getParameterType());
    
                    return principal;
                }
    
                 T findMethodAnnotation(Class annotationClass, MethodParameter parameter) {
                    T annotation = parameter.getParameterAnnotation(annotationClass);
                    if(annotation != null) {
                        return annotation;
                    }
                    Annotation[] annotationsToSearch = parameter.getParameterAnnotations();
                    for(Annotation toSearch : annotationsToSearch) {
                        annotation = AnnotationUtils.findAnnotation(toSearch.annotationType(), annotationClass);
                        if(annotation != null) {
                            return annotation;
                        }
                    }
                    return null;
                }
            });
        }
    }
    

    And then use it in a controller

    @RequestMapping("/userget")
    public User message(@CurrentUser User user){
        return user;
    }
    

    Note that User does not require to extends UserDetails anyamore. Hope this (will) help(s)

提交回复
热议问题