註冊 Spring Security – 密碼編碼

Spring Security
Remote
0
09:14 PM · Nov 29 ,2025

1. 概述

在本教程中,我們將討論註冊過程中的一個關鍵部分,密碼編碼,它基本上是指不將密碼存儲為純文本。

Spring Security 支持幾種編碼機制,對於本教程,我們將使用 BCrypt,因為它通常是可用的最佳解決方案。

其他機制,如 MD5PasswordEncoderShaPasswordEncoder,使用較弱的算法並且現在已被棄用。

2. 定義密碼編碼器

我們首先將簡單的BCryptPasswordEncoder定義為配置中的一個Bean:

@Bean
public PasswordEncoder encoder() {
    return new BCryptPasswordEncoder();
}

較早的實現,如SHAPasswordEncoder,需要客户端在編碼密碼時傳遞鹽值。

但是,BCrypt會在內部生成一個隨機鹽。 這很重要,因為它意味着每次調用都會產生不同的結果,因此我們只需要編碼密碼一次。

為了使隨機鹽生成工作,BCrypt會將鹽存儲在哈希值本身中。 例如,以下哈希值:

$2a$10$ZLhnHxdpHETcxmtEStgpI./Ri1mksgJ9iDP36FmfMdYyVg9g0b2dq

這三個字段之間用$分隔:

  1. “2a”代表BCrypt算法版本
  2. “10”代表算法的強度
  3. “ZLhnHxdpHETcxmtEStgpI”部分實際上是隨機生成的鹽。 基本上,前22個字符是鹽。 剩餘的部分是實際的文本哈希版本。

另外,請注意,BCrypt算法生成一個長度為60的字符串,因此我們需要確保密碼將被存儲在能夠容納它的列中。 常見錯誤是創建不同長度的列,然後在身份驗證時出現無效用户名或密碼錯誤。

3. 註冊時對密碼進行編碼

我們將使用 PasswordEncoder 在我們的 UserService 中,在用户註冊過程中對密碼進行哈希:

示例 3.1. UserServic e 對密碼進行哈希

@Autowired
private PasswordEncoder passwordEncoder;

@Override
public User registerNewUserAccount(UserDto accountDto) throws EmailExistsException {
    if (emailExist(accountDto.getEmail())) {
        throw new EmailExistsException(
          "There is an account with that email adress:" + accountDto.getEmail());
    }
    User user = new User();
    user.setFirstName(accountDto.getFirstName());
    user.setLastName(accountDto.getLastName());
    
    user.setPassword(passwordEncoder.encode(accountDto.getPassword()));
    
    user.setEmail(accountDto.getEmail());
    user.setRole(new Role(Integer.valueOf(1), user));
    return repository.save(user);
}

4. 在身份驗證時編碼密碼

現在我們將處理這個過程的另一半,並在用户身份驗證時編碼密碼。

首先,我們需要將我們在前面定義的密碼編碼器 Bean 注入到我們的身份驗證提供程序中:

@Autowired
private UserDetailsService userDetailsService;

@Bean
public DaoAuthenticationProvider authProvider() {
    DaoAuthenticationProvider authProvider = new DaoAuthenticationProvider();
    authProvider.setUserDetailsService(userDetailsService);
    authProvider.setPasswordEncoder(encoder());
    return authProvider;
}

安全配置非常簡單:

  • 我們注入了我們的用户詳情服務實現
  • 我們定義了一個引用我們詳情服務的身份驗證提供程序
  • 我們還啓用了密碼編碼器

最後,我們需要在我們的安全 XML 配置中引用這個身份驗證提供程序:

<authentication-manager>
    <authentication-provider ref="authProvider" />
</authentication-manager>

或者,如果我們在使用 Java 配置:

@Configuration
@ComponentScan(basePackages = { "com.baeldung.security" })
@EnableWebSecurity
public class SecSecurityConfig {

    @Bean
    public AuthenticationManager authManager(HttpSecurity http) throws Exception {
        return http.getSharedObject(AuthenticationManagerBuilder.class)
            .authenticationProvider(authProvider())
            .build();
    }
    
    ...
}

5. 結論

本文檔繼續介紹註冊系列,通過利用簡單但非常強大的BCrypt實現,演示如何正確地將密碼存儲在數據庫中。

下一條 »
註冊API變得RESTful
« 上一篇
Spring Security 註冊 – 發送驗證郵件
user avatar
0 位用戶收藏了這個故事!
收藏

發佈 評論

Some HTML is okay.