Springboot 驗證碼實現

近期在閱讀一份開源專案,將其中的驗證碼功能抽取出來,與讀者一起分享。

實現框架:

springboot

kaptcha

redis

base64

下面是實現步驟:

pom匯入jar包;

驗證碼(數字和字母)配置;

應用。生成驗證碼後,依據使用者輸入的資訊,存入redis,並設定2分鐘內有效。,,每一個驗證碼的生成需要攜帶一個唯一編碼保證唯一性。

1、匯入jar包

<!—— 驗證碼 ——> com。github。penggle kaptcha 2。3。2

Springboot 驗證碼實現

驗證碼生成與驗證碼圖片生成

2、驗證碼配置

@Configurationpublic class CaptchaConfig{ @Bean(name = “captchaProducer”) public DefaultKaptcha getKaptchaBean() { DefaultKaptcha defaultKaptcha = new DefaultKaptcha(); Properties properties = new Properties(); // 是否有邊框 預設為true 我們可以自己設定yes,no properties。setProperty(KAPTCHA_BORDER, “yes”); // 驗證碼文字字元顏色 預設為Color。BLACK properties。setProperty(KAPTCHA_TEXTPRODUCER_FONT_COLOR, “black”); // 驗證碼圖片寬度 預設為200 properties。setProperty(KAPTCHA_IMAGE_WIDTH, “160”); // 驗證碼圖片高度 預設為50 properties。setProperty(KAPTCHA_IMAGE_HEIGHT, “60”); // 驗證碼文字字元大小 預設為40 properties。setProperty(KAPTCHA_TEXTPRODUCER_FONT_SIZE, “38”); // KAPTCHA_SESSION_KEY properties。setProperty(KAPTCHA_SESSION_CONFIG_KEY, “kaptchaCode”); // 驗證碼文字字元長度 預設為5 properties。setProperty(KAPTCHA_TEXTPRODUCER_CHAR_LENGTH, “4”); // 驗證碼文字字型樣式 預設為new Font(“Arial”, 1, fontSize), new Font(“Courier”, 1, fontSize) properties。setProperty(KAPTCHA_TEXTPRODUCER_FONT_NAMES, “Arial,Courier”); // 圖片樣式 水紋com。google。code。kaptcha。impl。WaterRipple 魚眼com。google。code。kaptcha。impl。FishEyeGimpy 陰影com。google。code。kaptcha。impl。ShadowGimpy properties。setProperty(KAPTCHA_OBSCURIFICATOR_IMPL, “com。google。code。kaptcha。impl。ShadowGimpy”); Config config = new Config(properties); defaultKaptcha。setConfig(config); return defaultKaptcha; } @Bean(name = “captchaProducerMath”) public DefaultKaptcha getKaptchaBeanMath() { DefaultKaptcha defaultKaptcha = new DefaultKaptcha(); Properties properties = new Properties(); // 是否有邊框 預設為true 我們可以自己設定yes,no properties。setProperty(KAPTCHA_BORDER, “yes”); // 邊框顏色 預設為Color。BLACK properties。setProperty(KAPTCHA_BORDER_COLOR, “105,179,90”); // 驗證碼文字字元顏色 預設為Color。BLACK properties。setProperty(KAPTCHA_TEXTPRODUCER_FONT_COLOR, “blue”); // 驗證碼圖片寬度 預設為200 properties。setProperty(KAPTCHA_IMAGE_WIDTH, “160”); // 驗證碼圖片高度 預設為50 properties。setProperty(KAPTCHA_IMAGE_HEIGHT, “60”); // 驗證碼文字字元大小 預設為40 properties。setProperty(KAPTCHA_TEXTPRODUCER_FONT_SIZE, “35”); // KAPTCHA_SESSION_KEY properties。setProperty(KAPTCHA_SESSION_CONFIG_KEY, “kaptchaCodeMath”); // 驗證碼文字生成器 properties。setProperty(KAPTCHA_TEXTPRODUCER_IMPL, “com。ruoyi。framework。config。KaptchaTextCreator”); // 驗證碼文字字元間距 預設為2 properties。setProperty(KAPTCHA_TEXTPRODUCER_CHAR_SPACE, “3”); // 驗證碼文字字元長度 預設為5 properties。setProperty(KAPTCHA_TEXTPRODUCER_CHAR_LENGTH, “6”); // 驗證碼文字字型樣式 預設為new Font(“Arial”, 1, fontSize), new Font(“Courier”, 1, fontSize) properties。setProperty(KAPTCHA_TEXTPRODUCER_FONT_NAMES, “Arial,Courier”); // 驗證碼噪點顏色 預設為Color。BLACK properties。setProperty(KAPTCHA_NOISE_COLOR, “white”); // 干擾實現類 properties。setProperty(KAPTCHA_NOISE_IMPL, “com。google。code。kaptcha。impl。NoNoise”); // 圖片樣式 水紋com。google。code。kaptcha。impl。WaterRipple 魚眼com。google。code。kaptcha。impl。FishEyeGimpy 陰影com。google。code。kaptcha。impl。ShadowGimpy properties。setProperty(KAPTCHA_OBSCURIFICATOR_IMPL, “com。google。code。kaptcha。impl。ShadowGimpy”); Config config = new Config(properties); defaultKaptcha。setConfig(config); return defaultKaptcha; }}

驗證碼文字生成器

public class KaptchaTextCreator extends DefaultTextCreator{ private static final String[] CNUMBERS = “0,1,2,3,4,5,6,7,8,9,10”。split(“,”); @Override public String getText() { Integer result = 0; Random random = new Random(); int x = random。nextInt(10); int y = random。nextInt(10); StringBuilder suChinese = new StringBuilder(); int randomoperands = (int) Math。round(Math。random() * 2); if (randomoperands == 0) { result = x * y; suChinese。append(CNUMBERS[x]); suChinese。append(“*”); suChinese。append(CNUMBERS[y]); } else if (randomoperands == 1) { if (!(x == 0) && y % x == 0) { result = y / x; suChinese。append(CNUMBERS[y]); suChinese。append(“/”); suChinese。append(CNUMBERS[x]); } else { result = x + y; suChinese。append(CNUMBERS[x]); suChinese。append(“+”); suChinese。append(CNUMBERS[y]); } } else if (randomoperands == 2) { if (x >= y) { result = x - y; suChinese。append(CNUMBERS[x]); suChinese。append(“-”); suChinese。append(CNUMBERS[y]); } else { result = y - x; suChinese。append(CNUMBERS[y]); suChinese。append(“-”); suChinese。append(CNUMBERS[x]); } } else { result = x + y; suChinese。append(CNUMBERS[x]); suChinese。append(“+”); suChinese。append(CNUMBERS[y]); } suChinese。append(“=?@” + result); return suChinese。toString(); }}

3、實現方式

採用使用到數字驗證碼 和 字元驗證碼,最後採用base64字串返回

@RestControllerpublic class CaptchaController { @Resource(name = “captchaProducer”) private Producer captchaProducer; @Resource(name = “captchaProducerMath”) private Producer captchaProducerMath; @Autowired private RedisCache redisCache; // 驗證碼型別 @Value(“${ruoyi。captchaType}”) private String captchaType; /** * 生成驗證碼 */ @GetMapping(“/captchaImage”) public AjaxResult getCode(HttpServletResponse response) throws IOException { // 儲存驗證碼資訊 String uuid = IdUtils。simpleUUID(); String verifyKey = Constants。CAPTCHA_CODE_KEY + uuid; String capStr = null, code = null; BufferedImage image = null; // 生成驗證碼 if (“math”。equals(captchaType)) { String capText = captchaProducerMath。createText(); capStr = capText。substring(0, capText。lastIndexOf(“@”)); code = capText。substring(capText。lastIndexOf(“@”) + 1); image = captchaProducerMath。createImage(capStr); } else if (“char”。equals(captchaType)) { capStr = code = captchaProducer。createText(); image = captchaProducer。createImage(capStr); } redisCache。setCacheObject(verifyKey, code, Constants。CAPTCHA_EXPIRATION, TimeUnit。MINUTES); // 轉換流資訊寫出 FastByteArrayOutputStream os = new FastByteArrayOutputStream(); try { ImageIO。write(image, “jpg”, os); } catch (IOException e) { return AjaxResult。error(e。getMessage()); } AjaxResult ajax = AjaxResult。success(); ajax。put(“uuid”, uuid); ajax。put(“img”, Base64。encode(os。toByteArray())); return ajax; }}

4、總結:

透過開源專案的閱讀,對專案上的實現的細節有有些新的認知。