验证码的三个常见漏洞和修复方法
作者:junjie 时间:2023-10-25 17:46:26
把验证码存储在Cookie中
一般来说,我们会把验证码的值用Session存储起来,通过对比用户提交的验证码和Session中的验证码,就可以知道输入是否正确。由于Session会占用服务器资源,我曾经想过是否可以把验证码的值加密后存储在Cookie中。不过事实证明,这只是异想天开罢了。
假设验证码的值是a,通过sha1加密后得到的值为b = sha1(a),并且把b存储在Cookie中。而用户提交的验证码值为c,通过判断sha1(c)是否与b相等,可以知道输入的验证码是否正确。然而,Cookie是受客户端控制的。如果用户事先通过肉眼看到验证码的值是a,又从Cookie中得知此时的加密值为b,那么,他只要在提交前把Cookie的值修改为b,提交的验证码值为a,就可以永远通过验证。
没有进行非空判断
这种情况可以直接用代码来说明:
if (Request["captcha"] == Session["captcha"] as string)
{
// 验证通过,继续操作
}
假设用户绕过了系统提供的表单直接提交数据,此时验证码还没生成,Session["captcha"]为空。用户不提交验证码时,Request["captcha"]也为空。于是,验证通过了。
要解决这个问题,其实只要加个非空判断就可以了:
if (!String.IsNullOrEmpty(Request["captcha"]) &&
Request["captcha"] == Session["captcha"] as string)
{
// 验证通过,继续操作
}
没有及时销毁验证码
使用验证码要遵循一个原则,在一次比对之后,无论用户输入正确与否,都要立刻将验证码销毁。
如果不这样做,就可以出现以下情况:
假设用户输入错误,且验证码没有重新生成,那么他就可以一直尝试,直到正确为止。虽然机器对图片的一次性识别率比较低,但是,如果同一张图片你给它无限次机会的话,它还是可以识别出来的。
假设用户输入成功,且验证码没有销毁,那么在Session过期之前,他就可以一直用这个验证码通过验证。
标签:验证码,漏洞,修复
![](/images/zang.png)
![](/images/jiucuo.png)
猜你喜欢
Android实现点击获取验证码60秒后重新获取功能
2021-09-21 22:42:01
![](https://img.aspxhome.com/file/2023/1/109211_0s.gif)
Spring Bean生命周期之BeanDefinition的合并过程详解
2023-11-29 02:50:35
Android简单音乐播放实例
2023-04-13 05:49:55
![](https://img.aspxhome.com/file/2023/4/138364_0s.png)
Java爬虫实现爬取京东上的手机搜索页面 HttpCliient+Jsoup
2023-02-19 23:22:37
![](https://img.aspxhome.com/file/2023/1/78851_0s.jpg)
Java利用蒙特卡洛方法求解圆周率π值
2023-04-10 14:10:28
![](https://img.aspxhome.com/file/2023/3/91123_0s.png)
C#构建树形结构数据(全部构建,查找构建)
2022-07-22 12:22:52
![](https://img.aspxhome.com/file/2023/3/81133_0s.png)
Kotlin Option与Either及Result实现异常处理详解
2022-03-31 17:33:18
![](https://img.aspxhome.com/file/2023/8/138158_0s.png)
使用@Validated 和 BindingResult 遇到的坑及解决
2022-12-18 20:36:28
![](https://img.aspxhome.com/file/2023/3/64223_0s.png)
MyBatis源码浅析(一)开篇
2022-09-28 03:28:24
Java中final与继承操作实例分析
2023-09-14 08:56:02
![](https://img.aspxhome.com/file/2023/4/114044_0s.png)
C#取得Web程序和非Web程序的根目录的N种取法总结
2023-07-16 07:37:32
Android ProgressDialog使用总结
2023-07-10 22:16:33
android TextView加下划线的方法
2023-09-11 01:12:36
C#中DataTable和List互转的示例代码
2022-08-25 21:40:06
基于StreamRead和StreamWriter的使用(实例讲解)
2022-09-11 22:12:36
使用mybatis插件PageHelper实现分页效果
2023-03-29 15:12:03
![](https://img.aspxhome.com/file/2023/1/65271_0s.jpg)
Android文件下载进度条的实现代码
2023-02-14 20:08:24
C#中的Socket编程详解
2021-10-24 01:25:00
![](https://img.aspxhome.com/file/2023/4/88374_0s.gif)
c语言switch反汇编的实现
2023-06-29 03:38:17
![](https://img.aspxhome.com/file/2023/6/99286_0s.png)
Android仿美团下拉菜单(商品选购)实例代码
2023-05-07 06:03:34
![](https://img.aspxhome.com/file/2023/1/137111_0s.gif)