60-Shiro功能扩展(记住我)

Shiro扩展功能应用

Shiro缓存配置

​ 当我们进行授权操作时,每次都会从数据库查询用户权限信息,为了提高授权性能,可以将用户权限信息查询出来以后进行缓存,下次授权时从缓存取数据即可。

Shiro中内置缓存应用实现

第一步:在SpringShiroConfig中配置缓存Bean对象(Shiro框架提供)

/**
	 * 配置shiro框架的缓存管理器对象(这个对象不是缓存对象,是管理缓存的一个对象)
	   基于此配置可以在Shiro框架内部初始化一个Cache对象,此Cache对象可以存储用户的权限
	   信息,当用户访问一个授权才可以访问的方法时,我们需要从数据库获取用户权限信息,
	   然后还可以将用户的这个权限信息缓存起来,下次需要时从缓存获取即可。
	 * @return
	 */
@Bean
public CacheManager shiroCacheManager() {
    return new MemoryConstrainedCacheManager();
}

说明:这个CacheManager对象的名字不能写cacheManager,因为spring容器中已经存在一个名字为cacheManager的对象了.

第二步:修改securityManager的配置,将缓存对象注入给SecurityManager对象。

@Bean
public SecurityManager securityManager(
    Realm realm,
    CacheManager cacheManager) {
    DefaultWebSecurityManager sManager=
        new DefaultWebSecurityManager();
    sManager.setRealm(realm);
    sManager.setCacheManager(cacheManager);
    return sManager;
}

Shiro记住我

客户端业务实现

在login.html页面上获取记住我这个值

function doLogin(){
    var params={
        username:$("#usernameId").val(),
        password:$("#passwordId").val(),
        isRememberMe:$("#rememberId").prop("checked"),
    }
    var url="user/doLogin";
    console.log("params",params);
    $.post(url,params,function(result){
        if(result.state==1){
            //跳转到indexUI对应的页面
            location.href="doIndexUI?t="+Math.random();
        }else{
            $(".login-box-msg").html(result.message); 
        }
        return false;//防止刷新时重复提交
    });
}

服务端业务实现

第一步:在SysUserController中的doLogin方法中基于是否选中记住我,设置token的setRememberMe方法。

//登录login
@RequestMapping("doLogin")
public JsonResult doLogin(String username,String password,boolean isRememberMe) {

    //将用户提交的信息交给securityManager进行认证
    Subject subject = SecurityUtils.getSubject();
    //封装用户名和密码的令牌,通过构造方法
    UsernamePasswordToken token = new UsernamePasswordToken(username, password);
    //判断是否选中了记住我
    if (isRememberMe) {
        token.setRememberMe(isRememberMe);
    }
    subject.login(token);//提交给securityManager
    return new JsonResult("login ok");
}

第二步:在SpringShiroConfig配置类中添加记住我配置

/**
	 * 配置记住我管理器对象,此对象可以通过cookie对象存储账户信息,并将此信息
	 * 写到客户端,下次客户端可以访问服务端时,可以携带cookie中的信息进行自动
	 * 认证。
	 */
@Bean
public RememberMeManager rememberMeManager() {
    CookieRememberMeManager cManager=new CookieRememberMeManager();
    SimpleCookie cookie=new SimpleCookie("rememberMe");
    cookie.setMaxAge(7*24*60*60);
    cManager.setCookie(cookie);	
    //设置加密解密密钥(假如服务器重启以后,还是需要重新登陆,将下面的语句注释掉)
    //注意:
    //1)密钥的选择16位的一个字符串
    //2)密钥的复杂度越高,加密以后的内容就越安全。
    //cManager.setCipherKey(Base64.decode("6ZmI6I2j5Y+R5aSn5ZOlAA=="));
    //cManager.setCipherKey("abcd12345678qwer".getBytes());
    return cManager;
}

第三步:在SpringShiroConfig中修改securityManager的配置,为securityManager注入rememberManager对象。

@Bean
public SecurityManager securityManager(Realm realm,CacheManager cacheManager,RememberMeManager rememberManager) {
    DefaultWebSecurityManager sManager=
        new DefaultWebSecurityManager();
    sManager.setRealm(realm);
    sManager.setCacheManager(cacheManager);
    sManager.setRememberMeManager(rememberManager);
    return sManager;
}

**第四步:修改shiro的过滤认证级别,将 **/**=authc改为/**=user

map.put("/**", "user");//authc
		//user表示可以通过用户端提交的cookie信息进行认证

Shiro会话时长配置

​ 使用shiro框架实现认证操作,用户登录成功会将用户信息写入到会话对象中,其默认时长为30分钟,假如需要对此进行配置,可参考如下配置:

第一步:在SpringShiroConfig类中,添加会话管理器配置。

/**
 *  配置会话管理对象(Session管理器),在Shiro框架的应用中,用户登陆成功以后
 默认会将用户信息存储到session(服务端的一个对象)。
 */
@Bean
public SessionManager sessionManager() {
    DefaultWebSessionManager sessionManager=new DefaultWebSessionManager();
    //设置session生命周期(默认为30分钟)
    sessionManager.setGlobalSessionTimeout(60*60*1000);
    return sessionManager;
}

第二步:在SpringShiroConfig配置类中,对安全管理器 securityManager 增加 sessionManager值的注入

/**
     * SecurityManager 对象shiro框架的核心。
     * @Bean 通常会配置@Configuration注解进行使用,其它特点:
     * 1)此注解描述方法会交给spring管理
     * 2)@Bean注解没有指定其value属性的值,则bean的名字默认为方法名
     * @return
     */
//@Bean(value="sManager")
@Bean
public SecurityManager securityManager(Realm realm,
                                       CacheManager cacheManager,
                                       RememberMeManager rememberManager,
                                       SessionManager sessionManager) {
    DefaultWebSecurityManager sManager=new DefaultWebSecurityManager();
    sManager.setRealm(realm);
    sManager.setCacheManager(cacheManager);
    sManager.setRememberMeManager(rememberManager);
    sManager.setSessionManager(sessionManager);
    return sManager;
}

实例操作:实现用户登录后显示当前用户

第一步:定义一个工具类(ShiroUtils),获取用户登陆信息.

package com.cy.pj.common.util;
public class ShiroUtils {

	public static String getUsername() {
		return getUser().getUsername();
	}
	/**
	 * 获取登陆用户信息
	 * @return
	 */
	public static SysUser getUser() {
		//从session中获取登录用户
		return (SysUser)SecurityUtils.getSubject().getPrincipal();
	}
}


第二步:修改PageController中的doIndexUI方法

@RequestMapping("doIndexUI")
public String doIndexUI(Model model) {
    SysUser user = ShiroUtils.getUser();
    String username = user.getUsername();
    model.addAttribute("username", username);
    return "starter";
}

第三步:借助thymeleaf中的表达式直接在页面上(starter.html)获取登陆用户信息

 <span class="hidden-xs" id="loginUserId">[[${username}]]</span>

posted on 2020-07-27 23:25  liqiangbk  阅读(360)  评论(0编辑  收藏  举报

导航