ShiroConfig.java
@Configuration
public class ShiroConfig {
//注入自定义的realm,告诉shiro如何获取用户信息来做登录或权限控制
@Bean
public Realm realm() {
return new MyRealm();
}
public SimpleCookie rememberMeCookie() {
// 设置cookie名称,对应login.html页面的<input type="checkbox" name="rememberMe"/>
SimpleCookie cookie = new SimpleCookie("rememberMe");
// 设置cookie的过期时间,单位为秒,这里为一天
cookie.setMaxAge(86400);
return cookie;
}
/**
* cookie管理对象
* @return
*/
public CookieRememberMeManager rememberMeManager() {
CookieRememberMeManager cookieRememberMeManager = new CookieRememberMeManager();
cookieRememberMeManager.setCookie(rememberMeCookie());
// rememberMe cookie加密的密钥
cookieRememberMeManager.setCipherKey(Base64.decode("4AvVhmFLUs0KTA3Kprsdag=="));
return cookieRememberMeManager;
}
@Bean
public SessionsSecurityManager securityManager(){
DefaultWebSecurityManager securityManager = new DefaultWebSecurityManager();
//将自定义的realm交给SecurityManager管理
securityManager.setRealm(realm());
// 使用记住我
securityManager.setRememberMeManager(rememberMeManager());
return securityManager;
}
@Bean
public static DefaultAdvisorAutoProxyCreator getDefaultAdvisorAutoProxyCreator() {
DefaultAdvisorAutoProxyCreator creator = new DefaultAdvisorAutoProxyCreator();
/**
* setUsePrefix(false)用于解决一个奇怪的bug。在引入spring aop的情况下。
* 在@Controller注解的类的方法中加入@RequiresRole注解,会导致该方法无法映射请求,导致返回404。
* 加入这项配置能解决这个bug
*/
creator.setUsePrefix(true);
return creator;
}
/**
* 这里统一做鉴权,即判断哪些请求路径需要用户登录,哪些请求路径不需要用户登录。
* 这里只做鉴权,不做权限控制,因为权限用注解来做。
* @return
*/
@Bean
public ShiroFilterChainDefinition shiroFilterChainDefinition() {
DefaultShiroFilterChainDefinition chain = new DefaultShiroFilterChainDefinition();
//哪些请求可以匿名访问
chain.addPathDefinition("/login", "anon");
chain.addPathDefinition("/userLogin", "anon");
chain.addPathDefinition("/static/**", "anon");
//除了以上的请求外,其它请求都需要登录
chain.addPathDefinition("/**", "user");
return chain;
}
}
Controller
@RequestMapping("userLogin")
@ResponseBody
public Result userLogin(@RequestParam("username") String username, @RequestParam("password") String password, @RequestParam(value = "rememberme",required = false) String rememberme,HttpSession session){
Subject currentUser = SecurityUtils.getSubject();
try {
String depassword = null;//解密密码
try {
depassword = AesUtil.aesDecrypt(password); //解密web传值的密码
} catch (Exception e) {
e.printStackTrace();
}
UsernamePasswordToken token = new UsernamePasswordToken(username, depassword);
rememberme = rememberme == null ? "false" : rememberme; //null=>false
token.setRememberMe(Boolean.parseBoolean(rememberme));
//登录
currentUser.login(token);
//从session取出用户信息
User user = (User) currentUser.getPrincipal();
session.setAttribute("user",user);
if (user==null) throw new AuthenticationException();
//返回登录用户的信息给前台,含用户的所有角色和权限
return ResultGenerator.genSuccessResult();
} catch ( UnknownAccountException uae ) {
return ResultGenerator.genFailResult("登录失败,用户或密码错误!");
} catch ( IncorrectCredentialsException ice ) {
return ResultGenerator.genFailResult("登录失败,用户或密码错误!");
} catch ( AuthenticationException ae ) {
return ResultGenerator.genServiceErrorResult();
}
}
注意,User类需要实现
Serializable
增加属性
private static final long serialVersionUID = 1L;