共计 2946 个字符,预计需要花费 8 分钟才能阅读完成。
此处应用 kaptcha 依赖实现图形验证码校验性能
引入依赖
<dependency>
<groupId>com.github.penggle</groupId>
<artifactId>kaptcha</artifactId>
<version>2.3.2</version>
</dependency>
Kaptcha 相干配置
-
配置 kaptcha 实例
@Bean public Producer captcha() { // 配置图形验证码的基本参数 Properties properties = new Properties(); // 图片宽度 properties.setProperty("kaptcha.image.width", "150"); // 图片长度 properties.setProperty("kaptcha.image.height", "50"); // 字符集 properties.setProperty("kaptcha.textproducer.char.string", "0123456789"); // 字符长度 properties.setProperty("kaptcha.textproducer.char.length", "4"); Config config = new Config(properties); // 应用默认的图形验证码实现,当然也能够自定义实现 DefaultKaptcha defaultKaptcha = new DefaultKaptcha(); defaultKaptcha.setConfig(config); return defaultKaptcha; }
-
配置 kaptcha 路由
@Controller public class CaptchaController { @Autowired private Producer captchaProducer; @GetMapping("/captcha.jpg") public void getCaptcha(HttpServletRequest request, HttpServletResponse response) throws IOException { // 设置内容类型 response.setContentType("image/jpeg"); // 创立验证码文本 String capText = captchaProducer.createText(); // 将验证码文本设置到 session request.getSession().setAttribute("captcha", capText); // 创立验证码图片 BufferedImage bi = captchaProducer.createImage(capText); // 获取响应输入流 ServletOutputStream out = response.getOutputStream(); // 将图片验证码数据写到响应输入流 ImageIO.write(bi, "jpg", out); // 推送并敞开响应输入流 try {out.flush(); } finally {out.close(); } } }
-
在 security config 办法中对所有 kaptcha 申请放行
.antMatchers("/app/api/**", "/captcha.jpg").permitAll()
配置过滤器
security 的 过滤器链 示意所有的过滤器性能,(Security 全局配置中的 HttpSecurity 即示意配置了一个过滤器链)。诸如 CSRF、formLogin 等等。每一项 httpsecurity 的配置即示意一个过滤器链中的过滤器配置。
这里波及到的是,在 Security 框架提供的过滤器之外,自定义的过滤器。
留神:第七行需改成我的项目对应的 login 路由。
public class VerificationCodeFilter extends OncePerRequestFilter {
@Override
protected void doFilterInternal(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, FilterChain filterChain) throws ServletException, IOException {System.out.println("into filter");
// 非登录申请不校验验证码
if (!"/customlogin".equals(httpServletRequest.getRequestURI())) {filterChain.doFilter(httpServletRequest, httpServletResponse);
} else {verificationCode(httpServletRequest);
filterChain.doFilter(httpServletRequest, httpServletResponse);
}
}
public void verificationCode (HttpServletRequest httpServletRequest) throws VerificationCodeException {String requestCode = httpServletRequest.getParameter("captcha");
HttpSession session = httpServletRequest.getSession();
String savedCode = (String) session.getAttribute("captcha");
System.out.println("--->" + savedCode);
if (!StringUtils.isEmpty(savedCode)) {
// 顺手革除验证码,不论是失败还是胜利,所以客户端应在登录失败时刷新验证码
session.removeAttribute("captcha");
}
// 校验不通过抛出异样
if (StringUtils.isEmpty(requestCode) || StringUtils.isEmpty(savedCode) || !requestCode.equals(savedCode)) {throw new VerificationCodeException();
}
}
}
抛出的异样:
public class VerificationCodeException extends AuthenticationException {public VerificationCodeException () {super("图形验证码校验失败");
}
}
配置页面
表单中增加以下内容即可
<div>
<!-- 新增图形验证码的输入框 -->
<input type="text" name="captcha" placeholder="captcha" />
<!-- 图片指向图形验证码 API -->
<img src="/captcha.jpg" alt="captcha" height="50px" width="150px" style="margin-left: 20px;">
</div>
正文完
发表至: spring-security
2020-11-02