출처 : http://blog.naver.com/PostView.nhn?blogId=affectionjs&logNo=140132417142
회원 자동 가입 방지 코드가 필요해서 인터넷을 검색하다가
GD라이브러리를 이용하여 간단히 만들 수 있을 것 같아서 만들어 보았다.
이미지를 비튼다던가 아니면 글자를 읽어주던가 하는 이런 고급기능은 없다.
준비물 - 배경이미지(없어도 됨), 각 글자 및 숫자 이미지(배경이미지와 겹치게 보이려면 배경이 투명인 PNG이미지가 좋다, 각 숫자 및 글자 이미지의 파일명은 숫자 및 글자와 같아야 한다. 예- 0.png, a.png 등)
PHP설정에서 GD라이브러리를 포함하여야 한다.
우선 직접 이미지를 보여주는 파일(secureimage.php)
<?php
$SI_CHAR_LEN = 5; // 보여줄 글자수
$SI_IMAGE_WIDTH = 27; // 글자 이미지 하나의 폭
$SI_IMAGE_HEIGHT = 35; // 글자 이미지 하나의 높이
$SI_CHAR_ARRAY = array('0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z'); // 보여줄 글자 목록
$img = imagecreatefrompng('images/copybg.png'); // 배경이미지를 읽어온다
$char_num = count($SI_CHAR_ARRAY); // 글자목록 개수
$RANDOM_KEY = '';
$RANDOM_KEY_CHAR = '';
for ($i = 0 ; $i < $SI_CHAR_LEN; $i++) {
$RANDOM_KEY_CHAR = $SI_CHAR_ARRAY[rand(0, $char_num - 1)]; // 글자목록 중 임의로 한개를 선택한다.// $RANDOM_KEY .= $RANDOM_KEY_ARRAY[$i];
$RANDOM_KEY .= $RANDOM_KEY_CHAR;
$src = imagecreatefrompng('images/' . $RANDOM_KEY_CHAR . '.png'); // 선택된 임의의 글자 이미지를 읽어온다.
imagecopy($img, $src, $SI_IMAGE_WIDTH * $i, 0, 0, 0, $SI_IMAGE_WIDTH, $SI_IMAGE_HEIGHT); // 배경이미지와 합친다
}
session_start();
$_SESSION['SECURE_TEXT'] = $RANDOM_KEY; // 선택된 글자들을 세션변수에 저장한다.
header('Content-type: image/gif');
imagegif($img); // 이미지 뿌리기
imagedestroy($img);
?>
CAPTCHA 이미지 뿌리기
<img src="secureimage.php" id="scureimage" />
해당 이미지가 적용된 실제 예이다.
CAPTCHA 이미지 갱신
해당이미지를 읽을 수 없을 경우 이미지를 바꾸어 줘야 하는데 javascript 를 이용하면 된다.
문제는 이미지를 갱신해도 소스가 같으면 브라우져가 캐시된 이미지를 보여주기때문에 갱신된 이미지를 보여주지 않는 경우가 있다
이를 방지하기 위해 뒤에 쓰레기코드(?)를 추가해 준다.
html코드
<img src="secureimage.php?key=<?php echo rand(); ?>" id="scureimage" alt="중복가입방지코드" /><!-- captcha 이미지 -->
<input type="text" name="securetext" /><!-- 텍스트 입력 박스 -->
<a href="#secureimage" id="imagerefresh">[새로고침]</a><!-- 이미지 갱신 버튼 -->
자바스크립트(jquery이용)
$(document).ready(function(){
$("a#imagerefresh").click(function(){ // [새로고침] 클릭시
$("img#securetext").attr("src", "secureimage.php?key=" + parseInt(Math.rand() * 100000, 10)); // 이미지 소스를 변경, 브라우져가 다른 이미지로 인식하도록 랜덤코드를 추가해준다.
return false;
});
});
입력된 텍스트가 맞는지 확인하는 법은 입력된 텍스트
input#securetext 의 value값과 php세션에 저장되어있는 $_ SESSION['SECURE_TEXT']값을 비교하면 된다.
form값을 통해 비교를 하던가 ajax를 이용하던가는 사용자 마음이다.
PS. captcha 이미지는 시각장애인들은 인식할 수 없기 때문에 웹접근성에 부합하지 않는다. 이를 보완하기 위해 이미지를 음성으로 읽어주던가 아니면 이미지가 아닌 간단한 퀴즈를 보여주던가 하는 방법을 생각해 볼 수 있다.
'리눅스 서버에 대해서 > python' 카테고리의 다른 글
파이선 간단한 captchr 소스 (0) | 2013.09.20 |
---|---|
파이선 PIL 간단 예제 (0) | 2013.09.20 |
파이썬의 PIL 이미지 라이브러리 사용 강좌 (0) | 2013.09.18 |
captcha 우회하기 (0) | 2013.09.18 |
TIME_WAIT를 남기지 않는 세션종료 (Graceful Shutdown) (0) | 2013.05.15 |