应抛出 CaptchaMismatchException 异常,继承 RuntimeException,用于标识验证码错误或过期;校验时需从缓存取值、判空、忽略大小写比对;全局用 @ControllerAdvice 统一返回 400 响应。

在 Java Web 应用中,当用户提交的验证码(Captcha)与服务端缓存的值不匹配,或验证码已过期时,应抛出 CaptchaMismatchException 异常,这是一种典型的业务校验异常,用于明确区分验证码错误与其他系统异常。
定义 CaptchaMismatchException
建议继承 RuntimeException,避免强制上层处理,符合表单校验失败的语义:
<font size="2"><pre class="brush:php;toolbar:false;">public class CaptchaMismatchException extends RuntimeException {<br> public CaptchaMismatchException() {<br> super("验证码错误或已过期");<br> }<br><br> public CaptchaMismatchException(String message) {<br> super(message);<br> }<br>}
校验逻辑中主动抛出
在登录、注册等接口中,获取用户提交的验证码后,需比对缓存值并检查时效性。不匹配或超时即抛出异常:
- 从 Session 或 Redis 中取出原始验证码(注意:取完可立即删除,实现“一次性”)
- 判断是否为空(已使用或过期)→ 抛出
CaptchaMismatchException - 忽略大小写比对用户输入,避免因大小写导致误判
- 比对失败 → 抛出
CaptchaMismatchException
全局异常处理器统一响应
配合 Spring MVC 的 @ControllerAdvice,将该异常转为标准错误响应:
立即学习“Java免费学习笔记(深入)”;
<font size="2"><pre class="brush:php;toolbar:false;">@ExceptionHandler(CaptchaMismatchException.class)<br>public ResponseEntity<ApiResponse> handleCaptchaMismatch(CaptchaMismatchException e) {<br> return ResponseEntity.badRequest().body(<br> ApiResponse.error(400, "验证码不正确,请重新输入")<br> );<br>}
这样前端能收到明确的状态码(如 400)和提示,便于统一提示用户刷新验证码。
避免常见陷阱
- 不要用
NullPointerException或IllegalArgumentException替代 —— 语义不清,不利于日志归类和监控 - 不要在捕获后静默吞掉异常或返回模糊提示(如“请求失败”),影响用户体验
- Redis 缓存验证码时务必设置合理过期时间(如 2~5 分钟),并启用 key 失效监听(非必需,但有助于清理)


















