单点登陆解决方案以及代码分析与实现
来源:互联网 发布:淘宝无线端链接转换 编辑:程序博客网 时间:2024/06/15 13:10
1.什么是单点登陆
同一家公司不同应用使用同一套登陆系统叫做单点登陆系统
2.单点登陆的引出
比如QQ号可以登陆很多游戏,而且这些游戏都是腾讯公司的,所以不再开发新的登陆模块,QQ就可以登陆多个应用.在写的过程中,我们注重用户体验,考虑用户体验的时候我们的用户名和密码的判断都是很精准的。没有用户名或者密码字样的出现。
3.代码实现
/*** 登陆* @param username 帐号* @param password 密码* @param ReturnUrl 回调地址* @param request 浏览器--服务器* @param response 服务器--浏览器* @param model springmvc模型* @return 请求转发至登陆页面或重定向到回调地址*/@RequestMapping(value = "/Login.aspx", method = RequestMethod.POST) public String login(String username, String password, String ReturnUrl, HttpServletRequest request,HttpServletResponse response, Model model) { // 用户名不能为空 if (null != username) { // 密码不能为空 if (null != password) { // 用户名必须正确 Buyer buyer = buyerService.selectBuyerByUserName(username); if (buyer != null) { // 密码必须正确 if (buyer.getPassword().equals(encodingPassword(password))) { // TODO 密码不正确3次之后出现 验证码 不能为空 验证码 必须正确 // 保存用户信息到远程session 单点登陆解决方案 sessionProviderService.setAttributeForUserName (RequestUtils.getCSESSIONID(request,response),buyer.getUsername()); return "redirect:" + ReturnUrl; } else { model.addAttribute("error", "用户名必须正确"); } } else { model.addAttribute("error", "用户名必须正确"); } } else { model.addAttribute("error", "密码不能为空"); } } else { model.addAttribute("error", "用户名不能为空"); } return "login"; }
同样在分布式架构中 在数据库中查询用户名也不是一个好的选择 ,因为不再是一个数据库,后期会搭建数据库集群,数据的存放是根据id存放的,在数据库中直接查询 用户名必须正确 buyerService.selectBuyerByUserName(username); 这一条SQL语句是十分浪费性能的,用户姓名是一个varchar字段,首先是不能建立比较好的索引策略,同时前台也无法传入正确的用户id。我们应该根据用户的id去查询用户,这样只会查询相应的数据库而不会全库扫描。
用户名查询解决方案
@Override public Buyer selectBuyerByUserName(String username) { Buyer buyer = null; // redis 中查找用户id String id = jedis.hget("user", username); if (id != username) { // 用户查找对象 buyer = buyerDao.selectByPrimaryKey(Long.parseLong(id)); } return buyer; }
redis 中存放的是用户的类型是哈希 key 是用户名称 value 是用户的id 因为redis 是单线程并且是一个nosql数据库,查询速度非常的快,因此将用户存入redis 是在用户注册时候进行的。
redis 中命令如下 hmset username zhangsan 1
/** * 令牌工具类 * @author ZhuPengWei * @date 2017年11月7日 */public class RequestUtils { /** * 生成令牌 * @param request 浏览器-服务器 * @param response 服务器-浏览器 * @return 令牌 */ public static String getCSESSIONID(HttpServletRequest request, HttpServletResponse response) { // 浏览器中有没有对应cookie CSSESIONID Cookie[] cookies = request.getCookies(); for (Cookie cookie : cookies) { if (Constant.COOKIE_CSSESIONID.equals(cookie.getName())) { // 存在cookie return cookie.getValue(); } } // 没有 创建一个令牌 String csession = UUID.randomUUID().toString().replaceAll("-", ""); Cookie cookie = new Cookie(Constant.COOKIE_CSSESIONID, csession); cookie.setPath("/"); // 0立即失效 -1关闭浏览器失效 cookie.setMaxAge(-1); // 写在浏览器之中 response.addCookie(cookie); return csession; }}
和大多公司单点登录解决方案一样,模拟request.getSession(),做出了一个假的session 存入了cookie中,
这样 服务器可以通过这个令牌在redis中获取数据或者设置数据了
/** * Session业务层接口 * 提供session * 获取session * @author ZhuPengWei * @date 2017年11月7日 */public interface SessionProviderService { /** * 设置远程session * @param key 令牌 * @param userName 用户名 */ public void setAttributeForUserName(String key, String userName); /** * 从redis中取出用户名 * @param key 令牌 */ public String getAttributeUserNameByRedis(String key);}
package open.shopping.service.user;import org.springframework.beans.factory.annotation.Autowired;import org.springframework.stereotype.Service;import open.shopping.common.web.Constant;import redis.clients.jedis.Jedis;/** * Session业务层实现类 * 提供session * 获取session * @author ZhuPengWei * @date 2017年11月7日 */@Service("sessionProviderService")public class SessionProviderServiceImpl implements SessionProviderService { @Autowired private Jedis jedis; @Override public void setAttributeForUserName(String key, String userName) { jedis.set(Constant.USER_SESSION + key, userName); // 设置存活时间为30分钟 jedis.expire(Constant.USER_SESSION + key, 60 * 30); jedis.close(); } @Override public String getAttributeUserNameByRedis(String key) { String userName = jedis.get(Constant.USER_SESSION + key); if (null != userName) { // 设置存活时间为30分钟 jedis.expire(Constant.USER_SESSION + key, 60 * 30); } jedis.close(); return userName; }}
是不是觉得单点登录其实也很简单。
阅读全文
0 0
- 单点登陆解决方案以及代码分析与实现
- 单点登陆与实现原理
- 单点登陆的技术实现机制分析
- 京东SSO单点登陆实现分析
- 京东SSO单点登陆实现分析
- 单点登陆解决方案
- 单点登陆解决方案一
- 单点登陆解决方案二
- 单点登陆原理与简单实现
- Session和Cookie小结以及PHP单点登陆的实现
- SSO-单点登陆/单点登录完全解决方案
- 单点登陆最简单解决方案
- 单点登陆最简单解决方案
- 网站用户单点登陆解决方案
- 网站用户单点登陆解决方案
- 单点登陆、session共享解决方案
- MOSS2007 实现单点登陆
- 跨子域实现单点登陆
- 红包分享给你,就是让你点进来的,支付宝红包
- 大数据(三十三)HBASE【Phoenix】
- 分别采用匿名类和lambda来实现spark API的接口
- 鸡鸡鸡鸡汤
- 机器学习十大算法之K-means算法
- 单点登陆解决方案以及代码分析与实现
- C语言 45章作业
- Python xrange与range的区别返回的结果不一样
- Spring Boot
- anaconda下安装opencv_python
- 1!+2!+...+n!的和
- bootstrap 实现轮播图
- HTML&CSS项目创建(页面练习)
- SQL 习题进阶 二