Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/spring/11.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java Spring安全性-@预授权不工作_Java_Spring_Spring Security - Fatal编程技术网

Java Spring安全性-@预授权不工作

Java Spring安全性-@预授权不工作,java,spring,spring-security,Java,Spring,Spring Security,我在使用@PreAuthorize注释时遇到了一个问题。即使我的用户不拥有所请求的角色,也会执行我的安全方法 我的控制器: @Controller @RequestMapping("/stats/distributions") public class DistributionStatsController { @PreAuthorize("hasAnyAuthority('AK_LOCAL_DIST_INT', 'AK_ADMIN')") @RequestMapping(me

我在使用
@PreAuthorize
注释时遇到了一个问题。即使我的用户不拥有所请求的角色,也会执行我的安全方法

我的控制器:

@Controller
@RequestMapping("/stats/distributions")
public class DistributionStatsController {

    @PreAuthorize("hasAnyAuthority('AK_LOCAL_DIST_INT', 'AK_ADMIN')")
    @RequestMapping(method = RequestMethod.POST, consumes = "application/json; charset=utf-8", 
        produces = "application/json; charset=utf-8")
    public @ResponseBody List<DistributionStatsResource> filter(@RequestBody DistributionStatsResource resource,  
           @RequestParam(required = false, value = "documentId") Long documentId, 
           @RequestParam(required = false, value = "distStatus") EnumDistributionStatus distributionStatus, 
           Pageable pageable, HttpServletRequest request) {
    }
}
我注册了这个类,我们得到了登录用户的权限。一切似乎都很好

当我与一个只有
aku CONSULT
角色的用户一起运行此代码时,将执行该方法,并且不会触发
503错误


谢谢你的帮助。

我的同事们找到了窍门。 @EnableGlobalMethodSecurity(prespenabled=true)注释必须
spring-security
配置类中,但在Servlet配置类中。

@Configuration
@EnableWebMvc
@EnableSpringDataWebSupport
@EnableJpaRepositories
@EnableGlobalMethodSecurity(prePostEnabled = true)
@ComponentScan(basePackages = { "mypackage.spring.rest" }, excludeFilters = @Filter(type = FilterType.ANNOTATION, value = Configuration.class))
public class SpringRestConfiguration {

}

而且它有效

TLDR:
@EnableAspectJAutoProxy(proxyTargetClass=true)
可以改为在WebConfig上使用

问题的根源可能是Spring不生成控制器的代理类——默认情况下,Spring只将定义为接口和Spring IoC的bean包装到代理中,以找到它们的实现。如果您的控制器是不实现/扩展任何内容的类,则必须使用CGLIB代理(我建议您阅读,因此,代理类被生成并作为控制器实现注入——这就是Spring包含额外逻辑以尊重
@PreAuthorize
@posauthorize
注释条件的地方

在SpringV5(非SpringBoot)上,当
@EnableGlobalMethodSecurity(prespenabled=true)
仅用于
SecurityConfiguration
时,
WebConfig
将不会拾取它。将其移动到
WebConfig
将使Spring Security能够处理前后注释,并将打开CGLIB代理机制

就个人而言,我建议只在WebConfig上添加
@EnableAspectJAutoProxy(proxyTargetClass=true)
,并将
@EnableGlobalMethodSecurity
留在
安全配置中


我只在SpringV5上测试过它,但由于文档的原因,它在SpringV4上的工作原理应该是一样的。

使用XML配置Spring时,必须在SpringMVC上下文上启用“pre-post”,而不是在SpringSecurity上启用。这是否与您遇到的问题相同(我不太喜欢使用注释来配置Spring)?您可以看看这里,我认为这也是一个类似的问题,可能会有所帮助:它看起来像我的问题。但为了解决这个问题,他将注释设置在服务层上,而不是控制器上(我希望如此)。正如他们在一篇评论中所说,在web上有很多这样的示例,其中该注释位于控制器中。粘贴所有代码,包括实现日志的userDetails类的位置inI添加了所有安全配置类内容和my RequestHeaderAuthenticationFilter类。
public class NgwisRequestHeaderAuthenticationFilter extends RequestHeaderAuthenticationFilter {

    public static final String HABILE_FILTER_NAME = "HABILE";

    /** Pour mise à disposition des informations de sécurité */
    public static final String BEAN_SECURITIES = "com.airfrance.springsecurity.securities";

    private static final org.slf4j.Logger logger = LoggerFactory.getLogger(NgwisRequestHeaderAuthenticationFilter.class);

    // AK de l'utilisateur en fonction de ses profils
    private UserAccessKeys userAccessKeys = null;

    // Pour passer l'info au niveau de la config de spring security
    private String credentialsRequestHeader;

    @Inject
    private IAgentService agentService;

    @Inject
    private DozerBeanMapper mapper;

    /** Credentials aren't usually applicable, but if a {@code credentialsRequestHeader} is set, this will be read and used as
     * the credentials value. Otherwise a dummy value will be used. */
    @Override
    protected Object getPreAuthenticatedCredentials(HttpServletRequest request) {
        Collection<GrantedAuthority> tmp = new ArrayList<GrantedAuthority>();
        User user = new User(request.getRemoteUser().toUpperCase(), "none", false, false, false, false, tmp);
        if (credentialsRequestHeader != null) {
            if (credentialsRequestHeader.equalsIgnoreCase("HABILE")) {
                try {
                    LdapBean ldBean = LdapBeanAccessor.getLdapBean(request);
                    if (ldBean != null) {
                        userAccessKeys = new UserAccessKeys(request, ldBean, agentService, mapper);
                        request.getSession().setAttribute(BEAN_SECURITIES, userAccessKeys);
                        List<String> auths = new ArrayList<String>();
                        for (GrantedAuthority auth : userAccessKeys.getAuthorities()) {
                            auths.add(auth.getAuthority());
                        }
                        logger.debug("User {} connected with authorities {}", userAccessKeys.getLogin(), StringUtils.join(auths, ", "));
                        user = new User(request.getRemoteUser().toUpperCase(), "none", true, true, true, true, userAccessKeys.getAuthorities());
                    }
                } catch (NoLdapBeanInSessionException e) {
                    logger.error("Erreur lors de la connexion de {}", request.getRemoteUser().toUpperCase(), e);
                } catch (NotProtectedGetLdapException e) {
                    logger.error("Erreur technique ", e);
                }
                if (userAccessKeys.getAgent() != null) {
                    return user;
                } else {
                    return null;
                }
            } else {
                return request.getHeader(credentialsRequestHeader);
            }
        }

        return "N/A";
    }

    @Override
    public void setCredentialsRequestHeader(String credentialsRequestHeader) {
        Assert.hasText(credentialsRequestHeader, "credentialsRequestHeader must not be empty or null");
        this.credentialsRequestHeader = credentialsRequestHeader;
    }
}
@Configuration
@EnableWebMvc
@EnableSpringDataWebSupport
@EnableJpaRepositories
@EnableGlobalMethodSecurity(prePostEnabled = true)
@ComponentScan(basePackages = { "mypackage.spring.rest" }, excludeFilters = @Filter(type = FilterType.ANNOTATION, value = Configuration.class))
public class SpringRestConfiguration {

}