From 4ef2de7aa7fc24ee19020330e781bae0b51b956c Mon Sep 17 00:00:00 2001
From: 无关风月 <443237572@qq.com>
Date: 星期一, 30 十二月 2024 10:23:58 +0800
Subject: [PATCH] 小程序

---
 applet/src/main/java/com/jilongda/applet/security/AuthenticationProvider.java |   88 ++++++++++++++++++++++++++++++++++++++++++++
 1 files changed, 88 insertions(+), 0 deletions(-)

diff --git a/applet/src/main/java/com/jilongda/applet/security/AuthenticationProvider.java b/applet/src/main/java/com/jilongda/applet/security/AuthenticationProvider.java
new file mode 100644
index 0000000..d44a5cf
--- /dev/null
+++ b/applet/src/main/java/com/jilongda/applet/security/AuthenticationProvider.java
@@ -0,0 +1,88 @@
+package com.jilongda.applet.security;
+
+import lombok.extern.slf4j.Slf4j;
+import org.springframework.security.authentication.*;
+import org.springframework.security.authentication.dao.DaoAuthenticationProvider;
+import org.springframework.security.core.Authentication;
+import org.springframework.security.core.AuthenticationException;
+import org.springframework.security.core.userdetails.UserDetails;
+import org.springframework.security.core.userdetails.UsernameNotFoundException;
+import org.springframework.security.crypto.password.PasswordEncoder;
+
+import java.util.Objects;
+
+/**
+ * 身份验证提供者--->登录验证逻辑
+ * <p>
+ * 不管是 implements AuthenticationProvider  还是 extends DaoAuthenticationProvider 区别不大
+ * <p>
+ * DaoAuthenticationProvider 实现了 AuthenticationProvider 类
+ * <p>
+ * 验证逻辑都是在 public Authentication authenticate(Authentication authentication) throws AuthenticationException {} 方法中
+ *
+ * @author xiaochen
+ * @date 2021-01-02 20:17
+ */
+@Slf4j
+public class AuthenticationProvider extends DaoAuthenticationProvider {
+
+    private SysUserDetailsService loadUserDetailsService;
+    private PasswordEncoder passwordEncoder;
+
+    public AuthenticationProvider(SysUserDetailsService loadUserDetailsService, PasswordEncoder passwordEncoder) {
+        this.loadUserDetailsService = loadUserDetailsService;
+        this.passwordEncoder = passwordEncoder;
+        setUserDetailsService(loadUserDetailsService);
+        setPasswordEncoder(passwordEncoder);
+    }
+
+    @Override
+    public Authentication authenticate(Authentication authentication) {
+        // 可以在此处覆写整个登录认证逻辑
+        // [1] 获取 username 和 password
+        String userName = (String) authentication.getPrincipal();
+        String password = (String) authentication.getCredentials();
+        log.info("用户数据查询======================================");
+        // [2] 使用用户名从数据库读取用户信息
+        SecurityUserDetails userDetails = this.loadUserDetailsService.loadUserByUsername(userName);
+        log.info("用户数据查询======================================:{}", userDetails);
+        // 判断是否被封禁
+//        userDetails.setEnabled(userDetails.getState());
+        // [3] 检查用户信息
+        if (Objects.isNull(userDetails)) {
+            throw new UsernameNotFoundException("用户账户不存在");
+//        } else if (userDetails.isEnabled() || userDetails.getState()) {
+//            throw new DisabledException(userName + " 用户已被禁用或删除,请联系管理员");
+        } else if (!userDetails.isAccountNonExpired()) {
+            throw new AccountExpiredException(userName + " 账号已过期");
+        } else if (!userDetails.isAccountNonLocked()) {
+            throw new LockedException(userName + " 账号已被锁定");
+        } else if (!userDetails.isCredentialsNonExpired()) {
+            throw new LockedException(userName + " 凭证已过期");
+        }
+        // [4] 数据库用户的密码,一般都是加密过的
+        String encryptedPassword = userDetails.getPassword();
+
+        // 根据加密算法加密用户输入的密码,然后和数据库中保存的密码进行比较
+        if (!this.passwordEncoder.matches(password, encryptedPassword)) {
+            throw new BadCredentialsException("密码错误");
+        }
+        // [5] 成功登陆,把用户信息提交给 Spring Security
+        // 把 userDetails 作为 principal 的好处是可以放自定义的 UserDetails,这样可以存储更多有用的信息,而不只是 username,
+        // 默认只有 username,这里的密码使用数据库中保存的密码,而不是用户输入的明文密码,否则就暴露了密码的明文
+        // 不暴露密码
+//        userDetails.setPassword(null);
+        UsernamePasswordAuthenticationToken usernamePasswordAuthenticationToken = new UsernamePasswordAuthenticationToken(userDetails.getUsername(), null, null);
+        // 设置详情
+        //String userInfo = JsonUtils.toJsonString(userDetails);
+        usernamePasswordAuthenticationToken.setDetails(userDetails);
+        return usernamePasswordAuthenticationToken;
+    }
+
+    @Override
+    protected void additionalAuthenticationChecks(UserDetails userDetails, UsernamePasswordAuthenticationToken authentication)
+            throws AuthenticationException {
+        // 可以在此处覆写密码验证逻辑
+        super.additionalAuthenticationChecks(userDetails, authentication);
+    }
+}

--
Gitblit v1.7.1