云计算百科
云计算领域专业知识百科平台

Spring Boot + Vue + Uniapp 企业登录安全:图形/滑块验证码 + 短信验证码 + Redis 限频实战

Spring Boot + Vue + Uniapp 企业登录安全:图形/滑块验证码 + 短信验证码 + Redis 限频实战

一句话:密码只是第一道门;验证码挡机器、短信验真人、Redis 控频率、日志留痕迹——四层叠在一起,登录页才敢对外网开放。

登录安全全景

开源仓库:GitCode · RuoyiOffice|AtomGit · RuoyiOffice


先看登录页长什么样

多租户、账号密码、手机号登录、扫码与第三方入口——企业登录从来不是「两个输入框 + 按钮」。

PC 登录页

在这里插入图片描述

本机开发环境常会关掉图形验证码方便调试;生产必须打开。下文按「打开验证码后的真实链路」讲。


为什么企业登录不能只校验密码?

攻击面只靠密码会怎样企业常见对策
撞库 / 暴力破解 弱口令几分钟试完 图形或滑块验证码 + 失败锁定
短信轰炸 接口被刷成运营账单 场景码 + 日上限 + IP/手机号频控
验证码复用 截到一次短信反复登录 核销即失效(Redis 标记 used)
审计缺失 出事对不上人 登录成功/失败写登录日志
多端入口 只做 PC、忘了 App 同一套 Auth API,前端换壳

RuoyiOffice 管理端认证集中在 系统模块 Auth 服务:账号登录、短信登录、发送短信、刷新 Token、登出共用一套 Token 发放逻辑。


整体架构:四层防御

┌──────────────── Vue3 / UniApp 登录页 ────────────────┐
│ 租户选择 │ 账号密码 │ 滑块/图形 │ 手机号+短信 │ 扫码… │
└────────────┬───────────────┬───────────────┬─────────┘
│ │ │
POST /login POST /send-sms-code POST /sms-login
│ │ │
▼ ▼ ▼
┌──────────────── Spring Boot 3 AuthService ─────────────┐
│ ① 验证码开关? → CaptchaService.verification │
│ ② 认证用户(密码 / 短信码) │
│ ③ 写登录日志(成功/失败原因) │
│ ④ 发 OAuth2 AccessToken + RefreshToken │
└────────────┬───────────────┬───────────────────────────┘
│ │
▼ ▼
Redis(AJ-Captcha) Redis(短信码 + 频控)


第一层:图形 / 滑块验证码(挡机器)

设计要点

  • 可配置开关:开发关掉、生产打开;关闭时校验直接放行,避免联调被滑块卡住。
  • 校验发生在密码校验之前:验证码错了不要去撞数据库密码,既省资源,也少暴露「用户是否存在」的时序差异(仍建议错误文案统一)。
  • 失败也写登录日志:原因记为「验证码错误」,方便安全同学看爆破曲线。
  • 实现可插拔:项目里用 AJ-Captcha + Redis 存挑战态;也可换成纯图形字、Turnstile 等,只要登录 VO 带上 captchaVerification(或你们约定的字段)。
  • 伪代码(对应真实服务结构)

    void validateCaptcha(LoginReq req) {
    if (!captchaEnable) {
    return; // 开发环境
    }
    ResponseModel r = captchaService.verification(req.getCaptchaVerification());
    if (!r.isSuccess()) {
    createLoginLog(..., CAPTCHA_CODE_ERROR);
    throw businessException(r.getMessage());
    }
    }

    AuthLoginResp login(LoginReq req) {
    validateCaptcha(req); // 先挡机器
    AdminUser user = authenticate(req.getUsername(), req.getPassword());
    return createTokenAfterLoginSuccess(user);
    }

    前端配合

    • 滑块成功后拿到 captchaVerification,和账号密码一起提交。
    • 验证码失败:刷新挑战,不要清空密码(体验友好)。
    • 记住:验证码是一次性挑战,刷新页面必须重新滑。

    生产建议

    项建议
    开关 配置中心 / 环境变量,禁止写死在前端
    Redis 与业务 Redis 可同实例,建议独立 key 前缀
    难度 对公网管理端用滑块;内网可降级图形字
    CDN 验证码静态资源走 HTTPS,防混合内容

    第二层:短信验证码(验真人 + 无密码登录)

    账号密码适合办公电脑;手机号登录适合外勤、忘记密码、高管临时看审批。

    发送链路

    前端输入手机号 + 场景码(如后台登录)

    AuthController.sendSmsCode

    SmsCodeService.createSmsCode
    ├─ 校验场景是否启用
    ├─ 查最近一条:未过期且间隔 < 频率 → 拒绝(防连点)
    ├─ 今日已发条数 ≥ 日上限 → 拒绝(防轰炸)
    ├─ 生成 4~6 位码写入记录表 / Redis
    └─ 调短信通道发送

    登录链路

    smsLogin(mobile, code)
    → 校验场景 + 核销验证码(标记已使用)
    → 按手机号找用户(不存在可按产品策略拒绝或自动注册,管理端通常拒绝)
    → 同账号登录一样发 Token + 写成功日志

    频控参数怎么定?

    参数经验值说明
    发送间隔 60s 小于间隔直接拒,前端倒计时对齐
    日上限 10~20 / 手机号 / 场景 按短信成本调
    有效期 5~10 分钟 过期自动失效
    核销 成功登录即 used 禁止「一条短信登三次」

    场景码很重要:同一手机号「登录」和「改密」应分开计数,避免改密把登录额度耗光。


    第三层:Token 与登出

    验证码和短信只解决「你是谁」;会话靠 AccessToken:

    • 登录成功 → createAccessToken(绑定用户类型、客户端)
    • 刷新 → refreshToken
    • 登出 → 删 Token + 写登出日志

    前端要做:401 统一跳登录、多页签共享 Token 策略、敏感操作可二次校验短信。


    第四层:失败日志与运营看板

    在这里插入图片描述

    至少区分这些结果枚举(名称可自定):

    • 验证码错误
    • 账号或密码错误
    • 用户禁用
    • 短信码错误 / 过期
    • 登录成功

    安全同学按小时聚合「验证码错误」和「密码错误」:前者暴涨像脚本,后者暴涨像撞库。


    和「限流 / 幂等」怎么分工?

    能力解决什么不解决什么
    验证码 机器批量试 同一真人慢速撞库(需锁定)
    短信频控 短信账单与骚扰 密码爆破
    网关限流 单 IP QPS 分布式代理池
    账号锁定 连续密码错误 验证码被刷(应在验证码层挡)

    建议:验证码错误不计入密码错误次数,否则攻击者可故意输错验证码锁死管理员(或反过来:只计密码错误,验证码失败单独告警)。


    前端多入口:一套 API,多种壳

    入口主要校验
    账号密码 验证码 + 密码
    手机号登录 短信码(可再加图形码防刷发送接口)
    扫码 二维码票据轮询 + 已登录端确认
    第三方 OAuth 回调绑定本系统用户

    PC 与 App 共用后端 Auth;差别只在 UI 与深链。移动端也要带租户(或企业码),否则多租户会串。


    配置清单(上线前核对)

    • 生产打开图形/滑块验证码
    • Redis 可达,验证码与短信 key 不冲突
    • 短信通道签名、模板已审;场景码已配置
    • 发送间隔、日上限与产品文案一致
    • 登录失败日志入库且可查
    • HTTPS;Cookie/Token 不落明文日志
    • 开发环境开关与生产隔离(别把生产关掉图方便)

    FAQ

    Q1:开发环境验证码太烦怎么办? A:用配置关闭校验;切勿把关闭逻辑写进前端「隐藏滑块但仍提交空串」——后端一开就全员登录失败。

    Q2:短信接口要不要再套一层图形码? A:公网强烈建议。否则脚本可绕过登录页直接打 send-sms-code。

    Q3:验证码存 DB 还是 Redis? A:挑战态、短 TTL 优先 Redis;审计流水可落 DB。短信「今日条数」可用记录表 count,也可用 Redis INCR + 次日过期。

    Q4:多租户下验证码是否按租户隔离? A:挑战本身可不绑租户,但登录必须先解析租户,再查该租户用户;短信模板也可按租户品牌定制。

    Q5:和注册、忘记密码如何复用? A:复用 SmsCodeService,换场景码与模板;不要复用「登录成功发 Token」那段到注册未完成状态。


    和 RuoyiOffice 的对应关系

    能力开源中的位置(概念)
    账号 / 短信登录 API 系统模块 AuthController
    验证码校验与开关 AuthService + Captcha 配置
    AJ-Captcha + Redis Framework Captcha 自动配置
    短信创建 / 频控 / 核销 SmsCodeService
    PC 登录页 web-antd /auth/login
    App 登录 UniApp 登录页

    完整后端:GitCode / AtomGit 前端:GitCode · vben 移动端:GitCode · uniapp


    延伸阅读

    • Spring Boot 3 + Vue3 企业级 RBAC
    • BPM 任务操作按钮设计
    • 产品向:何时该上 OA、AI 二开主源码等文,见专栏同系列

    总结

    企业登录安全是产品能力,不是装饰:

  • 验证码挡机器,且可按环境开关
  • 短信验真人,频控 + 核销缺一不可
  • Token 会话与登录日志构成审计闭环
  • PC / App / 第三方共用 Auth,前端只换壳
  • 下一篇我们换业务视角:审批单如何驱动人事主数据(入职建档、转正改状态),以及为什么「状态更新」和「建档」必须拆事务。


    ⭐ GitCode · AtomGit 点星,夏日活动攒积分。 在线体验:https://www.ruoyioffice.com 商业版源码授权:https://www.ruoyioffice.com/contact· 企业微信 17156169080


    关键词:Spring Boot 3 登录安全、滑块验证码、短信验证码、Redis 限频、Vue3 登录页、多租户认证、OAuth2 Token

    赞(0)
    未经允许不得转载:网硕互联帮助中心 » Spring Boot + Vue + Uniapp 企业登录安全:图形/滑块验证码 + 短信验证码 + Redis 限频实战
    分享到: 更多 (0)

    评论 抢沙发

    评论前必须登录!