0

我的 Spring MVC Web 应用程序中有一个相当简单的 Spring Security 配置。我正在接收来自远程 Web 应用程序的 REST 请求,这些请求通过我的 preauth 过滤器进行了身份验证。我只是在请求中查找标头,如果存在,我返回该字符串值(即用户名)作为身份验证对象。这工作正常,当请求进来时,用户会得到身份验证。

无论出于何种原因,每当我尝试强制执行基于模式的安全性 antMatcher 或控制器方法注释的安全性时,都会导致客户端收到 CORS 错误。我必须保持访问完全开放,以允许在这个跨域环境中进行实际请求。

我的问题是,一段时间后,会话似乎到期了。当用户点击我的一个控制器并尝试从 Principal 对象中获取用户名时,我会收到 NullPointerException,因为 Principal 为空。一旦它过期,它看起来像 AnonymousAuthFilter 启动并让用户以匿名方式连接。

我假设我不想要一个完全无状态的身份验证会话,因为我也在使用 websockets 的会话,当我使用我的消息传递模板来“convertAndSendToUser”时,我需要提供用户名和 Spring 需要查找网络套接字会话。但是,我想强制安全链识别传入请求是否没有分配主体,以通过我的 PreAuthFilter 强制请求返回并重新建立会话。

这可能吗?

以下是我的安全配置文件中配置方法的简要说明:

@Override
    protected void configure(HttpSecurity http) throws Exception {
        // Create authentication providers and authentication manager
        List<AuthenticationProvider> authenticationProviders = new ArrayList<>(1);
        AuthenticationProvider authProvider = preAuthenticatedAuthenticationProvider();
        authenticationProviders.add(authProvider);
        AuthenticationManager authenticationManager = authenticationManager(authenticationProviders);

        // Create the pre-authentication filter
        MyPreAuthFilter myPreAuthFilter = myPreAuthFilter(authenticationManager);
        myPreAuthFilter.setAuthenticationManager(authenticationManager);

        // configure http security
        http
                .csrf().disable()
                .headers().addHeaderWriter(new XFrameOptionsHeaderWriter(XFrameOptionsHeaderWriter.XFrameOptionsMode.SAMEORIGIN))
                .and()
                .authenticationProvider(authProvider)
                .addFilter(myPreAuthFilter)
                .authorizeRequests()
                .antMatchers(HttpMethod.OPTIONS, "/**").permitAll()
                .antMatchers("/stomp/**").permitAll()
                .antMatchers("/**").permitAll();
    }

更新:所以我刚刚在 http 对象上了解了这个方法:

.anonymous().disable()

但是,当我使用它时,我所有的 CORS 请求都会再次失败。我认为这个问题特别是预检 OPTIONS 请求。这不能被验证——它需要匿名访问。因此,我认为要从跨域身份验证中获得我想要的行为,我需要禁用匿名过滤器,但这样做会破坏能够执行跨域请求的关键租户之一。啊。有人知道如何为除 OPTIONS 之外的所有请求禁用匿名吗?

4

1 回答 1

2

在您的 Web 应用程序初始化程序(或 web.xml)中的 spring 安全过滤器链之前放入CORS 过滤器 以消除 CORS 问题(通过将 Access-Control-Allow-Origin 设置为与您的请求来源匹配来允许 REST 请求的来源) .

然后您可以使用基于角色(通过 ant 匹配器和 JSR-250 注释)的授权。对于您提供的用例,禁用匿名用户似乎不是一个好主意。

于 2015-07-16T04:19:42.223 回答