在 Spring Security 中禁用浏览器身份验证对话框

use*_*956 6 java spring spring-mvc spring-security

我正在使用 spring security 4,出于某种原因,在我完成登录页面的身份验证后,我收到浏览器身份验证对话框,这迫使我再次进行身份验证。

这是我的安全配置:

    http.antMatcher("/test")
            .httpBasic()
            .and()
            .authorizeRequests()
            .antMatchers("/index.html", "/login.html", "/", "/scripts/**",
                    "/bower_components/**", "/styles/**", "/views/**",
                    "/login", "/api/user/*").permitAll().anyRequest()
            .authenticated().and().logout().logoutUrl("/api/logout").and()
            .csrf().csrfTokenRepository(csrfTokenRepository()).and()
            .addFilterAfter(csrfHeaderFilter(), CsrfFilter.class);
Run Code Online (Sandbox Code Playgroud)

Mar*_*idt 11

身份验证弹出窗口是由响应标头引起的,该标头WWW-Authenticate: BasicBasicAuthenticationEntryPoint设置。

使用AuthenticationEntryPoint未设置的自定义WWW-Authenticate: Basic

public class NoPopupBasicAuthenticationEntryPoint implements AuthenticationEntryPoint {

    @Override
    public void commence(HttpServletRequest request, HttpServletResponse response,
        AuthenticationException authException) throws IOException, ServletException {
    
        response.sendError(HttpServletResponse.SC_UNAUTHORIZED, authException.getMessage());
    }

}
Run Code Online (Sandbox Code Playgroud)

将自定义身份验证入口点添加到安全配置(顺序很重要):

http
    .httpBasic()
    .authenticationEntryPoint(new NoPopupBasicAuthenticationEntryPoint())
Run Code Online (Sandbox Code Playgroud)


Vla*_*yar 5

在 WebFlux 中,仅禁用 httpBasic 是不够的。有一个 ExceptionTranslationWebFilter 默认使用 HttpBasicServerAuthenticationEntryPoint,导致这种行为。要禁用它,您应该安装另一个 ServerAuthenticationEntryPoint,例如:

http.exceptionHandling()
    .authenticationEntryPoint(HttpStatusServerEntryPoint(HttpStatus.FORBIDDEN))
    .
Run Code Online (Sandbox Code Playgroud)


Abh*_*Rai 2

使用formLogin()而不是httpBasic(). 将您的配置重构为:

http
   .antMatcher("/test")
   .authorizeRequests()
   .antMatchers("/index.html", "/login.html", "/", "/scripts/**",
       "/bower_components/**", "/styles/**", "/views/**",
       "/login", "/api/user/*").permitAll()
   .anyRequest().authenticated()
   .and().formLogin().loginPage("/your_login_page_here").permitAll()
   .and().logout().logoutUrl("/api/logout").and()
   .csrf().csrfTokenRepository(csrfTokenRepository()).and()
   .addFilterAfter(csrfHeaderFilter(), CsrfFilter.class);
Run Code Online (Sandbox Code Playgroud)

如果/login.html是您的登录页面,您可能希望将其从其中一个permitAll()位置删除。