今日在SpringBoot項目中使用 Spring Security ,登錄時發現報500錯,報錯信息如下:
There is no PasswordEncoder mapped for the id "null"
我接着查找了前端頁面上,發現密碼框的name屬性確實指定的是 password ,並沒有出錯。這是怎么回事呢?
於是就上網百度,發現這是由於Spring security5中新增加了加密方式,並把原有的spring security的密碼存儲格式改了。
去官網查找得知,修改后的密碼存儲格式為:
{id}encodedPassword
於是大概就明白了程序出錯的原因: 前端傳過來密碼后,程序會查找被 花括號"{}"包括起來的id ,以此來確定后面的密碼怎么進行加密,而我們在前面並沒有按該格式進行處理,這就導致找不到id,就報錯了。
明白了報錯的原因,就好解決了, 我們只需要對前端傳過來的密碼進行某種方式加密,就可以了,而官方推薦的是使用bcrypt的加密方式。解決辦法如下:
在Securty配置類SecurtyConfig(繼承 WebSecurityConfigurerAdapter)中修改 配置即可。
-
@EnableWebSecurity
-
public
class SecurtyConfig extends WebSecurityConfigurerAdapter {
-
/**
-
* 自定義配置
-
*
-
* @param http
-
* @throws Exception
-
*/
-
@Override
-
protected void configure(HttpSecurity http) throws Exception {
-
http.authorizeRequests()
-
.antMatchers(
"/css/**",
"/js/**",
"/fonts/**",
"/index").permitAll()
//都可以訪問
-
.antMatchers(
"/users/**").hasRole(
"ADMIN")
//需要相應的角色才能訪問
-
.and()
-
.formLogin()
//基於Form表單登錄驗證
-
.loginPage(
"/login").failureUrl(
"/login-error");
//自定義登錄界面
-
}
-
-
/**
-
* 認證信息管理
-
* spring5中摒棄了原有的密碼存儲格式,官方把spring security的密碼存儲格式改了
-
*
-
* @param auth
-
* @throws Exception
-
*/
-
@Autowired
-
public void configureGlobal(AuthenticationManagerBuilder auth) throws Exception {
-
auth.inMemoryAuthentication()
//認證信息存儲到內存中
-
.passwordEncoder(passwordEncoder())
-
.withUser(
"user").password(passwordEncoder().encode(
"123456")).roles(
"ADMIN");
-
}
-
-
private PasswordEncoder passwordEncoder() {
-
return
new BCryptPasswordEncoder();
-
}
-
}
主要是需要對 密碼進行加密操作,定義的 passwordEncoder() 方法返回一個 BCryptPasswordEncoder對象,對上面的密碼進行加密。這樣就解決了該問題。
另外 還有一個也可以解決.
-
@Bean
-
public static PasswordEncoder passwordEncoder(){
-
return NoOpPasswordEncoder.getInstance();
-
}
該方法已經過時,不建議使用。