在Spring Boot项目

时间:2018-06-25 10:34:33

标签: spring spring-boot thymeleaf

我正在学习spring boot并编写一个注册表,但是当我运行它并提交表单时,浏览器就会出现

  

发生意外错误(类型=禁止,状态= 403)。   禁止

我实际上是通过使用spring initializr创建项目的,选择web + jpa + h2 + thymeleaf。 我定义了一个名为Worker的实体,并在ValidationMessages.properties中设置了错误消息,这里是Worker实体

@Entity
public class Worker implements UserDetails {

    private static final long serialversionUID = 1L;

    @Id
    @NotNull
    @Size(min = 5, max = 16, message = "{username.size}")
    private String username;
    @NotNull
    @Size(min = 2, max = 30, message = "{firstName.size}")
    private String firstname;
    @NotNull
    @Size(min = 2, max = 30, message = "{lastName.size")
    private String lastname;
    @NotNull
    @Size(min = 5, max = 25,message = "{password.size}")
    private String password;
    @NotNull
    @Size(min = 2, max = 30, message = "{profession,size}")
    private String profession;

    public String getUsername() {
        return username;
    }

    public void setUsername(String username) {
        this.username = username;
    }

    public String getFirstname() {
        return firstname;
    }

    public void setFirstname(String firstname) {
        this.firstname = firstname;
    }

    public String getLastname() {
        return lastname;
    }

    public void setLastname(String lastname) {
        this.lastname = lastname;
    }

    public String getPassword() {
        return password;
    }

    public void setPassword(String password) {
        this.password = password;
    }

    public String getProfession() {
        return profession;
    }

    public void setProfession(String profession) {
        this.profession = profession;
    }

    //UserDetails methods


    @Override
    public Collection<? extends GrantedAuthority> getAuthorities() {
        return Arrays.asList(new SimpleGrantedAuthority("WORKER"));
    }

    @Override
    public boolean isAccountNonExpired() {
        return true;
    }

    @Override
    public boolean isAccountNonLocked() {
        return true;
    }

    @Override
    public boolean isCredentialsNonExpired() {
        return true;
    }

    @Override
    public boolean isEnabled() {
        return true;
    }
}

和工人资料库

public interface WorkersRepository extends JpaRepository<Worker, String> {
Worker findByUsername(String username);

}

我添加了spring安全性,并编写了配置文件:

@Configuration
@EnableWebSecurity
public class SecurityConfig extends WebSecurityConfigurerAdapter {

    @Autowired
    private WorkersRepository workersRepository;

    @Override
    protected void configure(HttpSecurity http) throws Exception {
        http
            .authorizeRequests()
            .antMatchers("/submit").access("hasRole('WORKER')")
            .anyRequest().permitAll()
            .and()
            .formLogin()
            .loginPage("/login")
            .and()
            .logout()
            .logoutSuccessUrl("/")
            .and()
            .rememberMe()
            .tokenValiditySeconds(4838400)
            .key("workerKey");
    }

    @Override
    protected void configure(AuthenticationManagerBuilder auth) throws      Exception {
        auth.userDetailsService(new UserDetailsService() {
            @Override
            public UserDetails loadUserByUsername(String username) throws       UsernameNotFoundException {
                return workersRepository.findByUsername(username);
            }
        });
    }
}

如果寄存器输入发生错误,则控制器返回registerForm.html要求用户再次正确输入。如果寄存器没有错误,则控制器将重定向到简单的welcome.html“ /”。但是无论输入是否正确,我总是会收到错误403。输入http://localhost:8080/时,我可以获取welcome.html,这是一个带有“ welcome!”的简单页面。话。我的控制器是

private WorkersRepository workersRepository;

@Autowired
public  WorkingHoursController(
        WorkersRepository workersRepository) {
    this.workersRepository = workersRepository;
}

@RequestMapping(method = RequestMethod.GET)
public String welcomePage() {
    return "welcome";
}

@RequestMapping(value = "/register", method = RequestMethod.GET)
public  String showRegistrationForm(Model model) {
    model.addAttribute(new Worker());
    return "registerForm";
}

@RequestMapping(value = "/register", method = RequestMethod.POST)
public String registrationProcessing(@Valid Worker worker, Errors errors, RedirectAttributes model) {
    if(errors.hasErrors()) {
        return "registerForm";
    }
    workersRepository.save(worker);
    model.addAttribute("username", worker.getUsername());
    model.addFlashAttribute("worker", worker);
    return "redirect:/";
}
...

我使用百里香叶编写了registerForm.html并添加了错误验证。我的registerForm.html是

<form class="form-signin" method="post" th:object="${worker}">
<div class="errors" th:if="${#fields.hasErrors('*')}">
    <ul>
        <li th:each="err : ${#fields.errors('*')}"
            th:text="${err}">Input is in correct.</li>
    </ul>
</div>
<img class="mb-4" src="https://getbootstrap.com/assets/brand/bootstrap-solid.svg" alt="" width="72" height="72">
<h1 class="h3 mb-3 font-weight-normal">Please register</h1>

<!-- input username -->
<label for="inputUsername" th:class="${#fields.hasErrors('username')}? 'error'">Username</label>
<input type="text" id="inputUsername" th:field="*{username}" th:class="${#fields.hasErrors('username')}? 'error form-control':'form-control'" placeholder="Username">
...
<!-- input password -->
<label for="inputPassword" th:class="${#fields.hasErrors('password')}? 'error'">Password</label>
<input type="password" id="inputPassword" th:field="*{password}" th:class="${#fields.hasErrors('password')}? 'error form-control':'form-control'" placeholder="Password">
<div class="checkbox mb-3">
    <label>
        <input type="checkbox" id="remember-me" name="remember-me"> Remember me
    </label>
</div>
<button class="btn btn-lg btn-primary btn-block" type="submit">Register</button>

在我在thymeleaf中添加验证并添加spring安全性之前,一切似乎都正常运行。

3 个答案:

答案 0 :(得分:3)

您没有在form标签内进行任何操作。也许这就是为什么您会出错。将动作放入这样的表单标签中

<form class="form-signin" action="#" th:action="@{/register}" method="post" th:object="${worker}">

答案 1 :(得分:0)

请根据您的Spring Security JAR版本检查一次角色是“ WORKER”还是“ ROLE_WORKER”。另外,在您的应用程序中禁用CSRF,并设置全局CORS配置以接受所有请求。

答案 2 :(得分:0)

将以下内容添加到您的配置类中

@Override
public void configure(HttpSecurity http) throws Exception {
    http 
        .csrf() 
        .disable() 
}

这是安全性的东西,它可以防止黑客在未经您的许可的情况下使用您的开放帐户凭据,即,您收到一封电子邮件,单击“单击此处”(单击将您的用户信息未经您的同意而带到另一个站点)。仅将以上内容用于开发。 对于亲将csrf令牌添加为表单上的隐藏输入。这个令牌在您的spring服务器中。

<input type="hidden" name="_csrf" th:value="${_csrf.token}"/>