Spring 整合Shiro:記住我
阿新 • • 發佈:2018-12-26
有限公司 remember post 是否 RKE term set lock dag
1、登錄方法
/** * 執行登錄操作 * * @param username * @param password * @param rememberMe * @param model * @return */ @Log("登錄") @RequestMapping("/login") String login(String username, String password, Boolean rememberMe, Model model) {//判斷用戶名和密碼為空 if (StringUtils.isEmpty(username) || StringUtils.isEmpty(password)) { model.addAttribute("msg", "用戶名和密碼不能為空!"); return "login.html"; } // shiro登錄步驟 // 1、獲取subject對象 Subject subject = SecurityUtils.getSubject();// 2、封裝對象 UsernamePasswordToken token = new UsernamePasswordToken(username, password); System.out.println(token.toString()); // 3、執行登錄(失敗會報異常,需捕獲異常) // 實際開發中,用戶名和密碼錯誤,不給出明確提示 try { // 設置是否記住我 rememberMe = rememberMe == null ? false : rememberMe;// 設置記住我 token.setRememberMe(rememberMe);
// 登錄 subject.login(token); // 這樣url會改變為index_v1,不然還會是login return "redirect:/index_v1"; } catch (UnknownAccountException e) {//賬號不存在 model.addAttribute("msg", "用戶名不存在!"); return "/login"; } catch (LockedAccountException e) {//賬戶鎖定 model.addAttribute("msg", "賬戶被鎖定!"); return "/login"; } catch (IncorrectCredentialsException e) {//密碼錯誤 model.addAttribute("msg", "密碼錯誤!"); return "/login"; } }
2、ShiroConfig
/** * Copyright (C), 2018-2018, 謫仙科技有限公司 * FileName ShiroConfig * Author wangzhiguo * Date 2018-12-25 2:49 * Description Shiro配置 * History * <author> <time> <version> <desc> * wangzhiguo 2018-12-25 版本號 描述 */ package com.itgeek.config.shiro.config; import com.itgeek.config.shiro.realm.Myrealm; import org.apache.shiro.codec.Base64; import org.apache.shiro.session.mgt.SessionManager; import org.apache.shiro.spring.web.ShiroFilterFactoryBean; import org.apache.shiro.web.mgt.CookieRememberMeManager; import org.apache.shiro.web.mgt.DefaultWebSecurityManager; import org.apache.shiro.web.servlet.SimpleCookie; import org.apache.shiro.web.session.mgt.DefaultWebSessionManager; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import java.util.LinkedHashMap; import java.util.Map; /** * 〈功能描述〉 * Shiro配置 * <p> * <p> * 系統啟動,執行順序 * realm -- > securityManager -- > filter * * @author wangzhiguo * @date 2018-12-25 * @since 1.0.0 */ @Configuration public class ShiroConfig { /** * shiro核心filter * * @return */ @Bean() public ShiroFilterFactoryBean getShiroFilterFactoryBean() { System.out.println("Shiro過濾器"); ShiroFilterFactoryBean shiroFilterFactoryBean = new ShiroFilterFactoryBean(); // 設置SecurityManager(必須) shiroFilterFactoryBean.setSecurityManager(securityManager()); /** * shiro常用過濾器 * anon:無需認證 * authc:必須認證 * user:如果使用rememberMe功能可以直接訪問 * perms:必須得到資源權限可以訪問 * role:必須得到角色權限可以訪問 */ // LinkedHashMap 可以保持順序 Map<String, String> filterMap = new LinkedHashMap<>(); // 1、認證 filterMap.put("/", "anon"); filterMap.put("/index", "anon"); filterMap.put("/toLogin", "anon"); filterMap.put("/login", "anon"); // 2、資源權限 filterMap.put("/sys/add", "perms[user:edit]"); // 3、角色權限 // 所有請求都要認證 // filterMap.put("/**", "authc"); // 認證或記住我都可以登錄 filterMap.put("/**", "user"); // 未授權 shiroFilterFactoryBean.setUnauthorizedUrl("/noAuth"); // 設置跳轉的登錄頁 shiroFilterFactoryBean.setLoginUrl("/toLogin"); // 設置登錄成功的頁面 shiroFilterFactoryBean.setSuccessUrl("/index_v1"); shiroFilterFactoryBean.setFilterChainDefinitionMap(filterMap); return shiroFilterFactoryBean; } /** * 安全管理器 * 緩存註入在這 * * @return */ @Bean() public DefaultWebSecurityManager securityManager() { System.out.println("Shiro安全管理器"); DefaultWebSecurityManager securityManager = new DefaultWebSecurityManager(); // 設置realm securityManager.setRealm(myrealm()); // session會話 // securityManager.setSessionManager(sessionManager()); // 設置記住我 securityManager.setRememberMeManager(rememberMeManager()); return securityManager; } /** * realm:自定義的認證和授權邏輯 * * @return */ @Bean() public Myrealm myrealm() { System.out.println("自定義Realm"); return new Myrealm(); } /** * 記住我 * * @return */ @Bean public CookieRememberMeManager rememberMeManager() { System.out.println("記住我:rememberMe"); CookieRememberMeManager cookieRememberMeManager = new CookieRememberMeManager(); cookieRememberMeManager.setCookie(rememberMeCookie()); //這個地方有點坑,不是所有的base64編碼都可以用,長度過大過小都不行,沒搞明白,官網給出的要麽0x開頭十六進制,要麽base64 cookieRememberMeManager.setCipherKey(Base64.decode("4AvVhmFLUs0KTA3Kprsdag==")); return cookieRememberMeManager; } /** * Cookie管理 * 創建記住我cookie * * @return */ @Bean public SimpleCookie rememberMeCookie() { System.out.println("rememberMeCookie"); SimpleCookie cookie = new SimpleCookie("rememberMe"); cookie.setHttpOnly(true); // 聲明周期 cookie.setMaxAge(1 * 60 * 60); return cookie; } }
3、登錄頁面
<form action="/login" method="post"> <span style="color: red" th:text="${msg}"></span> <br> 姓名<input type="text" name="username"> <br> 密碼<input type="password" name="password"> <br> 記住我<input type="checkbox" checked="checked" name="rememberMe"> <br> <button type="submit">登錄</button> </form>
4、登錄(記住我),會生成rememberMe CookIe
不記住我:rememberMe Cookie 不會生成
註銷(SHiro:/logout)也會清除rememberMe Cookie
Spring 整合Shiro:記住我