1. 概述
在本快速教程中,我們將討論如何在註冊流程後立即自動驗證用户——在 Spring Security 實現中。
簡單來説,一旦用户完成註冊,他們通常會被重定向到登錄頁面,並需要重新輸入用户名和密碼。
讓我們看看如何通過自動驗證用户來避免這種情況。
在開始之前,請注意,我們正在本網站的註冊系列範圍內工作。
2. 使用 HttpServletRequest
通過利用 HttpServletRequest 的 login() 方法,可以以一種非常簡單的方式實現程序化強制認證:
public void authWithHttpServletRequest(HttpServletRequest request, String username, String password) {
try {
request.login(username, password);
} catch (ServletException e) {
LOGGER.error("登錄過程中出現錯誤 ", e);
}
}
現在,在底層,HttpServletRequest.login() API 使用 AuthenticationManager 來執行認證。
重要的是要理解並處理在此級別可能發生的 ServletException。
3. 使用 AuthenticationManager
接下來,我們還可以直接創建 UsernamePasswordAuthenticationToken – 然後通過標準的 AuthenticationManager 手動進行流程:
public void authWithAuthManager(HttpServletRequest request, String username, String password) {
UsernamePasswordAuthenticationToken authToken = new UsernamePasswordAuthenticationToken(username, password);
authToken.setDetails(new WebAuthenticationDetails(request));
Authentication authentication = authenticationManager.authenticate(authToken);
SecurityContextHolder.getContext().setAuthentication(authentication);
}
請注意,我們創建了令牌請求,將其傳遞到標準的身份驗證流程中,然後明確地將結果設置在當前安全上下文中。
4. 複雜註冊
在某些更復雜的場景中,註冊過程包含多個階段,例如——用户可以登錄系統之前,需要進行確認步驟。
在這種情況下,重要的是要理解我們可以在哪裏自動驗證用户。因為在用户註冊後立即進行自動驗證是不可能的,因為此時新創建的賬户仍然被禁用。
簡單來説——我們必須在用户確認賬户後執行自動驗證。
此外,請記住,此時我們不再擁有用户的實際、原始憑據。我們只擁有用户編碼後的密碼——這是我們將在這裏使用的:
public void authWithoutPassword(User user){
List<Privilege> privileges = user.getRoles().stream().map(Role::getPrivileges)
.flatMap(Collection::stream).distinct().collect(Collectors.toList());
List<GrantedAuthority> authorities = privileges.stream()
.map(p -> new SimpleGrantedAuthority(p.getName()))
.collect(Collectors.toList());
Authentication authentication = new UsernamePasswordAuthenticationToken(user, null, authorities);
SecurityContextHolder.getContext().setAuthentication(authentication);
}
請注意,我們在這裏正確設置了認證權限,就像通常在 AuthenticationProvider 中所做的那樣。
5. 結論
我們討論了在註冊流程後自動驗證用户的方法。