这是我们之前项目的业务流程,做一下简单介绍。

登录:

用户输入账号、密码、验证码。我们先判断用户输入的验证码是不是我们session存的验证码,然后去查账号密码是否正确。

如果登录成功,发送给用户一张凭证(ticket)。

登录后

之后的每次请求,用户携带ticket,服务器得到后,根据ticket去login_ticket表中查找登录信息,并且根据登录信息再查user表获得更多的用户信息。

使用Redis存储验证码

- 验证码需要频繁的访问与刷新,对性能要求较高。
- 验证码不需永久保存,通常在很短的时间后就会失效。
- 分布式部署时,存在Session共享的问题。

我们重构思路:进入登录页面会访问验证码方法,此方法会自动生成一个验证码和图片,将验证码和图片输出给浏览器,并且下发一个cookies,这个cookies里面存的是一段随机数,这段随机数作为key存在redis里面(之前是存session),value就是验证码,并设置一个过期时间;

    //验证码@RequestMapping(path = "/kaptcha", method = RequestMethod.GET)public void getKaptcha(HttpServletResponse response/*, HttpSession session*/) {// 生成验证码String text = kaptchaProducer.createText();BufferedImage image = kaptchaProducer.createImage(text);// 将验证码存入session//session.setAttribute("kaptcha", text);//验证码的归属String owner= CommunityUtil.generateUUID();Cookie cookie=new Cookie("kaptchaOwner",owner);cookie.setMaxAge(60);cookie.setPath(contextPath);response.addCookie(cookie);//存入redisString redisKey= RedisKeyUtil.getKaptchaKey(owner);redisTemplate.opsForValue().set(redisKey,text,60, TimeUnit.SECONDS);// 将图片输出给浏览器response.setContentType("image/png");try {OutputStream os = response.getOutputStream();ImageIO.write(image, "png", os);} catch (IOException e) {logger.error("响应验证码失败:" + e.getMessage());}}
    @RequestMapping(path = "/login",method = RequestMethod.POST)public String login(String username,String password,String code,boolean rememberme,Model model,/*HttpSession session,*/HttpServletResponse response,@CookieValue("kaptchaOwner") String kaptchaOwner){// 检查验证码//String kaptcha = (String) session.getAttribute("kaptcha");String kaptcha=null;if(StringUtils.isNotBlank(kaptchaOwner)){String redisKey=RedisKeyUtil.getKaptchaKey(kaptchaOwner);kaptcha=(String) redisTemplate.opsForValue().get(redisKey);}if(StringUtils.isBlank(kaptcha) || StringUtils.isBlank(code) || !kaptcha.equalsIgnoreCase(code)){model.addAttribute("codeMsg", "验证码不正确!");return "/site/login";}// 检查账号,密码int expiredSeconds = rememberme ? REMEMBER_EXPIRED_SECONDS : DEFAULT_EXPIRED_SECONDS;Map<String, Object> map = userService.login(username, password, expiredSeconds);if (map.containsKey("ticket")) {Cookie cookie = new Cookie("ticket", map.get("ticket").toString());cookie.setPath(contextPath);cookie.setMaxAge(expiredSeconds);response.addCookie(cookie);return "redirect:/index";} else {...}}

使用Redis存储登录凭证

- 处理每次请求时,都要查询用户的登录凭证,访问的频率非常高。

登录时不存MySQL里,存redis里

    public Map<String,Object> login(String username,String password,int expiredSeconds){Map<String,Object> map=new HashMap<>();// 生成登录凭证LoginTicket loginTicket = new LoginTicket();loginTicket.setUserId(user.getId());loginTicket.setTicket(CommunityUtil.generateUUID());loginTicket.setStatus(0);loginTicket.setExpired(new Date(System.currentTimeMillis() + expiredSeconds * 1000));//loginTicketMapper.insertLoginTicket(loginTicket);String redisKey= RedisKeyUtil.getTicketKey(loginTicket.getTicket());redisTemplate.opsForValue().set(redisKey,loginTicket);...}

查找

退出时也是改redis

    public void logout(String ticket) {//loginTicketMapper.updateStatus(ticket, 1);String redisKey= RedisKeyUtil.getTicketKey(ticket);LoginTicket loginTicket=(LoginTicket) redisTemplate.opsForValue().get(redisKey);loginTicket.setStatus(1);redisTemplate.opsForValue().set(redisKey,loginTicket);}

使用Redis缓存用户信息

- 处理每次请求时,都要根据凭证查询用户信息,访问的频率非常高。

缓存用户信息:因为会经常根据userid来查询user对象,所以使用redis来缓存提高服务器性能。使用redis的String类型,存入user对象,会自动将整个对象转换成json字符串,同时设置过期时间;

取值:优先从redis中取,取不到的时候从mysql中取,并将数据初始化到redis中

更新:更新的时候先更新mysql中的值,然后清除缓存数据;

    // 1.优先从缓存中取值private User getCache(int userId) {String redisKey = RedisKeyUtil.getUserKey(userId);return (User) redisTemplate.opsForValue().get(redisKey);}// 2.取不到时初始化缓存数据private User initCache(int userId) {User user = userMapper.selectById(userId);String redisKey = RedisKeyUtil.getUserKey(userId);redisTemplate.opsForValue().set(redisKey, user, 3600, TimeUnit.SECONDS);return user;}// 3.数据变更时清除缓存数据private void clearCache(int userId) {String redisKey = RedisKeyUtil.getUserKey(userId);redisTemplate.delete(redisKey);}
    public User findUserById(int id) {
//        return userMapper.selectById(id);User user = getCache(id);if (user == null) {user = initCache(id);}return user;}
    public int updateHeader(int userId, String headerUrl) {//return userMapper.updateHeader(userId, headerUrl);int rows=userMapper.updateHeader(userId, headerUrl);clearCache(userId);return rows;}

redis——对项目的一些优化方案相关推荐

  1. 前端Vue项目打包性能优化方案

    文章目录 一.前言 二.优化方案 1丶路由懒加载(代码分割) 2丶第三方插件按需加载 3丶常用插件库使用CDN加速 4.gzip压缩 5.打包不生成map文件 三.工具推荐 可视化分析包大小 总结 一 ...

  2. 基于Redis实现延时队列的优化方案

    一.延时队列的应用 近期在开发部门的新项目,其中有个关键功能就是智能推送,即根据用户行为在特定的时间点向用户推送相应的提醒消息,比如以下业务场景: 在用户点击充值项后,半小时内未充值,向用户推送充值未 ...

  3. 轨迹系列8——记某真实项目中轨迹展示查询效率优化方案一(初步设计)

    文章版权由作者李晓晖和博客园共有,若转载请于明显处标明出处:http://www.cnblogs.com/naaoveGIS/ 1.    背景 准确说,该项目的迹展示涉及到两个方面,一个是轨迹查询展 ...

  4. 宝塔linux优化wordpress,WordPress加速 宝塔面板速度优化方案 Memcached + Redis | 「讲文兄博客」...

    WordPress 网站的速度应该上每个站长必须关注的一个问题,对于刚使用 WordPress 的朋友,优化网站速度是比较困难的事情,找不到好的解决方案.今天就来推荐 WordPress 速度优化方案 ...

  5. Redis性能优化方案总结

    一.优化的一些建议 1.尽量使用短的key 当然在精简的同时,不要为了key的"见名知意".对于value有些也可精简,比如性别使用0.1. 2.避免使用keys * keys * ...

  6. 项目优化方案及分析过程,解决办法

    一.工具和排查方法 二.大批量的导入导出优化 三.抽样计算功能的优化 1.1. 工具和排查方法 1.1.1. 使用jdk自带的 jconsole,直接在cmd命令中打入jconsole,就会弹出一个窗 ...

  7. 火云开发课堂 - 《使用Cocos2d-x 开发3D游戏》系列 第二十五节: 3D项目优化方案

    <使用Cocos2d-x 开发3D游戏>系列在线课程 第二十五节:3D项目优化方案 视频地址:http://edu.csdn.net/course/detail/1330/20825?au ...

  8. mysql 常用优化方案_项目中常用的 19 条 MySQL 优化方案

    声明一下:下面的优化方案都是基于 " Mysql-索引-BTree类型 " 的 一.EXPLAIN 做MySQL优化,我们要善用 EXPLAIN 查看SQL执行计划. 下面来个简单 ...

  9. Vue 项目性能优化方案

    前言 Vue 框架通过数据双向绑定和虚拟 DOM 技术,帮我们处理了前端开发中最脏最累的 DOM 操作部分, 我们不再需要去考虑如何操作 DOM 以及如何最高效地操作 DOM:但 Vue 项目中仍然存 ...

最新文章

  1. 用eclipse玩转Python,让习惯java开发的童鞋拥有一个更爽的开发体验
  2. 再见,数据库!MySQL千亿数据分库分表架构,堪称惊艳!
  3. 三丰三坐标编程基本步骤_数控车床编程,经典实例教程
  4. RT2870 5370等移植(ARM,X86)
  5. opengl笔记—— glMultMatrixf() 区别 glLoadMatrixf()
  6. python安装mysqldb模块_Python的MySQLdb模块安装
  7. GBK编码/GBK内码/Big5
  8. 组态王五层电梯c语言编程,PLC编程实例分享,多图详解五层楼电梯控制系统~...
  9. python视频转化_python实现视频读取和转化图片
  10. java宽度优先搜索之八数码,广度优先搜索解决八数码问题
  11. uniapp H5 seo 百度自动收录(html通用代码)
  12. No tests found for given includes: [xxx.xxx.testList](filter.includeTestsMatching)
  13. Y件DOOK: VSC 安装 谷歌浏览器调试 固件插件 Debugger for Chorme
  14. Matlab求分段函数的积分
  15. 学好计算机的用途,学电脑的用途是什么
  16. win7安装vs2012失败
  17. 预测算法——指数平滑法
  18. MySQL的analyze table和optimize table对表进行定期优化
  19. 前端实训-----摆弄形状、浮动,高度塌陷等
  20. 解决conda创建新环境慢 conda install 速度慢 报错问题

热门文章

  1. python 局域网扫描_Python 简化版扫描局域网存活主机
  2. 由于找不到openni2_Kinect开发教程八:OpenNI2显示深度、彩色及融合图像
  3. 中国大学慕课计算机专业导论,2015秋计算机专业导论(大连大学)
  4. Arcgis自下而上从左到右进行编号
  5. 【转】CT解析重建**
  6. 【转】C#字节数组_字符串相互转换
  7. 【转】刨根究底字符编码之十六——Windows记事本的诡异怪事:微软为什么跟联通有仇?
  8. [你必须知道的.NET]第二十九回:.NET十年(上)
  9. 如何学习(记住)linux命令(常用选项)
  10. Github+jsDelivr+PicGo 打造稳定快速、高效免费图床