svg-captcha生成验证码以及验证

生成验证码

构建简单的node服务器

  • 新建serve文件夹
  • 进入 serve文件夹初始化npm项目 npm init
  • 新建server.js文件
const express = require('express');
const http = require('http');
const app = express();
const server = http.createServer(app);
const svgCaptcha = require('svg-captcha');  //验证码插件

//设置允许跨域访问
app.all("*", function(req, res, next) {
  //设置允许跨域的域名,*代表允许任意域名跨域
  res.header("Access-Control-Allow-Origin", "*");
  //允许的header类型
  res.header("Access-Control-Allow-Headers", "content-type");
  //跨域允许的请求方式 
  res.header("Access-Control-Allow-Methods", "DELETE,PUT,POST,GET,OPTIONS");
  if (req.method.toLowerCase() == 'options')
    res.send(200);  //让options尝试请求快速结束
  else
    next();
})
// 获取验证码接口
app.get('/getCodeImg', (req, res) => {
  // 字母验数字证码
  // let codeConfig = {
  //     size: 4,// 验证码长度
  //     ignoreChars: '0o1i', // 验证码字符中排除 0o1i
  //     noise: 5, // 干扰线条的数量
  //     width: 100, //验证码宽度
  //     height: 40, //验证码高度
  //     fontSize: 40,   //字体大小
  //     color: true,    //开启字体颜色
  //     background: '#cc9966',//背景颜色
  //     // charPreset:'abcd123456789', //随机预设字符
  // }
  // let captcha = svgCaptcha.create(codeConfig); //验证码

  // 数学表算式验证码
  let codeConfig = {
    mathMin: 1, //数学表达式的最小值
    mathMax: 20, // 数学表达式的最大值
    mathOperator: '+', // 使用的运算符:+、-或+-(用于随机的+或-)
    noise: 5, // 干扰线条的数量
    width: 100, //验证码宽度
    height: 40, //验证码高度
    fontSize: 40,   //字体大小
    color: true,    //开启字体颜色
    background: '#cc9966',//背景颜色
  }
  let captcha = svgCaptcha.createMathExpr(codeConfig); //算式验证码
  //captcha.text 验证码的文字码
  //captcha.data 验证码图片的svg数据
  res.json({
    status: 200,
    data: captcha.data
  })
});

server.listen(3000, () => {
  console.log("server is up and running on  http://127.0.0.1:3000");
});
  • 安装express包
    npm i express -s
  • 安装svg-captcha包
    npm i svg-captcha -s
  • 启动服务器
    node server.js

在serve文件同级目录新建客户端网页 client.html

<!DOCTYPE html>
<html lang="en">

<head>
  <meta charset="UTF-8">
  <meta http-equiv="X-UA-Compatible" content="IE=edge">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>验证码</title>
</head>
<style>
  .main {
    width: 1000px;
    margin: 0 auto;
    padding-top: 100px;
  }

  .code {
    height: 40px;
    line-height: 40px;
    padding: 0 4px;
    box-sizing: border-box;
    outline: 0;
    font-size: 16px;
  }

  .code-img {
    vertical-align: middle;
    margin-left: 20px;
  }

  .btn {
    cursor: pointer;
    color: #fff;
    background-color: #409eff;
    border: 1px solid #409eff;
    text-align: center;
    box-sizing: border-box;
    outline: 0;
    margin: 0;
    font-weight: 500;
    padding: 12px 20px;
    font-size: 14px;
    border-radius: 4px;
  }
</style>

<body>
  <div class="main">
    <div>
      <input type="text" class="code" id="code">
      <sapn class="code-img" id="codeImg" onclick="getCodeImg()"></sapn>
    </div>
    <button class="btn" >验证</button>
  </div>
</body>
</html>
<script>
  window.onload = function() {
    getCodeImg();
  }
   async function getCodeImg() {
    // 请求接口获取验证码数据
    // fetch 默认是get请求
    let response = await fetch('http://127.0.0.1:3000/getCodeImg');
    response.json().then(res => {
      document.querySelector('#codeImg').innerHTML = res.data; //渲染验证码图片
    })
  }
</script>

这时候运行网页就可以看到验证码

验证

在验证之前我们要先将验证码的答案保存起来,为了确保验证码答案不会被另一个浏览器的验证码覆盖,使用fingerprint2插件获取浏览器的指纹ID

修改客户端网页代码

  • 引用 fingerprint2
<script src="https://lib.baomitu.com/fingerprintjs2/2.1.5/fingerprint2.js"></script>
  • 获取浏览器的指纹ID
 // 获取浏览器指纹
  function getFingerprint() {
    // 因为是异步的所以使用 Promise
    return new Promise((resolve, reject) => {
      // 浏览器指纹
      Fingerprint2.get((components) => {
        const values = components.map(component => component.value);
        const murmur = Fingerprint2.x64hash128(values.join(''), 31); // 生成浏览器指纹
        resolve(murmur)
      });
    })
  }
  • 将指纹ID作为获取获取验证码接口的参数
  let browserId = ''; //定义浏览器id全局变量
  window.onload = function() {
    getFingerprint().then(res => {
      browserId = res;
      getCodeImg();
    })
  }
   async function getCodeImg() {
    // 请求接口获取验证码数据
    // fetch 默认是get请求
    let response = await fetch('http://127.0.0.1:3000/getCodeImg?browserId=' + browserId);
    response.json().then(res => {
      document.querySelector('#codeImg').innerHTML = res.data;  //渲染验证码图片
    })
  }

服务端代码修改

  • 因为没有使用数据库,所以我们将数据保存在本地json文件
  • 在server.js同级目录创建json文件 db.json
const fs = require('fs'); //引入 fs 核心模块
const dbJson = './db.json'; //文件路径
  • 在getCodeImg接口添加代码
 let browserId = req.query.browserId; // 获取浏览器指纹id参数
  fs.readFile(dbJson, function(err, data) {
    if (err) {
      return console.error(err);
    }
    //将二进制的数据转换为字符串
    let str = data.toString();
    let verificationCode = [];
    //将字符串转换为json对象
    if (str) {
      verificationCode = JSON.parse(str);
    }
    let index = verificationCode.findIndex(item => item.browserId === browserId)
    console.log(str, 'str')
    console.log(index, 'index')
    if (index > -1) {
      verificationCode[index].answer = captcha.text
    } else {
      let obj = {
        browserId: browserId,
        answer: captcha.text
      }
      verificationCode.push(obj);//将传来的对象push进数组对象中
    }
    let dataStr = JSON.stringify(verificationCode);//把json对象转换成字符串重新写入json文件中
    fs.writeFile(dbJson, dataStr, function(err) {
      if (err) {
        console.error(err);
      }
    })
  })
  • 编写验证接口
app.post('/validationCode', (req, res) => {
  var data = '';
  req.on('data', function(chunk) {
    data += chunk;
  });
  req.on('end', function() {
    data = decodeURI(data);
    var dataObject = JSON.parse(data);
    fs.readFile(dbJson, function(err, data) {
      if (err) {
        return console.error(err);
      }
      let verificationCode = JSON.parse(data.toString()) || [];
      let captcha = verificationCode.filter(item => item.browserId === dataObject.browserId)[0]
      if (dataObject.code === captcha.answer) {
        res.json({
          status: 200,
          msg: '验证码正确',
        })
      } else {
        res.json({
          status: 201,
          msg: '验证码错误'
        })
      }
    })
  });
});

修改ndoe代码要重启服务才会生效

客户端验证按钮

  // 验证
  document.querySelector('#verificationBtn').addEventListener('click', async function() {
    let code = document.querySelector('#code').value
    let param = {
      browserId: browserId,
      code: code
    }
    let response = await fetch('http://127.0.0.1:3000/validationCode', {
      method: "POST",
      body: JSON.stringify(param)
    })
    response.json().then(res => {
      alert(res.msg)
    })
  })

最终效果如下

在这里插入图片描述

源码地址

https://gitee.com/swfcode/code-img.git

  • 1
    点赞
  • 10
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
在 Koa2 中使用 svg-captcha 生成验证码可以按照以下步骤进行: 1. 安装 svg-captcha 和 koa-svgrouter 模块 ```bash npm install svg-captcha koa-svgrouter --save ``` 2. 在 Koa2 应用中引入相关模块 ```javascript const Koa = require('koa'); const Router = require('koa-router'); const svgrouter = require('koa-svgrouter'); const svgCaptcha = require('svg-captcha'); const app = new Koa(); const router = new Router(); ``` 3. 设置路由,生成验证码 ```javascript router.get('/captcha', async (ctx, next) => { const captcha = svgCaptcha.create(); ctx.session.captcha = captcha.text; ctx.type = 'svg'; ctx.body = captcha.data; }); ``` 4. 添加 SVG 路由 ```javascript app.use(svgrouter('/captcha/:id', { useSession: true, sessionName: 'captcha' })); ``` 5. 在需要使用验证码的地方,可以通过如下代码获取验证码图片 ```html <img src="/captcha/1" /> ``` 注意,上述代码中的数字 1 是路由参数,可以自行设置。 6. 验证验证码 在需要验证验证码的地方,可以通过如下代码获取用户输入的验证码,并与之前生成验证码进行比较。 ```javascript const userCaptcha = ctx.request.body.captcha; if (userCaptcha.toLowerCase() === ctx.session.captcha.toLowerCase()) { // 验证码输入正确 } else { // 验证码输入错误 } ``` 以上就是使用 svg-captcha 生成验证码的基本步骤。需要注意的是,在生成验证码验证验证码时都需要使用到 Koa2 的 session 功能,因此需要在应用中添加相关中间件。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值