文档章节

shiro web 登陆流程

4rnold
 4rnold
发布于 2017/09/04 16:03
字数 486
阅读 18
收藏 0

web.xml 注册filter

<!-- shiro 安全过滤器 -->
<filter>
  <filter-name>shiroFilter</filter-name>
  <filter-class>org.springframework.web.filter.DelegatingFilterProxy</filter-class>
  <async-supported>true</async-supported>
  <init-param>
    <param-name>targetFilterLifecycle</param-name>
    <param-value>true</param-value>
  </init-param>
</filter>

此处只是配置一个shiroFilterFactory,真正的filter在spring中配置

ps:这样配置将原本需要配置在web.xml中的filter配置在了spring.xml中

spring-config-shiro.xml

<!-- Shiro的Web过滤器 -->
<bean id="shiroFilter" class="org.apache.shiro.spring.web.ShiroFilterFactoryBean">
  <property name="securityManager" ref="securityManager"/>
  <property name="loginUrl" value="/login"/>
  <property name="filters">
    <util:map>
      <!--shiroFilter-->
      <entry key="authc" value-ref="formAuthenticationFilter"/>
      <entry key="sysUser" value-ref="sysUserFilter"/>
    </util:map>
  </property>
  <property name="filterChainDefinitions">
    <value>
      /login = authc
      /logout = logout
      /authenticated = authc
      /** = user,sysUser
    </value>
  </property>
</bean>

其中配置了formAuthenticationFilter

public class FormAuthenticationFilter extends AuthenticatingFilter {}
//MyFormAuthenticationFilter.java
public class MyFormAuthenticationFilter extends FormAuthenticationFilter {
    @Override
    protected boolean onAccessDenied(ServletRequest request, ServletResponse response, Object mappedValue) throws Exception {
        if(request.getAttribute(getFailureKeyAttribute()) != null) {
            return true;
        }
        return super.onAccessDenied(request, response, mappedValue);
    }
}

如果之前的filter(验证码filter)错误了,不再继续执行 return true;

之前没错则执行onAccessDenied()。 ShiroFilterFactoryBean 具有拦截filter的能力,filters首先按web.xml配置的顺序执行,执行到ShiroFilterFactoryBean,注册shiro自己的filters,率先执行自己的filters,之后再接着执行web.xml中的filter

在FormAuthenticationFilter.onAccessDenied()

​ -> AuthenticatingFilter.executeLogin()执行登陆。

AuthenticatingFilter提供create(request,response)

AccessControlFilter提供getSubject(request,response)

​ -> (DelegatingSubject)subject.login(token)

​ -> DelegatingSubject#securityManager.login() 登陆后对subject中的属性做一些赋值

​ -> AuthenticatingSecurityManager#authenticator.authenticate()

​ -> ModularRealmAuthenticator#realms.getAuthenticationInfo()

最终落到realms上

<bean id="credentialsMatcher" class="com.github.zhangkaitao.shiro.chapter16.credentials.RetryLimitHashedCredentialsMatcher">
        <constructor-arg ref="cacheManager"/>
        <property name="hashAlgorithmName" value="md5"/>
        <property name="hashIterations" value="2"/>
        <property name="storedCredentialsHexEncoded" value="true"/>
    </bean>

    <!-- Realm实现 -->
    <bean id="userRealm" class="com.github.zhangkaitao.shiro.chapter16.realm.UserRealm">
        <property name="credentialsMatcher" ref="credentialsMatcher"/>
        <property name="cachingEnabled" value="false"/>
        <!--<property name="authenticationCachingEnabled" value="true"/>-->
        <!--<property name="authenticationCacheName" value="authenticationCache"/>-->
        <!--<property name="authorizationCachingEnabled" value="true"/>-->
        <!--<property name="authorizationCacheName" value="authorizationCache"/>-->
    </bean>

realm可以配置credentialsMatcher 在哪用?

//ModularRealmAuthenticator.java
protected AuthenticationInfo doMultiRealmAuthentication(Collection<Realm> realms, AuthenticationToken token) {

        //策略
        AuthenticationStrategy strategy = getAuthenticationStrategy();

        AuthenticationInfo aggregate = strategy.beforeAllAttempts(realms, token);

        if (log.isTraceEnabled()) {
            log.trace("Iterating through {} realms for PAM authentication", realms.size());
        }

        for (Realm realm : realms) {

            aggregate = strategy.beforeAttempt(realm, token, aggregate);

            if (realm.supports(token)) {

                log.trace("Attempting to authenticate token [{}] using realm [{}]", token, realm);

                AuthenticationInfo info = null;
                Throwable t = null;
                try {
                    info = realm.getAuthenticationInfo(token);  //试用CredentialsMatcher匹配 
                } catch (Throwable throwable) {
                    t = throwable;
                    if (log.isDebugEnabled()) {
                        String msg = "Realm [" + realm + "] threw an exception during a multi-realm authentication attempt:";
                        log.debug(msg, t);
                    }
                }

                aggregate = strategy.afterAttempt(realm, token, info, aggregate, t);

            } else {
                log.debug("Realm [{}] does not support token {}.  Skipping realm.", realm, token);
            }
        }

        aggregate = strategy.afterAllAttempts(token, aggregate);

        return aggregate;
    }

© 著作权归作者所有

共有 人打赏支持
4rnold
粉丝 1
博文 51
码字总数 26866
作品 0
深圳
程序员
私信 提问
从权限控制到shiro框架的应用

说明:本文很多观点和内容来自互联网以及各种资料,如果侵犯了您的权益,请及时联系我,我会删除相关内容。 权限管理 基本上涉及到用户参与的系统都要进行权限管理,权限管理属于系统安全的范...

神秘的寇先森
01/01
0
0
【shiro】入门程序

Apache Shiro是一个强大的且易用的java安全框架,执行身份验证、授权、密码学和会话管理。使用Shiro的易于理解的API,可以快速,轻松的获得任何应用程序,从最小的移动应用程序到最大的网络和...

binggetong
2017/12/19
0
0
【shiro】基于url的权限管理和shiro的对比

♦基于URL的权限管理 这种是企业中比较常用的,用的是web应用中filter来实现,用户请求URL,通过filter拦截,判断用户身份是否合法(用户认证),判断请求的地址是否是用户权限范围内的URL(...

binggetong
2017/12/20
0
0
zhaoml529/SpringMVC-Activiti5.16-Shiro

SpringOA简介 基于SpringMVC+Shiro+Activiti 5.16 的简单OA,可以快速入门Activiti学习用。 此版本前台使用的是EasyUI 框架简介 框架以Spring Framework为核心、Spring MVC作为模型视图控制器...

zhaoml529
2017/05/19
0
0
Shiro之身份认证、与spring集成(入门级)

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

左羽
05/03
0
0

没有更多内容

加载失败,请刷新页面

加载更多

寻找数学的广度——《这才是数学》读书笔记2700字

寻找数学的广度——《这才是数学》读书笔记2700字: 文|程哲。数学学习方式之广:国内外数学教育方面的专家,进行了很多种不同的数学学习方式尝试,如数学绘本、数学游戏、数学实验、数学步道...

原创小博客
15分钟前
3
0
vimrc

set rtp+=/usr/local/lib/python3.7/site-packages/powerline/bindings/vim/set laststatus=2set t_Co=256set cursorlinehi cursorline cterm=none term=nonehighlight CursorLine gui......

kut
17分钟前
1
0
ubuntu常用操作

显卡GPU 查看显卡信息sudo lshw -numeric -class video# 查看显卡型号lspci | grep -i nvidia# 查看驱动版本sudo dpkg --list | grep nvidia-*或者 ubuntu-drivers devices#查看显卡...

hc321
昨天
2
0
mysql密码重置

方法一: 在my.ini的[mysqld]字段加入: skip-grant-tables 重启mysql服务,这时的mysql不需要密码即可登录数据库 然后进入mysql mysql>use mysql; mysql>更新 update user set password=pas...

architect刘源源
昨天
7
1
SpringBoot + Mybatis 配置多数据源(Srping boot 二)

前置条件,你已经配置好spring boot+mybatis,可以参考之前的博客 实现逻辑通过注解+aop切面编程来动态更新datasource 第一步,配置多个DataSource server: port: 8080freezing: ...

小海bug
昨天
14
0

没有更多内容

加载失败,请刷新页面

加载更多

返回顶部
顶部