shiroWeb项目-登陆与退出实现(九)
原理
使用FormAuthenticationFilter过虑器实现 ,原理如下:
将用户没有认证时,请求loginurl进行认证,用户身份和用户密码提交数据到loginurl
FormAuthenticationFilter拦截住取出request中的username和password(两个参数名称是可以配置的)
FormAuthenticationFilter调用realm传入一个token(username和password)
realm认证时根据username查询用户信息(在Activeuser中存储,包括 userid、usercode、username、menus)。
如果查询不到,realm返回null,FormAuthenticationFilter向request域中填充一个参数(记录了异常信息)
登陆页面
由于FormAuthenticationFilter的用户身份和密码的input的默认值(username和password),修改页面的账号和密码 的input的名称为username和password
代码控制:(只对错误进行控制,认证过程由realm传递给Authenticator认证信息)
package cn.qlq.springmvc.controller; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpSession; import org.apache.shiro.authc.IncorrectCredentialsException; import org.apache.shiro.authc.UnknownAccountException; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Controller; import org.springframework.web.bind.annotation.RequestMapping; import cn.qlq.springmvc.Exception.MyException; import cn.qlq.springmvc.pojo.ActiveUser; import cn.qlq.springmvc.service.SysService; @Controller public class LoginController { @Autowired private SysService sysService; // 登陆提交地址,和applicationContext-shiro.xml中配置的loginurl一致 @RequestMapping("/login.action") public String login(HttpServletRequest request) throws Exception { // 如果登陆失败从request中获取认证异常信息,shiroLoginFailure就是shiro异常类的全限定名 String exceptionClassName = (String) request.getAttribute("shiroLoginFailure"); // 根据shiro返回的异常类路径判断,抛出指定异常信息 if (exceptionClassName != null) { if (UnknownAccountException.class.getName().equals(exceptionClassName)) { // 最终会抛给异常处理器 throw new MyException("账号不存在"); } else if (IncorrectCredentialsException.class.getName().equals(exceptionClassName)) { throw new MyException("用户名/密码错误"); } else if ("randomCodeError".equals(exceptionClassName)) { throw new MyException("验证码错误 "); } else { throw new Exception("不是账户错误,也不是密码错误");// 最终在异常处理器生成未知错误 } } // 此方法不处理登陆成功(认证成功),shiro认证成功会自动跳转到上一个请求路径 // 登陆失败还到login页面 return "login"; } }
认证过滤拦截器
--------------------------------------------退出-------------------------------
使用LogoutFilter
不用我们去实现退出,只要去访问一个退出的url(该 url是可以不存在),由LogoutFilter拦截住,清除session。
在applicationContext-shiro.xml配置LogoutFilter:
页面中:
【当你用心写完每一篇博客之后,你会发现它比你用代码实现功能更有成就感!】