1. 程式人生 > >JCaptcha驗證碼工具的使用

JCaptcha驗證碼工具的使用

JCaptcha是Java的驗證碼生成、效驗工具,可以提供驗證碼的字型、文字裝飾等功能

其maven依賴為:

<dependency>
    <groupId>com.octo.captcha</groupId>
    <artifactId>jcaptcha</artifactId>
    <version>1.0</version>
</dependency>

但是倉庫配置上好像有點問題,我配了好幾次倉庫都不成功,後來再github上找到了原始碼,本地install成功,才可以使用

github地址:

https://github.com/svn2github/jcaptcha

下載原始碼,clean->compile->install,發現錯誤,依賴找不到,發現是父pom中倉庫配置的問題,改為:

<repositories>
        <repository>
            <id>3rd-party</id>
            <name>Repository for 3rd-party artifacts</name>
            <url>https://maven.atlassian.com/3rdparty/</url>
            <releases>
                <enabled>true</enabled>
            </releases>
            <snapshots>
                <enabled>false</enabled>
            </snapshots>
        </repository>
    </repositories>

再次編譯安裝,發現一個com.sun.xxxxxxx包不存在的問題,因為這個包程式碼太老,所以編譯級別有問題,點開問題程式碼,發現所有問題程式碼都在一個main方法中,刪除這個類即可,這次install成功

本地安裝之後,即可在自己專案中使用

下面貼出spring的配置示例:


import com.octo.captcha.CaptchaFactory;
import com.octo.captcha.component.image.backgroundgenerator.*;
import com.octo.captcha.component.image.color.ColorGenerator;
import com.octo.captcha.component.image.color.RandomListColorGenerator;
import com.octo.captcha.component.image.fontgenerator.FontGenerator;
import com.octo.captcha.component.image.fontgenerator.RandomFontGenerator;
import com.octo.captcha.component.image.textpaster.DecoratedRandomTextPaster;
import com.octo.captcha.component.image.textpaster.TextPaster;
import com.octo.captcha.component.image.textpaster.textdecorator.BaffleTextDecorator;
import com.octo.captcha.component.image.textpaster.textdecorator.LineTextDecorator;
import com.octo.captcha.component.image.textpaster.textdecorator.TextDecorator;
import com.octo.captcha.component.image.wordtoimage.ComposedWordToImage;
import com.octo.captcha.component.image.wordtoimage.WordToImage;
import com.octo.captcha.component.word.DictionaryReader;
import com.octo.captcha.component.word.FileDictionary;
import com.octo.captcha.component.word.wordgenerator.DictionaryWordGenerator;
import com.octo.captcha.component.word.wordgenerator.WordGenerator;
import com.octo.captcha.engine.CaptchaEngine;
import com.octo.captcha.engine.GenericCaptchaEngine;
import com.octo.captcha.image.gimpy.GimpyFactory;
import com.octo.captcha.service.captchastore.FastHashMapCaptchaStore;
import com.octo.captcha.service.image.DefaultManageableImageCaptchaService;
import com.octo.captcha.service.image.ImageCaptchaService;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

import java.awt.*;

import java.util.List;
/**
 * 圖片驗證碼配置
 */
@Configuration
public class ImageCaptchaConfig {

    /* 圖片驗證碼服務 */
    @Bean
    public ImageCaptchaService imageCaptchaService(CaptchaEngine captchaEngine){
        return new DefaultManageableImageCaptchaService(new FastHashMapCaptchaStore(),captchaEngine,180,100000,75000);
    }

    /* 圖片驗證碼引擎 */
    @Bean
    public CaptchaEngine captchaEngine(CaptchaFactory captchaFactory){
        return new GenericCaptchaEngine(new CaptchaFactory[]{captchaFactory});
    }

    /* 驗證碼工廠,控制如何生成驗證碼 */
    @Bean
    public CaptchaFactory captchaFactory(WordGenerator wordGenerator,WordToImage wordToImage){
        return new GimpyFactory(wordGenerator,wordToImage);
    }

    /* 單詞生成器 */
    @Bean
    public WordGenerator wordGenerator(DictionaryReader dictionaryReader){
        return new DictionaryWordGenerator(dictionaryReader);
    }

    /* 字典讀取器,這裡的FileDictionary從jar包自帶的resource讀取單詞 */
    @Bean
    public DictionaryReader dictionaryReader(){
        /* 從jar包自帶字典讀取單詞 */
        return new FileDictionary("toddlist");
    }

    /* 單詞轉換為圖片的元件,需要字型生成器、背景生成器、文字貼上器 */
    @Bean
    public WordToImage wordToImage(FontGenerator fontGenerator,BackgroundGenerator backgroundGenerator,TextPaster textPaster){
        return new ComposedWordToImage(fontGenerator,backgroundGenerator,textPaster);
    }

    /* 字型生成器 */
    @Bean
    public FontGenerator fontGenerator(){
        Font hakuyoxingshu = new Font("hakuyoxingshu7000",0,20);
        /* 最小最大字型大小 */
        return new RandomFontGenerator(40,50,new Font[]{hakuyoxingshu});
    }

    /* 背景生成器 */
    @Bean
    public BackgroundGenerator backgroundGenerator(){
        return new UniColorBackgroundGenerator(200,60,new Color(120,120,120));
        /* 生成效果像蛇皮 */
        //return new EllipseBackgroundGenerator(200,60);
        /* 背景由紅黃綠三種顏色組成 */
        //return new FunkyBackgroundGenerator(200,60);
        /* 背景為漸變色 */
        //return new GradientBackgroundGenerator(200,60,new Color(255,0,0),new Color(0,255,0));
        //return new MultipleShapeBackgroundGenerator(200,60);
    }

    /* TextPaster將文字貼上到背景上,需要字型顏色 */
    @Bean
    public TextPaster textPaster(){
        //TextDecorator baffle = new BaffleTextDecorator(5,new Color(0,0,0));
        TextDecorator line = new LineTextDecorator(2,new Color(0,255,0));
        Color blue = new Color(0,0,255);
        ColorGenerator generator =  new RandomListColorGenerator(new Color[]{blue});
        /* 最小最大單詞長度 */
        return new DecoratedRandomTextPaster(3, 5, generator,new TextDecorator[]{line});
    }

}

最後的工具類為:

package com.xidou.common;


import com.octo.captcha.service.CaptchaServiceException;
import com.octo.captcha.service.image.DefaultManageableImageCaptchaService;
import com.octo.captcha.service.image.ImageCaptchaService;
import com.xidou.enums.ExceptionCode;
import com.xidou.vo.BizException;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

import javax.imageio.ImageIO;
import javax.servlet.ServletOutputStream;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.awt.image.BufferedImage;
import java.util.Locale;

@Component
public class ImageCaptchaUtils {

    private static final Logger logger = LoggerFactory.getLogger(ImageCaptchaUtils.class);

    @Autowired
    private ImageCaptchaService instance;

    public void getImageCaptcha(HttpServletRequest request, HttpServletResponse response) {
        try{
            String captchaId = request.getSession().getId();
            logger.info("session id is "+captchaId);
            BufferedImage challenge = instance.getImageChallengeForID(captchaId,Locale.getDefault());
            response.setHeader("Cache-Control", "no-store");
            response.setHeader("Pragma", "no-cache");
            response.setDateHeader("Expires", 0);
            response.setContentType("image/jpeg");
            ServletOutputStream responseOutputStream = response.getOutputStream();
            ImageIO.write(challenge, "jpg", responseOutputStream);
            responseOutputStream.flush();
            responseOutputStream.close();
        }catch(Exception ex){
            throw new BizException(ExceptionCode.IMAGE_CAPTCHA_GENERATE_ERROR.getCode(),ExceptionCode.IMAGE_CAPTCHA_GENERATE_ERROR.getMsg()+ex);
        }
    }

    public void validateCaptcha(HttpServletRequest request,String code){
        Boolean isResponseCorrect =Boolean.FALSE;
        String captchaId = request.getSession().getId();
        try {
            isResponseCorrect = instance.validateResponseForID(captchaId, code);
        } catch (CaptchaServiceException ex) {
            throw new BizException(ExceptionCode.IMAGE_CAPTCHA_VALIDATE_ERROR.getCode(),ExceptionCode.IMAGE_CAPTCHA_VALIDATE_ERROR.getMsg()+ex);
        }
    }

}

可見JCaptcha有自己的驗證碼儲存,並且將sessionId與驗證碼關聯起來,這裡主要介紹一些JCaptcha常用的元件:

ImageCaptchaService:圖片驗證碼服務,獲取BufferedImage、驗證驗證碼都是使用這個元件
CaptchaEngine:包含了多個工廠
CaptchaFactory:驗證碼工廠,用於生成驗證碼的各種配置
WordGenerator:單詞生成器,用於獲取一個隨機字串
DictionaryReader:字典讀取器,用於從指定資源讀取單詞列表
WordToImage:負責單詞到圖片的元件
BackgroundGenerator:背景生成器,用於生成各種效果的背景,如漸變色等
FontGenerator:字型生成器,用於生成文字字型
TextPaster:文字貼上器,用於將文字貼上到圖片上
TextDecorator:文字裝飾器,用於裝飾文字,提高識別難度,有兩種效果,一個是給每個字母新增墨點,另一個是給每個字母新增干擾線
ColorGenerator:顏色生成器,通用元件,用於生成一組隨機顏色,很多其他元件都使用了這個元件