认证思路

  1. 调用 SecurityUtils.getSubject() 方法,获取当前的 Subject 对象 ;

  2. 调用 Subject.isAuthenticated() 测试当前的用户,即 Subject 是否以及被认证,即是否登录 ;

  3. 如果没有被认证,则进行认证操作;

  4. 将用户名和密码封装成 UsernamePasswordToken 对象;

  5. 自定义 Realm 的方法,从数据库获取对应的记录,返回给 shiro

    如果是仅仅完成登录,则继承 AuthenticatingRealm 类,实现 doGetAuthenticationInfo(AuthenticationToken) 方法 ;

  6. 调用 Subject.login(AuthenticationToken) 方法,执行登录 ;

  7. shiro 完成密码的比对 。


自定义用于登录检验的Realm的思路

在认证的时候, Subject.login(AuthenticationToken) 方法,传进去的参数,最终被传到了 AuthenticatingRealm 的自定义子类中,用于认证的方法中;

  1. 将方法中token参数,强转为 UsernamePasswordToken 对象;

  2. UsernamePasswordToken 中获取 用户名 ;

  3. 调用数据库方法,获取此用户名对用的记录;

  4. 如若此用户不存在,则抛出 UnknownAccountException 异常;

  5. 用户存在的情况下,根据实际情况看是否需要抛出其他 AuthenticationException 异常,比如:用户被锁定异常

  6. 根据用户情况,构建 AuthenticationInfo 对象返回,最常用的是实现类是:SimpleAuthenticationInfo

    如果不需要进行盐值加密,则调用有三个参数的构造器;

    1. principal : 认证的实体信息,也就上面我们是使用什么信息进行认证,比如这里就是使用 用户名 ;
    2. credentials:数据库中保存的密码;
    3. realmName:当前 realm 的名字,调用父类的 getName() 方法即可 ;

代码实现

控制器代码:

 @RequestMapping(value = "/isAllowLogin", method = {RequestMethod.POST})
@ResponseBody
public String isAllowLogin(@RequestParam("username") String username, @RequestParam("password") String password) throws IOException {
JSONObject jsonObject = new JSONObject();
Subject subject = SecurityUtils.getSubject();
if (!subject.isAuthenticated()) {
UsernamePasswordToken token = new UsernamePasswordToken(username, password);
try {
subject.login(token);
} catch (AuthenticationException e) {
jsonObject.put("result", "0");
return jsonObject.toJSONString();
}
} jsonObject.put("result", "1");
return jsonObject.toJSONString();
}

自定义Realm代码:

@Service
public class ShiroRealm extends AuthenticatingRealm { @Autowired
private UserMapper userMapper; @Override
protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken authenticationToken) throws AuthenticationException {
UsernamePasswordToken token = (UsernamePasswordToken) authenticationToken;
String username = token.getUsername(); User user = userMapper.findUserByName(username);
if (null == user) {
throw new UnknownAccountException("用户名或密码错误");
}
String password = user.getUserPass();
AuthenticationInfo info = new SimpleAuthenticationInfo(username, password, getName()); return info;
}
}

后记

shiro 的校验通过以后,同一个 session 对应的浏览器再次输入 任意登录信息 都会校验通过,这是 shiro 拿缓存了,没有走 realm 校验 ;

要想登出,可以使用在受保护页面那里配置一个 logout 进行登出操作;

   <property name="filterChainDefinitions">
<value>
/logout.action = logout
...
....
...
</value>
</property>

这里注意,前面的路径随便写,无论其存在不存在,只要后面写成 logout 就行, shiro 就会执行登出操作;其原理应该是销毁了对应的 session

(三)shiro的认证的更多相关文章

  1. Apache shiro集群实现 (三)shiro身份认证(Shiro Authentication)

    Apache shiro集群实现 (一) shiro入门介绍 Apache shiro集群实现 (二) shiro 的INI配置 Apache shiro集群实现 (三)shiro身份认证(Shiro ...

  2. Shiro入门之一 -------- Shiro权限认证与授权

    一  将Shirojar包导入web项目 二 在web.xml中配置shiro代理过滤器 注意: 该过滤器需要配置在struts2过滤器之前 <!-- 配置Shiro的代理过滤器 -->  ...

  3. spring boot(十四)shiro登录认证与权限管理

    这篇文章我们来学习如何使用Spring Boot集成Apache Shiro.安全应该是互联网公司的一道生命线,几乎任何的公司都会涉及到这方面的需求.在Java领域一般有Spring Security ...

  4. springboot+mybatis+shiro——登录认证和权限控制

    转载:https://z77z.oschina.io/ 一.引入依赖 shiro-all包含shiro所有的包.shiro-core是核心包.shiro-web是与web整合.shiro-spring ...

  5. Shiro 登录认证源码详解

    Shiro 登录认证源码详解 Apache Shiro 是一个强大且灵活的 Java 开源安全框架,拥有登录认证.授权管理.企业级会话管理和加密等功能,相比 Spring Security 来说要更加 ...

  6. Shiro身份认证---转

    目录 1. Shro的概念 2. Shiro的简单身份认证实现 3. Shiro与spring对身份认证的实现 前言: Shiro 可以非常容易的开发出足够好的应用,其不仅可以用在 JavaSE 环境 ...

  7. Shiro身份认证、盐加密

    目的: Shiro认证 盐加密工具类 Shiro认证 1.导入pom依赖 <dependency> <groupId>org.apache.shiro</groupId& ...

  8. SpringBoot整合Shiro完成认证

    三.SpringBoot整合Shiro思路 首先从客户端发来的所有请求都经过Shiro过滤器,如果用户没有认证的都打回去进行认证,认证成功的,再判断是否具有访问某类资源(公有资源,私有资源)的权限,如 ...

  9. 射频识别技术漫谈(12)——三次相互认证【worldsing笔记】

    射频识别系统中由于卡片和读写器并不是固定连接为一个不可分割的整体,二者在进行数据通讯前如何确信对方的合法身份就变得非常重要.根据安全级别的要求不同,有的系统不需认证对方的身份,例如大多数的TTF模式的 ...

  10. 阿里云API网关(11)API的三种安全认证方式

    网关指南: https://help.aliyun.com/document_detail/29487.html?spm=5176.doc48835.6.550.23Oqbl 网关控制台: https ...

随机推荐

  1. Python自动生成代码工具

    项目中有一个需求,对一个基类而言,拥有一个比较方法和拷贝方法,某些地方需要频繁地对这两个方法进行调用.对于所有子类而言,需要重写这两个方法,并在其中维护类内一些成员变量.例如有一个变量m_iMyVal ...

  2. Android中活动被回收了怎么办

    当一个活动进入到了停止状态,是有可能被系统回收的.按下返回键的时候,活动被重新创建一次,但是里面的数据就没办法重现: 这时Activity中提供了一个onSaveInstanceState()回调方法 ...

  3. mint-ui 做省市选择组件

    省市的数据是动态的,其实不是动态的更好搞 <!-- 省市选择 --> <mt-popup v-model="popupVisible" position=&quo ...

  4. docker技术入门(1)

    1Docker技术介绍 DOCKER是一个基于LXC技术之上构建的container容器引擎,通过内核虚拟化技术(namespace及cgroups)来提供容器的资源隔离与安全保障,KVM是通过硬件实 ...

  5. Unity火爆插件Behavior Designer行为树插件学习

    如果要让游戏里的角色或者NPC能执行预设的AI逻辑,最简单的用IF..ELSE...神器既可以实现, 但是再复杂的一般用经典的状态机来切换状态,但是写起来比较麻烦.相对的,行为树(Behavior T ...

  6. css3的选择器有哪几种?

    *通用选择器,ID选择器 ,.类选择器class,标签选择器,标签组合选择器,伪类选择器:,+相邻元素选择器,>子元素选择器,~同辈选择器,x[title]属性选择器[type="bu ...

  7. 自定义alert弹框,title不显示域名(重写alert)

    问题: 系统默认的alert弹框的title会默认显示网页域名 解决办法: (修改弹框样式) (function() { window.alert = function(name) { $(" ...

  8. [Java.File]如果写 File filesFolder = new File("/") ,在windows系统中,filesFolder 会去找哪个盘符? 答案:程序运行路径的根盘符.

    首先这段代码在Unix/Linux系统上会去找根路径,但在Windows系统上会去找C:盘还是D:盘还是其它盘呢? 其实它会去找user.dir所在盘符的根目录,user.dir即用户的当前工作目录, ...

  9. solidity语言介绍以及开发环境准备

    solidity语言介绍以及开发环境准备   Solidity 是一门面向合约的.为实现智能合约而创建的高级编程语言.这门语言受到了 C++,Python 和 Javascript 语言的影响,设计的 ...

  10. typescript类 继承 修饰符

    //1.ts中类的定义 /* es5: function Person(name){ this.name=name; this.run=function(){ console.log(this.nam ...