内容比较简单,需要完整项目的朋友留下邮箱,给你们发。

直接看效果:

下面是实现步骤

1.验证码生成工具类(引用自网络)

package com.laoxu.test.helloweb.util;

import javax.imageio.ImageIO;
import java.awt.*;
import java.awt.image.BufferedImage;
import java.awt.image.RenderedImage;
import java.io.FileOutputStream;
import java.io.OutputStream;
import java.util.HashMap;
import java.util.Map;
import java.util.Random; /**
* @Description: 原始验证码生成工具
* @Author laoxu
* @Date 2019/11/2 23:01
**/
public class VerifyCodeUtil {
private int width = 90;// 定义图片的width
private int height = 20;// 定义图片的height
private static int codeCount = 4;// 定义图片上显示验证码的个数
private static int xx = 15;
private int fontHeight = 18;
private static int codeY = 16;
private static char[] codeSequence = { 'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', 'M', 'N', 'O', 'P', 'Q', 'R',
'S', 'T', 'U', 'V', 'W', 'X', 'Y', 'Z', '0', '1', '2', '3', '4', '5', '6', '7', '8', '9' }; /**
* 生成一个map集合
* code为生成的验证码
* codePic为生成的验证码BufferedImage对象
* @return
*/
public static Map<String,Object> generateCodeAndPic(int width, int height, int fontHeight) {
// 定义图像buffer
BufferedImage buffImg = new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB);
// Graphics2D gd = buffImg.createGraphics();
// Graphics2D gd = (Graphics2D) buffImg.getGraphics();
Graphics gd = buffImg.getGraphics();
// 创建一个随机数生成器类
Random random = new Random();
// 将图像填充为白色
gd.setColor(Color.WHITE);
gd.fillRect(0, 0, width, height); // 创建字体,字体的大小应该根据图片的高度来定。
Font font = new Font("Fixedsys", Font.BOLD, fontHeight);
// 设置字体。
gd.setFont(font); // 画边框。
gd.setColor(Color.BLACK);
gd.drawRect(0, 0, width - 1, height - 1); // 随机产生40条干扰线,使图象中的认证码不易被其它程序探测到。
gd.setColor(Color.BLACK);
for (int i = 0; i < 30; i++) {
int x = random.nextInt(width);
int y = random.nextInt(height);
int xl = random.nextInt(12);
int yl = random.nextInt(12);
gd.drawLine(x, y, x + xl, y + yl);
} // randomCode用于保存随机产生的验证码,以便用户登录后进行验证。
StringBuffer randomCode = new StringBuffer();
int red = 0, green = 0, blue = 0; // 随机产生codeCount数字的验证码。
for (int i = 0; i < codeCount; i++) {
// 得到随机产生的验证码数字。
String code = String.valueOf(codeSequence[random.nextInt(36)]);
// 产生随机的颜色分量来构造颜色值,这样输出的每位数字的颜色值都将不同。
red = random.nextInt(255);
green = random.nextInt(255);
blue = random.nextInt(255); // 用随机产生的颜色将验证码绘制到图像中。
gd.setColor(new Color(red, green, blue));
gd.drawString(code, (i + 1) * xx, codeY); // 将产生的四个随机数组合在一起。
randomCode.append(code);
}
Map<String,Object> map =new HashMap<String,Object>();
//存放验证码
map.put("code", randomCode);
//存放生成的验证码BufferedImage对象
map.put("codePic", buffImg);
return map;
} public static void main(String[] args) throws Exception {
//创建文件输出流对象
OutputStream out = new FileOutputStream("D://tmp/"+System.currentTimeMillis()+".jpg");
Map<String,Object> map = VerifyCodeUtil.generateCodeAndPic(90,20,18);
ImageIO.write((RenderedImage) map.get("codePic"), "jpeg", out);
System.out.println("验证码的值为:"+map.get("code"));
}
}

2.写登录页

<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>登录页</title>
<link rel="stylesheet" href="css/bootstrap.min.css">
<link rel="stylesheet" href="css/login.css">
</head>
<body class="text-center">
<form class="form-signin">
<h1 class="h3 mb-3 font-weight-normal">请登录</h1>
<label for="username" class="sr-only">用户名:</label>
<input type="text" id="username" class="form-control" placeholder="" required="required" autofocus="">
<label for="password" class="sr-only">密码:</label>
<input type="password" id="password" class="form-control" placeholder="" required="required">
<div class="verify-div">
<label for="verify-code" class="sr-only">验证码:</label>
<input type="text" id="verify-code" style="width: 50%;" class="form-control" placeholder="" required="required">
<a href="#" onclick="changeVerifyCode()"><img id="imgObj" alt="验证码" src="/getVerifyCode"></a>
</div>
<button class="btn btn-lg btn-primary btn-block" type="submit" id="submit">登录</button>
</form>
</body>
<script type="text/javascript" src="js/jquery-1.11.3.min.js"></script>
<script type="text/javascript">
$(function() {
$("#submit").click(function (event) {
// 阻止表单默认提交
event.preventDefault(); var username = $("#username").val(), password = $("#password").val(),verifyCode=$("#verify-code").val();
if(username==""){
alert("用户名不能为空!");
return;
}
if(password==""){
alert("密码不能为空!");
return;
}
if(verifyCode==""){
alert("验证码不能为空!");
return;
} // 提交验证
$.ajax({
type: "POST",
url: "/checkLogin",
data: {
"username": username,
"password": password,
"verifyCode": verifyCode
},
success: function (result) {
if(result=='success'){
window.location.href="http://localhost:8080/success.html";
}else{
alert(result);
}
}
}); });
}); function changeVerifyCode() {
var imgSrc = $("#imgObj");
var src = imgSrc.attr("src");
imgSrc.attr("src", chgUrl(src));
} // 时间戳
// 为了使每次生成图片不一致,即不让浏览器读缓存,所以需要加上时间戳
function chgUrl(url) {
var timestamp = (new Date()).valueOf();
url = url.substring(0, 20);
if ((url.indexOf("&") >= 0)) {
url = url + "×tamp=" + timestamp;
} else {
url = url + "?timestamp=" + timestamp;
}
return url;
} </script>
</html>

3.写controller

package com.laoxu.test.helloweb;

import com.laoxu.test.helloweb.util.VerifyCodeUtil;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.*; import javax.imageio.ImageIO;
import javax.servlet.ServletOutputStream;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import java.awt.image.RenderedImage;
import java.io.IOException;
import java.util.Map; /**
* @Description:
* @Author laoxu
* @Date 2019/11/2 13:35
**/
@Controller
public class LoginController {
@RequestMapping("/login")
public String index(){
return "forward:/login.html";
} @RequestMapping("/getVerifyCode")
public void getVerifyCode(HttpServletRequest request, HttpServletResponse response){
// 调用工具类生成的验证码和验证码图片
Map<String, Object> codeMap = VerifyCodeUtil.generateCodeAndPic(90,20,18); // 将四位数字的验证码保存到Session中。
HttpSession session = request.getSession();
session.setAttribute("verifyCode", codeMap.get("code").toString().toUpperCase()); // 禁止图像缓存。
response.setHeader("Pragma", "no-cache");
response.setHeader("Cache-Control", "no-cache");
response.setDateHeader("Expires", -1); response.setContentType("image/jpeg"); // 将图像输出到Servlet输出流中。
ServletOutputStream sos;
try {
sos = response.getOutputStream();
ImageIO.write((RenderedImage) codeMap.get("codePic"), "jpeg", sos);
sos.close();
} catch (IOException e) {
e.printStackTrace();
}
} @ResponseBody
@RequestMapping("/checkLogin")
public String checkLogin(@RequestParam String username,
@RequestParam String password,
@RequestParam String verifyCode,
HttpServletRequest request){
String sessionVerifyCode = (String) request.getSession().getAttribute("verifyCode"); if(!"admin".equals(username)){
return "用户名错误!";
} if(!"123".equals(password)){
return "密码错误!";
} if(!sessionVerifyCode.equals(verifyCode.toUpperCase())){
return "验证码错误!";
} return "success";
}
}

需要完整项目的朋友留下邮箱。

spring boot实现验证码登录的更多相关文章

  1. spring Boot 简单的登录功能,利用了jdbcTemplate.class完成sql语句的执行,无需service层、dao层和.xml文件

    1.搭建SpringBoot项目首先我们先在IDEA上创建一个SpringBoot的Web项目(1)file ——> new ——> project——> Spring Initia ...

  2. Spring Boot中验证码实现kaptcha

    要生成验证码网上的方案比较多,基本是基于两大类:1为自定义生成,操作用Image类,2为kaptcha生成,有模糊算法. 当然也可以直接交由前端进行处理 1.基于kaptcha 首先不要怀疑的是报名是 ...

  3. 15 Spring Boot Shiro 验证码

    1. <dependency> <groupId>com.github.axet</groupId> <artifactId>kaptcha</a ...

  4. 14 Spring Boot Shiro限制登录尝试次数

  5. Spring Boot+Mybatis:实现数据库登录注册与两种properties配置参数读取

    〇.参考资料 1.hutool介绍 https://blog.csdn.net/abst122/article/details/124091375 2.Spring Boot+Mybatis实现登录注 ...

  6. 精通Spring Boot

    原 精通Spring Boot—— 第二十一篇:Spring Social OAuth 登录简介 1.什么是OAuth OAuth官网介绍是这样的: An open protocol to allow ...

  7. 详解Spring Security的formLogin登录认证模式

    一.formLogin的应用场景 在本专栏之前的文章中,已经给大家介绍过Spring Security的HttpBasic模式,该模式比较简单,只是进行了通过携带Http的Header进行简单的登录验 ...

  8. spring boot:spring security给用户登录增加自动登录及图形验证码功能(spring boot 2.3.1)

    一,图形验证码的用途? 1,什么是图形验证码? 验证码(CAPTCHA)是"Completely Automated Public Turing test to tell Computers ...

  9. spring Boot登录验证之验证码 邮箱

    一 验证码 登录login.jsp <%@ page contentType="text/html;charset=UTF-8" language="java&qu ...

  10. Spring Boot + Spring Cloud 实现权限管理系统 后端篇(十七):登录验证码实现(Captcha)

    登录验证码 登录验证是一般系统都会有的功能,验证的方式也多种多样,比如输入式验证码,拖动式验证条,拖动式验证拼图等等. 我们这里先实现常规的输入验证码的方式,右边显示验证码图片,点击可刷新,左边输入验 ...

随机推荐

  1. VMto阿里云的简单过程

    VMto阿里云的简单过程 第一步打开网站 https://smcnext.console.aliyun.com/sourceServers/importMigrationSource?spm=5176 ...

  2. 极简版本Clickhouse监控步骤

    极简版本Clickhouse监控步骤 背景 昨天处理了 鲲鹏920 上面的Clickhouse 的基于Docker的安装与部署 今天想着能够继续处理一下 增加监控信息 能够实现对clickhouse使 ...

  3. [转帖]Oracle的审计

    AUDIT_TRAIL 初始化参数AUDIT_TRAIL用于控制数据库审计,默认值为none. 参数类型: String 默认值: none 允许动态修改: 否 基本参数: 否 语法: AUDIT_T ...

  4. Tidb异名恢复Mysql数据库的过程

    Tidb异名恢复Mysql数据库的过程 背景 先说坑: TiDB备份恢复的方式 1. mysqldump + mysql source 的方式. 2. mydumper + loader tidb 的 ...

  5. [转帖]文件操作之zip、bzip2、gzip、tar命令

    文件操作之zip.bzip2.gzip.tar命令 原创 丁同学19902015-10-15 00:02:51博主文章分类:liunx基础著作权 文章标签linux tarlinux文件压缩linux ...

  6. [转帖]Docker:Python环境Docker镜像瘦身

    https://www.jianshu.com/p/c0ad13e0be85 关键字:Docker,Python 原始镜像 封装一个Python 3.7的环境并且安装Python依赖包实现一个机器学习 ...

  7. [转帖]PCIe信息查询

    https://www.jianshu.com/p/b3a57fcaff8d 查询PCIe设备厂商信息 通过PCIe设备的描述信息进行查询 PCIe设备的描述:Class号.厂商号(vender id ...

  8. [转帖]mysql百万级性能瓶颈-数据库选型

    项目中使用了mysql数据库,但数据量增长太快,不久到了百万级,很快又到表到了千万级,尝试了各种优化方式,最终效果仍难达到秒级响应,那么引发了我关于数据库选型到一些思考. 1.mysql的单表性能瓶颈 ...

  9. 大数据面试题集锦-Hadoop面试题(三)-MapReduce

    你准备好面试了吗?这里有一些面试中可能会问到的问题以及相对应的答案.如果你需要更多的面试经验和面试题,关注一下"张飞的猪大数据分享"吧,公众号会不定时的分享相关的知识和资料. 目录 ...

  10. 升级到win11 22h2的体验

    win11 22h2更稳定了 在win11 22h2发布后没多久,我就升级到了这个版本,截止目前已经使用半个月了,谈谈我的使用感受. 总体要比之前的版本更稳定,表现为笔记本风扇不会突然响,突然卡顿,不 ...