OJ项目【登录】——验证码、失败登录多次账户冻结、用户密码加密,我是如何实现的?

目录

前言

1、验证码

1.1、引入pom

1.2、前端核心代码

1.3、后端核心代码

2、账户冻结

2.1、思路: 

2.2、核心代码示例:

3、密码加密——加盐算法

3.1、思路:

3.2、代码实现示例:

4、小结:展示我的项目

4.1、后端代码:

4.2、效果展示:


前言

         前端代码,我只展示核心代码,其他的代码需要小伙伴们自行编写哦~

        项目是Spring项目,需要小伙伴们有一点点Spring基础~

        我这些实现方式,只是一个参考,并不是最优解~


1、验证码

        验证码这里,我们使用的是easy-captcha,对他感兴趣的伙伴,可以自行查一下资料,下面,我只实现4位验证码,有字母和数字组成的这种~

1.1、引入pom

        <!-- 验证码 --><dependency><groupId>com.github.whvcse</groupId><artifactId>easy-captcha</artifactId><version>1.6.2</version></dependency>

1.2、前端核心代码

准备一个html: 

<div class="row"><input type="text" id="authCode" class="form-control" name="verifyCode" placeholder="请输入验证码" required="true"><img class="imgCode" alt="点击图片刷新!" src="/common/kaptcha" onclick="this.src='/common/kaptcha?d='+new Date()*1">
</div>

说明:

  • 就是准备了一个input输入框,供我们输入验证码;准备一个图片,显示我们的验证码
  • 重点要说的就是照片img标签中,src的路径是一个URL,也就是说,这张照片的来源就是从这个URL来的;点击照片时,会触发onclick事件,这个事件会改变该图片src的属性,新的src为:'/common/kaptcha?d='new Date()*1,这个表达式会生成一个新的日期时间戳,并将其附加到图片的URL后面,从而获取一个新的图片~ 【src中的URL由后端实现~】

1.3、后端核心代码

准备一个controller类: 

package com.example.demo.controller;import com.wf.captcha.SpecCaptcha;
import com.wf.captcha.base.Captcha;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;@Controller
@RequestMapping("/common")
public class commonCotroller {@GetMapping("/kaptcha")public void defaultKaptcha(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse) throws Exception {httpServletResponse.setHeader("Cache-Control", "no-store");httpServletResponse.setHeader("Pragma", "no-cache");httpServletResponse.setDateHeader("Expires", 0);httpServletResponse.setContentType("image/gif");// 三个参数分别为宽、高、位数SpecCaptcha captcha = new SpecCaptcha(150, 30, 4);// 设置字体captcha.setCharType(Captcha.FONT_9);// 验证码存入sessionhttpServletRequest.getSession().setAttribute("authCode", captcha.text().toLowerCase());// 输出图片流captcha.out(httpServletResponse.getOutputStream());}
}

 说明:

        到这里,验证码的模块就实现完成了,具体,在登录时如何操作的,下面第四点中会举例说明~ 


2、账户冻结

2.1、思路: 

        关于账户冻结,我是在数据库设计中,给用户表添加了两个字段:状态state和冷却时间lTime。默认的state值为1,默认的lTime为0。当用户每登录错误一次时,给该用户的state加一;当state大于3时,表示该用户已经连续错误登录三次了,该账户将被冻结;冻结时间设置:获取现在的时间戳加上30000,换算成秒就是,给当前时间加上30s;在登录前,先验证给账户是否被冻结了,也就是查看当前时间戳是否小于该用户数据库中存储的冻结时间戳~

2.2、核心代码示例:

    @RequestMapping("/login")public AjaxResult login(HttpServletRequest request, String username, String password,String authCode) {//0.参数校验if(!StringUtils.hasLength(username) || username.length() > 50) {return AjaxResult.fail("用户名输入违法,请重新输入!");}if(!StringUtils.hasLength(password) ||password.length() > 10) {return AjaxResult.fail("密码输入违法,请重新输入!");}if(!StringUtils.hasLength(authCode)) {return AjaxResult.fail("验证码不能为空!");}//1、校验验证码是否正确相关操作// ...//2、验证该用户的登录功能是否被冻结//2.1、先根据用户名查询出数据中的username的信息Userinfo userinfo = userService.getUserExist(username);if(userinfo == null) {return AjaxResult.fail("用户名或密码错误,请重新输入~");}//2.2、查看该用户的登录功能是否被冻结了if(userinfo.getState() > 3 && userinfo.getLTime() > System.currentTimeMillis()) {return AjaxResult.fail("登录已锁定,请等待" + (userinfo.getLTime() - System.currentTimeMillis())/1000 + "秒后重试");} else if(userinfo.getState() > 3 && userinfo.getLTime() < System.currentTimeMillis()) {//放置state为1--时间过了,解除冻结userinfo.setState(1);userService.stateOne(userinfo);}//3、对比密码是否正确相关操作// ...//3.3、可以正确登录,将之间的state标记恢复原状userinfo.setState(1);userService.stateOne(userinfo);//4、可以正确登录,后续操作// ....return AjaxResult.success("登陆成功");}

         上述代码还是很好理解的,我就不做过多解释了~


3、密码加密——加盐算法

        我们准备一个类,这个类主要就是处理密码的加密和验证密码操作。

3.1、思路:

  • 1:我们使用UUID生成一个随机盐值;
  • 2:密码加工1:把密码和盐值加起来,然后使用MD5哈希算法进行加密
  • 3:密码加工2:为了后续可以取出盐值,从而来验证密码是否正确,所以最终的密码:盐值 + "$" +  密码加工1 【这里是以字符串的形式拼接的】
  • 4:密码验证:先通过$符,取出盐值,再通过相同的加密方式加密,验证新密码加密后的值是否与数据库中的值相等~

3.2、代码实现示例:

public class PasswordUtils {//密码加盐:public static String encrypt(String password) {//1、生成一个32位的盐值String salt = UUID.randomUUID().toString().replace("-","");//2、生成加盐后的密码,并将盐值和加盐后的密码并在一起return splicing(password,salt);}//验证密码是否正确public static boolean check(String inputPassword,String finPassword) {//1、获取saltString salt = finPassword.split("\\$")[0];//2、使用一样的盐值,加密String inputFinPassword = splicing(inputPassword,salt);if(inputFinPassword.equals(finPassword)) {return true;}return false;}//密码加盐的辅助方法private static String splicing(String password, String salt) {//1、使用md5生成加盐后的密码1String finpassword = DigestUtils.md5DigestAsHex((salt + password).getBytes());//2、返回最终密码【盐值 $ 密码1】return (salt + "$" +finpassword);}
}

4、小结:展示我的项目

        上述重复的代码,我就不展示了,展示一下,我的UserController类的实现吧~

4.1、后端代码:

@RestController
@RequestMapping("/user")
public class UserController {@Autowiredprivate UserService userService;@RequestMapping("/login")public AjaxResult login(HttpServletRequest request, String username, String password,String authCode) {//0.参数校验if(!StringUtils.hasLength(username) || username.length() > 50) {return AjaxResult.fail("用户名输入违法,请重新输入!");}if(!StringUtils.hasLength(password) ||password.length() > 10) {return AjaxResult.fail("密码输入违法,请重新输入!");}if(!StringUtils.hasLength(authCode)) {return AjaxResult.fail("验证码不能为空!");}//1、校验验证码是否正确HttpSession session = request.getSession();//默认为true,有则获取,无则会先新建再获取String trueAuthCode = (String) session.getAttribute("authCode");if(!trueAuthCode.equalsIgnoreCase(authCode)) {return AjaxResult.fail("验证码输入错误!");}//2、验证该用户的登录功能是否被冻结//2.1、先根据用户名查询出数据中的username的信息Userinfo userinfo = userService.getUserExist(username);if(userinfo == null) {return AjaxResult.fail("用户名或密码错误,请重新输入~");}//2.2、查看该用户的登录功能是否被冻结了if(userinfo.getState() > 3 && userinfo.getLTime() > System.currentTimeMillis()) {return AjaxResult.fail("登录已锁定,请等待" + (userinfo.getLTime() - System.currentTimeMillis())/1000 + "秒后重试");} else if(userinfo.getState() > 3 && userinfo.getLTime() < System.currentTimeMillis()) {//放置state为1--时间过了,解除冻结userinfo.setState(1);userService.stateOne(userinfo);}//3、对比密码是否正确if(!PasswordUtils.check(password,userinfo.getPassword())) {//3.1、如果密码错误,则数据库中标记+1userinfo.setState(userinfo.getState() + 1);//给数据库中的state+1userService.stateOne(userinfo);//3.2、错误次数达标,设置冷却时间if(userinfo.getState() > 3) {userinfo.setLTime(System.currentTimeMillis() + 30000);userService.setLTime(userinfo);}return AjaxResult.fail("用户名或密码错误,请重新输入~");}//3.3、可以正确登录,将之间的标记恢复原状userinfo.setState(1);userService.stateOne(userinfo);//4、可以正确登录,给session中存储给用户的信息-放置session信息session.setAttribute(AppVariable.USER_SESSION_KEY,userinfo);//5、返回登陆成功return AjaxResult.success("登陆成功");}
}

        前端代码,我就不展示了~ 大家自行发挥~~~

4.2、效果展示:

 

        好啦,本期就到这里咯,对效果展示中的弹窗感兴趣的伙伴,可以看看持续关注我后续的动态,会出一个简单的教程 

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/107442.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

在 Elasticsearch 中实现自动完成功能 2:n-gram

在第一部分中&#xff0c;我们讨论了使用前缀查询&#xff0c;这是一种自动完成的查询时间方法。 在这篇文章中&#xff0c;我们将讨论 n-gram - 一种索引时间方法&#xff0c;它在基本标记化后生成额外的分词&#xff0c;以便我们稍后在查询时能够获得更快的前缀匹配。 但在此…

MySQL InnoDB引擎深入学习的一天(InnoDB架构 + 事务底层原理 + MVCC)

目录 逻辑存储引擎 架构 概述 内存架构 Buffer Pool Change Buffe Adaptive Hash Index Log Buffer 磁盘结构 System Tablespace File-Per-Table Tablespaces General Tablespaces Undo Tablespaces Temporary Tablespaces Doublewrite Buffer Files Redo Log 后台线程 事务原…

30天工作量,推荐4个ai写作生成器工具,一键搞定!

全新升级&#xff01;畅销热门AI写作工具盘点40强&#xff0c;助你一键呈现顶尖文案&#xff01; AI写作工具&#xff0c;引领时代潮流&#xff0c;让办公生活更高效&#xff01;小编特意整理了市面上最好用的AI写作工具&#xff0c;共计40款&#xff01;你使用过哪些&#xff…

【JAVA-Day45】Java常用类StringBuffer解析

Java常用类StringBuffer解析 Java常用类StringBuffer解析一、什么是StringBuffer类二、StringBuffer类的方法2.1 append方法2.2 insert方法2.3 delete方法2.4 replace方法2.5 reverse方法2.6 toString方法2.7 capacity方法2.8 length方法 三、StringBuffer类的应用场景深入了解…

选择适合自身业务的HTTP代理有哪些因素决定?

相信对很多爬虫工作者和数据采集的企业来说&#xff0c;如何选购适合自己业务的HTTP代理是一个特别特别困扰的选题&#xff0c;市面上那么多HTTP代理厂商&#xff0c;好像这家有这些缺点&#xff0c;转头又看到另外一家的缺点&#xff0c;要找一家心仪的仿佛大海捞针。今天我们…

【音视频|ALSA】SS528开发板编译Linux内核ALSA驱动、移植alsa-lib、采集与播放usb耳机声音

&#x1f601;博客主页&#x1f601;&#xff1a;&#x1f680;https://blog.csdn.net/wkd_007&#x1f680; &#x1f911;博客内容&#x1f911;&#xff1a;&#x1f36d;嵌入式开发、Linux、C语言、C、数据结构、音视频&#x1f36d; &#x1f923;本文内容&#x1f923;&a…

二、深度测试(Z Test)

1.是什么 ①从渲染管线出发 ②书面上理解 所谓深度测试&#xff0c;就是针对当前对象在屏幕上&#xff08;更准确的说是frame buffer&#xff09;对应的像素点&#xff0c;讲对象自身的深度值与当前该像素点缓存的深度值进行比较&#xff0c;如果通过了&#xff0c;本对象再改…

使用 Github Actions 工作流自动部署 Github Pages

GitHub-Actions actions顾名思义就是一堆动作&#xff0c;是一个持续集成服务&#xff0c;持续集成包含了拉代码、运行测试、编译代码、登录远程服务器&#xff0c;发布到第三方服务等等的操作&#xff0c;GitHub将这些操作称为actions。 概念&#xff1a;Workflows, Events,…

【Java学习之道】网络编程的基本概念

引言 这一章我们将一同进入网络编程的世界。在开始学习网络编程之前&#xff0c;我们需要先了解一些基本概念。那么&#xff0c;我们就从“什么是网络编程”这个问题开始吧。 一、网络编程的基本概念 1.1 什么是网络编程 网络编程&#xff0c;顾名思义&#xff0c;就是利用…

【算法-动态规划】完全背包问题

&#x1f49d;&#x1f49d;&#x1f49d;欢迎来到我的博客&#xff0c;很高兴能够在这里和您见面&#xff01;希望您在这里可以感受到一份轻松愉快的氛围&#xff0c;不仅可以获得有趣的内容和知识&#xff0c;也可以畅所欲言、分享您的想法和见解。 推荐:kuan 的首页,持续学…

使用vue3+element-ui plus 快速构建后台管理模板

一、安装 vue3 脚手架 npm create vuelatestcd vue-ui-template #切换到刚刚创建好的vue项目根目录中 npm install #下载项目所需要的依赖包 npm run dev #启动运行项目服务项目启动后&#xff0c;默认页面显示如下&#xff1a; 二、安装element-ui plus 官网链接&#xff1a;…

Vue-3.0路由

生活中的路由&#xff1a;设备和ip的映射关系 路由就是一种映射关系 Vue中路由&#xff1a;路径和组件的映射关系&#xff0c;根据路由就能知道不同路径的&#xff0c;应该匹配渲染哪个组件 VueRouter的介绍 作用&#xff1a;修改地址栏路径时&#xff0c;切换显示匹配的组…

idea中父工程Project创建

1.file-->new-->Project 2.选择maven包和JavaSDK 3.填写项目名&#xff0c;选择文件目录&#xff0c;项目包等 4.配置maven tip&#xff1a;约定>配置>编码 5.设置项目编码 6.注解生效激活&#xff0c;便于项目中使用注解 7.Java编译版本选择8 8.File Type 过滤&a…

php74 安装sodium

下载编译安装libsodium wget https://download.libsodium.org/libsodium/releases/libsodium-1.0.18-stable.tar.gz tar -zxf libsodium-1.0.18-stable.tar.gz cd libsodium-stable ./configure --without-libsodium make && make check sudo make install下载编译安装…

ChatGPT DALL-E 3的系统提示词大全

每当给出图像的描述时&#xff0c;使用dalle来创建图像&#xff0c;然后用纯文本总结用于生成图像的提示。如果用户没有要求创建特定数量的图像&#xff0c;默认创建四个标题&#xff0c;这些标题应尽可能多样化。发送给Dalle的所有标题都必须遵循以下策略&#xff1a;1.如果描…

GitLab 502问题解决方案

由于最近 gitlab 切换到另一台服务器上部署的 gitlab 后&#xff0c;经常出现 502。平时重启 gitlab 后都能解决&#xff0c;今天突然重启多次后都还是 502&#xff08;重启日志是正常的&#xff09;&#xff0c;遂通过 gitlab-ctl tail 查看日志进行排查。 gitlab-ctl tail通…

到底什么是5G-R?

近日&#xff0c;工信部向中国国家铁路集团有限公司&#xff08;以下简称“国铁集团”&#xff09;批复5G-R试验频率的消息&#xff0c;引起了行业内的广泛关注。 究竟什么是5G-R&#xff1f;为什么工信部会在此时批复5G-R的试验频率&#xff1f; 今天&#xff0c;小枣君就通过…

让ChatGPT等模型学会自主思考!开创性技术“自主认知”框架

ChatGPT、百度文心一言、Bard等大语言模型展现出了超强的创造能力&#xff0c;加速了生成式AI的应用进程。但AI模型只能基于训练数据执行各种任务&#xff0c;无法像人类一样利用生活知识、过往经验用于复杂的推理和决策。 例如&#xff0c;在玩游戏时&#xff0c;人类可以利用…

Python 控制语句

目录 1 选择结构1.1 单分支选择结构1.2 条件表达式详解1.3 条件表达式中&#xff0c;不能有赋值操作符“”1.4 双分支选择结构1.5 三元条件运算符1.6 多分支选择结构1.7 选择结构嵌套 2 循环结构2.1 while循环2.2 for循环和可迭代对象遍历2.3 可迭代对象2.4 range对象2.5 嵌套循…

2023年淘宝天猫双11红包领取活时间什么时候开始领天猫淘宝双十一红包优惠券?

2023年淘宝天猫双11红包领取活动开始与结束时间 2023年10月24日20:00开始领取至11月11日23:59结束&#xff1b; 2023年淘宝天猫双11红包活动使用开始与结束时间 第一波&#xff1a;2023年10月31日20:00开始使用至11月3日23:59 第二波&#xff1a;2023年11月10日20:00开始使用…