Shiro记住我无效,被拦截;

1 篇文章 0 订阅

Shiro记住我无效,被拦截

场景描述:

       Shiro的记住我功能就是登录的时候,选择了记住当前用户的选项来登录,关闭浏览器之后,在登录信息存活期间再次访问项目里的某个页面可以直接访问。可以在程序中对某些敏感操作进行判断是否为通过记住我登录的用户,从而进行其他一系列限制操作。

       在按照网上的配置配置完之后,发现记住我之后再次访问其他功能时,会被拦截,并且不会通过项目中debug打了断点的部分,直接被跳转到未登录处理的登录页面,而且我查了很多很多的相关配置文档,都试了就是实现不了。事实上是取到了cookie中保存的信息,被拦截后的页面地址栏如下:

http://localhost:xxxx/xxxx/login.do;jsessionid=4D328B61960C713B2F563385F85EC43C

原因:

        通过询问其他朋友,发现是因为实体类没有序列化,Shiro是将实体对象序列化保存到本地cookie中,但是很多文档都没有提及这一点,或许是自己没有这个意识。

解决办法:

       更改之前:

public class User  {
...
}

        更改之后:

public class User implements Serializable {
...
}

     再次测试的时候,发现通过debug就会走项目中的打了断点的地方。

设置自定义拦截器将本地用户放入到session中

参考文章地址:https://blog.csdn.net/u011277123/article/details/70214599

场景描述:

       其他所有的controller中涉及到用户的都是从session中获取,但是通过记住我登录的用户的用户信息是放在本地的cookie中,然后shiro获取后是将其放入的subject中,通过subject可以获取记住我用户的信息,但是我的jsp页面中通过el标签获取了用户对象并展示在前台页面,所以干脆我就做了一个自定义过滤器,所有访问都需要走一遍这个过滤器,如果是通过记住我登录的,就把本地获取的用户对象放入到session中,配置如下:

java类:

public class MyRememberFilter extends FormAuthenticationFilter {
    @Override
    protected boolean isAccessAllowed(ServletRequest request, ServletResponse response, Object mappedValue) {
        Subject subject=getSubject(request,response);
        // 如果是记住我登录的,则需要处理一下
        // isRemembered为true、isAuthenticated为false
        if(!subject.isAuthenticated() && subject.isRemembered()){
            // 通过记住我第一次进程序,并且保存的principal中有内容,添加用户到session
            if(subject.getSession().getAttribute("user")==null && subject.getPrincipal() != null){
                subject.getSession().setAttribute("user",subject.getPrincipal());
            }
        }
        return subject.isAuthenticated() || subject.isRemembered();
    }
}

 

applicationContext.xml中的bean引入shiro过滤器配置:

	<!--自定义全局过滤器-->
	<bean id="MyRememberFilter" class="com.xxx.xxx.shrio.MyRememberFilter"></bean>	
    ...
    <!-- web.xml中shiro的filter对应的bean -->
	<bean id="shiroFilter" class="org.apache.shiro.spring.web.ShiroFilterFactoryBean">
        ...
		<!--在shiro中使用自定义过滤器-->
		<property name="filters">
			<util:map>
				<entry key="MyRemember" value-ref="MyRememberFilter"></entry>
			</util:map>
		</property>
		<!-- 指定过滤器
            Anon:不指定过滤器,这个过滤器是空的,什么都没做,跟没有一样。
            Authc:验证,这些页面必须验证后才能访问,也就是我们说的登录后才能访问。
            user:验证+记住我
         -->
		<property name="filterChainDefinitions">
			<value>
				<!--静态资源-->
				/static/** = anon
				<!--链接-->
				/login.do=anon
				/toLogin.do=anon
				/** = user
                <!--自定义过滤器-->
                /** = MyRemember
			</value>
		</property>
	</bean>
</beans>

        我只放了相关的配置,无关的都省略掉了;

by the way:

1.Shiro的其他配置建议看这位博主文章,我认为是写的最工整易懂的:https://blog.csdn.net/u012737182/article/category/6489910

2.序列化与反序列化的相关文章:https://blog.csdn.net/qq_27093465/article/details/78544505

shiro记住功能的前端主要需要实现以下几个步骤: 1. 在登录页面添加一个“记住我”的复选框,并绑定相应的事件。 2. 当用户勾选“记住我”复选框时,前端需要将用户名和密码保存到cookie中。 3. 在登录时,前端需要先检查是否存在“记住我”的cookie,如果存在,则自动填充用户名和密码,并勾选“记住我”复选框。 4. 如果用户点击了“退出登录”按钮,前端需要清除保存的用户名和密码的cookie。 下面是一个简单的示例代码: HTML代码: ```html <form> <label for="username">用户名:</label> <input type="text" id="username" name="username"> <br> <label for="password">密码:</label> <input type="password" id="password" name="password"> <br> <input type="checkbox" id="rememberMe" name="rememberMe"> <label for="rememberMe">记住我</label> <br> <button type="submit">登录</button> <button type="button" id="logout">退出登录</button> </form> ``` JavaScript代码: ```javascript // 检查是否存在“记住我”的cookie,并自动填充用户名和密码 if (document.cookie.indexOf('rememberMe=1') !== -1) { const username = localStorage.getItem('username'); const password = localStorage.getItem('password'); document.getElementById('username').value = username; document.getElementById('password').value = password; document.getElementById('rememberMe').checked = true; } // 绑定登录表单的提交事件 document.querySelector('form').addEventListener('submit', (event) => { event.preventDefault(); const username = document.getElementById('username').value; const password = document.getElementById('password').value; const rememberMe = document.getElementById('rememberMe').checked; // 记住用户名和密码 if (rememberMe) { localStorage.setItem('username', username); localStorage.setItem('password', password); document.cookie = 'rememberMe=1'; } else { localStorage.removeItem('username'); localStorage.removeItem('password'); document.cookie = 'rememberMe=0'; } // 发送登录请求 // ... }); // 绑定退出登录按钮的点击事件 document.getElementById('logout').addEventListener('click', () => { localStorage.removeItem('username'); localStorage.removeItem('password'); document.cookie = 'rememberMe=0'; // 发送退出登录请求 // ... }); ```
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值