如何修复由 SpringSecurity 引起的 Forbidden 403 错误?

Posted

技术标签:

【中文标题】如何修复由 SpringSecurity 引起的 Forbidden 403 错误?【英文标题】:How to fix Forbidden 403 error caused by SpringSecurity? 【发布时间】:2019-09-22 01:59:24 【问题描述】:

我正在运行 Spring Boot 应用程序,但无法从 html 表单中请求参数。每当我尝试使用 POST 方法通过表单发送参数时,它都会引发 Forbidden 403 错误。即使我将 spring 安全设置更改为 anyRequest.permitAll,它仍然会抛出 403。知道如何解决这个问题吗?

mastermind_home.jsp:

<form action="/mastermind/home" method="POST">
            <label>
                <input type="radio" name="difficulty" value="easy">
            </label>Easy<br>
            <label>
                <input type="radio" name="difficulty" value="medium" checked>
            </label>Medium<br>
            <label>
                <input type="radio" name="difficulty" value="hard">
            </label>Hard<br>
            <input type="submit" value="Start game">
        </form>`

控制器:

@AllArgsConstructor
@Controller
@RequestMapping("mastermind")
public class MastermindController 

private MastermindServiceImpl mastermindService;
private UserService userService;

@GetMapping("/home")
public String prepareMmHomePage() 
    return "mastermind_home";

@PostMapping("/home")
public String formRequest( @RequestParam String difficulty) 
    return "mastermind_home";

Spring 安全设置:

@Configuration
public class SecurityConfiguration extends WebSecurityConfigurerAdapter 

private DataSource dataSource;

public SecurityConfiguration(DataSource dataSource) 
    this.dataSource = dataSource;


@Bean
public PasswordEncoder passwordEncoder() 
    return PasswordEncoderFactories.createDelegatingPasswordEncoder();


@Bean
public Authentication authentication() 
    return SecurityContextHolder.getContext().getAuthentication();


@Override
protected void configure(AuthenticationManagerBuilder auth) throws   Exception 
    auth.jdbcAuthentication()
            .dataSource(dataSource)
            .passwordEncoder(passwordEncoder())
            .usersByUsernameQuery("SELECT user_name, password, true FROM users WHERE user_name = ?")
            .authoritiesByUsernameQuery("SELECT user_name, 'ROLE_USER' FROM users WHERE user_name = ?");


@Override
public void configure(WebSecurity web) throws Exception 
    super.configure(web);


@Override
protected void configure(HttpSecurity http) throws Exception 
    http.authorizeRequests()
            .antMatchers("/main_menu","/mastermind/**").authenticated()
            .antMatchers("/admin", "/admin/**").hasRole("ADMIN")
            .antMatchers("/home", "/register", "/registered_successfully").anonymous()
            .anyRequest().authenticated()
            .and()
            .formLogin()
            .defaultSuccessUrl("/main_menu")
            .and()
            .logout()
            .logoutSuccessUrl("/home");



【问题讨论】:

【参考方案1】:

在 spring 安全配置中禁用 csrf 解决了我的问题。

and()
.csrf().disable();

我的问题的另一个更好的解决方案:在 spring security 我添加了:

.antMatchers(HttpMethod.POST, "/mastermind/home").authenticated()

并在 jsp 中形成一个验证 csrf 的令牌:

<input type="hidden" name="$_csrf.parameterName" value="$_csrf.token" />

【讨论】:

【参考方案2】:

将此添加到 spring security 以忽略 url 模式

@Override
public void configure(WebSecurity webSecurity) throws Exception 
    webSecurity.ignoring()
            // All of Spring Security will ignore the requests.
            .antMatchers("/mastermind/home");


@Override
protected void configure(HttpSecurity http) throws Exception 
 ..........

【讨论】:

使用你的方法我可以 POST 参数并且我没有得到任何异常,但现在我无法从会话中获取用户... 给出的配置完全忽略了 Spring Security 的 url 模式,所以如果你需要会话没有会话,那么这个解决方案将不起作用【参考方案3】:

在您的 Spring 安全配置中,您指定所有对以 /mastermind 开头的 URL 的请求都需要经过身份验证 (.antMatchers("/main_menu","/mastermind/**").authenticated())。

如果您想为POST /mastermind/home 设置一个例外,那么您需要将您的配置更改为如下所示

http.authorizeRequests()
        .antMatchers(HttpMethod.POST, "/mastermind/home").permitAll()
        .antMatchers("/main_menu","/mastermind/**").authenticated()
        ....

请注意这两行的顺序很重要,因为 Spring 以相同的顺序匹配请求 URL。

【讨论】:

这个解决方案对我不起作用。仍然 403 被禁止。

以上是关于如何修复由 SpringSecurity 引起的 Forbidden 403 错误?的主要内容,如果未能解决你的问题,请参考以下文章

如何修复由 Pycharm 中的 Tensorflow 引起的 cudart64_110.dll 错误?

如何修复由 CSS 动画引起的奇怪色带?

如何修复由数据类型关系引起的“变量“$_v0_data”得到无效值' - Mutation Resolver

如何修复由 react-redux 中的循环依赖引起的“不变违规”

如何修复由目的地引起的膨胀错误不是此 NavGraph 的直接子级

如何修复由 Caused by: java.lang.NumberFormatException: For input string: "pets" 引起的 Asynctask 错