怎样获取验证码图片 本帖最后由 Jartru 于 2009-11-13 21:08:17 编辑 解决方案 » 免费领取超大流量手机卡,每月29元包185G流量+100分钟通话, 中国电信官方发货 随机生成数字, 或字母, 图片的名称和字母数字组合在一起例如, 有图片名 3de.jpg 和 seve52.jpg,你随机生成的数字组合又叫3de和seve52, 就这样显示<img src="3de.jpg" /> <img src="seve52.jpg"> 这是其中一种思路, 你还可以定义26个字母和10个数字的图片, 随机拿得的验证码去读这几张图片组合成一张输出 PHP100视频里有专讲做这个验证图片的 如果你不是想用PHP读取验证码的数值而是想直接页面显示验证码图片把图片地址放在页面对应位置的Img标签中即可 如果你是想要验证码实现的PHP代码手册里面就有现成代码的 没有这么简单的,因为验证图片是动态生成的,直接用img标签显示的是最新的验证码,这样用户输入就会错误 验证码可以用PHP的绘图函数生成。//生成验证码图片Header("Content-type: image/PNG");srand((double)microtime()*1000000);//播下一个生成随机数字的种子,以方便下面随机数生成的使用session_start();//将随机数存入session中$_SESSION['authnum']="";$im = imagecreate(62,20); //制定图片背景大小$black = ImageColorAllocate($im, 0,0,0); //设定三种颜色$white = ImageColorAllocate($im, 255,255,255);$gray = ImageColorAllocate($im, 200,200,200);imagefill($im,0,0,$gray); //采用区域填充法,设定(0,0)while(($authnum=rand()%100000)<10000);//将四位整数验证码绘入图片$_SESSION['authnum']=$authnum;imagestring($im, 5, 10, 3, $authnum, $black);// 用 col 颜色将字符串 s 画到 image 所代表的图像的 x,y 座标处(图像的左上角为 0, 0)。//如果 font 是 1,2,3,4 或 5,则使用内置字体for($i=0;$i<200;$i++) //加入干扰象素{$randcolor = ImageColorallocate($im,rand(0,255),rand(0,255),rand(0,255));imagesetpixel($im, rand()%70 , rand()%30 , $randcolor);}ImagePNG($im);ImageDestroy($im); 楼上正解,PHP100视频里有专讲做这个验证图片的 这不是要做验证码的问题,是要识别验证码,通过模拟浏览器 提交post数据,楼主找到答案讲一下哦,或者你上面别人实现了的网页是在那里啊,俺去看看 不知道楼主是不是想抓取别的网站的验证码不过那样是不可行的。。一般做验证码是向7楼那样用GD生成一个验证码存在SESSION中(独立一个PHP)然后向二楼那样用<IMG SRC="YZM.PHP">显示出来然后用SESION做对比。。 需要知道它生成验证码的页面PHP文件的名称。 require(ROOT_PATH . 'includes/cls_captcha.php');$img = new captcha(ROOT_PATH . 'data/captcha/', $_CFG['captcha_width'], $_CFG['captcha_height']);@ob_end_clean(); //清除之前出现的多余输入if (isset($_REQUEST['is_login'])){ $img->session_word = 'captcha_login';}$img->generate_image(); 不用抓赛。直接把产生图片的文件的路径赋到你的图片的img src 下面就行了赛,比如csdn的登录图片路径是:<img id="MzImgExpPwd" alt="" src="http://passport.csdn.net/ShowExPwd.aspx?temp=g242qwqw" complete="complete"/>csdn的服务器在产生验证码图片的时候已经把值放入session中了吧,但是我写了一个表单提交登录,登不进去,是不是服务器对表单来源做了验证的??如果对表单来源没加验证限制应该能登入,你试一下, 这是csdn的登录框:<form name="aspnetForm" id="aspnetForm" action="http://passport.csdn.net/UserLogin.aspx" method="post"> 登录名: <input name="ctl00$CPH_Content$tb_LoginNameOrLoginEmail" title="请输入用户名或者邮箱" class="unnamed1" id="ctl00_CPH_Content_tb_LoginNameOrLoginEmail" style="width: 12em;" type="text" maxLength="50"/> <br> 密码: <input name="ctl00$CPH_Content$tb_Password" class="unnamed1" id="ctl00_CPH_Content_tb_Password" style="width: 12em;" type="password" maxLength="50" Validators="[object]"/> <br> 验证码: <input name="ctl00$CPH_Content$tb_ExPwd" class="unnamed1" id="ctl00_CPH_Content_tb_ExPwd" style="width: 56px;" type="text" maxLength="5" Validators="[object]"/> <br> <img id="MzImgExpPwd" alt="" src="http://passport.csdn.net/ShowExPwd.aspx?temp=g242qwqw" complete="complete"/> <br> <input type='submit' value='登录'> </form> 1、抓取对方网站的内容,把cookie和图片都存下来(抓取图片的时候也需要带着cookie)2、把图片(本地保存的)显示给你的用户3、用户输入以后,用保存的cookie和用户输入post到对方网站上4、把对方网站返回的内容显示给用户 多谢iisbsd,我正是要实现这个功能,只是要抓取别人网站上的验证码来显示,现在碰到的问题是怎么在抓取网页时把cookie也保存下来,是不是要用到fsockopen()这样的函数呢? 建议你看看CURL,自己写HTTP客户端还是辛苦了点。 如查你的意思是iframe之类的意思,是可以的,当那个验证码图片显在你网站就行了 捎带说一句,抓取图片和提交验证码的时候最好加上Referer,不少网站也检查这个东西。 Referer和cookie都带上了,验证图片抓到了,但验证码还是不配套啊,总是提示“图片验证码校验失败”?!这么发referer和cookie没错吧: curl_setopt($ch,CURLOPT_REFERER, 'http://www.xxx.com.cn/'); curl_setopt($ch,CURLOPT_COOKIE, 'JSESSIONID=LHwp64HQFnQ3XZdMG1FnBtB1LWRJV4QWgsbnv5YjjTvfvky0fCNT!1491821324');用sniffer抓网页数据研究了一整天,这个问题还没搞定,大虾们帮帮忙吧! 看看这个网站的验证码吧,www.ems.com.cn只要能成功抓到验证码图片就成,不需要识别! 不是吧你看它的地址http://www.ems.com.cn/servlet/ImageCaptchaServlet,用的是servlet技术,又不是phpservlet我不太懂发到Java区去吧 这和java没关系,PHP能做到的 还没有解决吗?给你一段测试代码<?phpfclose(fopen('cookie.txt','w')); //文件 cookie.txt 用于存放取得的cookie$cookiejar = realpath('cookie.txt');$fp = fopen("example_homepage.txt", "w"); //文件 example_homepage.txt 用于存放取得的页面内容$ch = curl_init("http://www.ems.com.cn/servlet/ImageCaptchaServlet");curl_setopt($ch, CURLOPT_FILE, $fp);curl_setopt($ch, CURLOPT_COOKIEJAR, $cookiejar);curl_setopt($ch, CURLOPT_HEADER, 0);curl_exec($ch);curl_close($ch);fclose($fp);readfile($cookiejar); //查看取到的 cookie//readfile("example_homepage.txt"); //查看取到的图片1、程序不能执行连续执行,否则校验码会变2、需保存过渡文件后才能与用户交互 <?phpfclose(fopen('cookie.txt','w')); //文件 cookie.txt 用于存放取得的cookie$cookiejar = realpath('cookie.txt');$fp = fopen("example_homepage.txt", "w"); //文件 example_homepage.txt 用于存放取得的页面内容$ch = curl_init("http://www.ems.com.cn/servlet/ImageCaptchaServlet");curl_setopt($ch, CURLOPT_FILE, $fp);curl_setopt($ch, CURLOPT_COOKIEJAR, $cookiejar);curl_setopt($ch, CURLOPT_HEADER, 0);curl_exec($ch);curl_close($ch);fclose($fp); //readfile($cookiejar); //查看取到的 cookie//readfile("example_homepage.jpg"); //查看取到的图片echo "<img src='example_homepage.txt'>";if($_POST){ $parm = array(BBF9402C4316F9C78DD8BAF=>$_POST['code'], mailNum =>'EA739701017CS',//$_POST['number'], myEmsbarCode=>0465570086207,//正则分析获取 reqCode=>browseBASE );$ch = curl_init("http://www.ems.com.cn/qcgzOutQueryAction.do"); curl_setopt($ch, CURLOPT_HEADER, 0); curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1); curl_setopt($ch, CURLOPT_POST, 1); curl_setopt($ch, CURLOPT_POSTFIELDS, http_build_query($parm)); $_source = curl_exec($ch); curl_close($ch); var_dump($_source); exit; }?> 39楼的在发送表单信息时没有了cookies,望改进 39 楼回答的很完美,自己做个FORM表单把验证码图片 code 传回来就OK了提交不再需要COOKIE 今天又抽空看了下 我加了COOKIE提交完 返回的错误信息是信息提示:页面停留时间过长导致邮件查询标志丢失,请刷新查询页面。估计哪还有点问题? 楼主您可以结贴了,偶帮你实现了~查询页面 test_curl.php<html><head><meta http-equiv="Content-Type" content="text/html; charset=gb2312"><title>EMS快递查询</title></head><body><?phpfclose(fopen('cookie.txt','w')); //文件 cookie.txt 用于存放取得的cookie$cookiejar = realpath('cookie.txt');$fp = fopen("example_homepage.txt", "w"); //文件 example_homepage.txt 用于存放取得的页面内容 $ch = curl_init("http://www.ems.com.cn/servlet/ImageCaptchaServlet");curl_setopt($ch, CURLOPT_FILE, $fp); curl_setopt($ch, CURLOPT_COOKIESESSION, 1); curl_setopt($ch, CURLOPT_COOKIEJAR, $cookiejar);curl_setopt($ch, CURLOPT_COOKIEFILE, $cookiejar); curl_setopt($ch, CURLOPT_HEADER, 0);curl_exec($ch);curl_close($ch);fclose($fp); //readfile($cookiejar); //查看取到的 cookie//readfile("example_homepage.jpg"); //查看取到的图片?><form action="testpost.php" method="post" name="form1">快递号:<input name="mailNum" type="text" value="EA739701017CS" />(13位 首尾2位都是字母)<input name="code" type="text" value="" /> <?php echo "<img src='example_homepage.txt'>";?><input type="submit" value="提交"></form></body></html>提交页面 testpost.php<?phpif($_POST){//使用先前验证码的cookie文件 $cookiejar = realpath('cookie.txt'); //获取myEmsbarCode号 和验证码变量名$ch = curl_init("http://www.ems.com.cn");curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);curl_setopt($ch, CURLOPT_HEADER, 0); curl_setopt($ch, CURLOPT_COOKIEFILE, $cookiejar);curl_setopt($ch, CURLOPT_COOKIEJAR, $cookiejar);$result = curl_exec($ch);curl_close($ch); preg_match("/<input type=\"hidden\" name=\"myEmsbarCode\" value=\"(.*)\"\/>/isU",$result,$myEmsbarCode);preg_match("/<\/span><input name=\"(.*)\" type=\"text\"/isU",$result,$codename); $parm = array($codename[1]=>$_POST['code'], mailNum =>$_POST['mailNum'], myEmsbarCode=>$myEmsbarCode[1], reqCode=>'browseBASE' );//PRINT_R(http_build_query($parm));//EXIT;$ch = curl_init("http://www.ems.com.cn/qcgzOutQueryAction.do"); curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1); curl_setopt($ch, CURLOPT_HEADER, 0); curl_setopt($ch, CURLOPT_COOKIEFILE, $cookiejar); curl_setopt($ch, CURLOPT_COOKIEJAR, $cookiejar); curl_setopt($ch, CURLOPT_POST, 1); curl_setopt($ch, CURLOPT_REFERER, "http://www.ems.com.cn"); curl_setopt($ch, CURLOPT_POSTFIELDS, http_build_query($parm)); $_source = curl_exec($ch); curl_close($ch); //搞定 var_dump($_source); exit; }?> 不用curl,用fsockopen可以实现么? 好像表单里面动态input中数据和验证码同时传送过来的,怎么才能同步分开抓取,抓取不同步没用 $img=file_get_contents('http://www.ems.com.cn/servlet/ImageCaptchaServlet');file_put_contents('1.jpg',$img);echo '<img src=1.jpg>';so easy 呼叫好心人 求个正则 求助:请解释以下为什么结果是这样的? 利用自己的专业特长 如何每次只允许一个人执行 抓取网页信息图片不能正常显示 请问哪里可以下载到php 4.0.0(win32)?在线等候 请教从MYSQL显示图片的问题 类型为button的按钮,onclick后这样写为什么错了呢? PHP 有时间比较函数吗? php通过curl上传图片到https的服务器需要哪些要注意的。求调教 求解,怎样比较2个数组的大小 关于array_walk 为什么是这样
<img src="3de.jpg" /> <img src="seve52.jpg"> 这是其中一种思路, 你还可以定义26个字母和10个数字的图片,
随机拿得的验证码去读这几张图片组合成一张输出
而是想直接页面显示验证码图片
把图片地址放在页面对应位置的Img标签中即可
手册里面就有现成代码的
没有这么简单的,因为验证图片是动态生成的,直接用img标签显示的是最新的验证码,这样用户输入就会错误
Header("Content-type: image/PNG");
srand((double)microtime()*1000000);//播下一个生成随机数字的种子,以方便下面随机数生成的使用session_start();//将随机数存入session中
$_SESSION['authnum']="";
$im = imagecreate(62,20); //制定图片背景大小$black = ImageColorAllocate($im, 0,0,0); //设定三种颜色
$white = ImageColorAllocate($im, 255,255,255);
$gray = ImageColorAllocate($im, 200,200,200);imagefill($im,0,0,$gray); //采用区域填充法,设定(0,0)while(($authnum=rand()%100000)<10000);
//将四位整数验证码绘入图片
$_SESSION['authnum']=$authnum;
imagestring($im, 5, 10, 3, $authnum, $black);
// 用 col 颜色将字符串 s 画到 image 所代表的图像的 x,y 座标处(图像的左上角为 0, 0)。
//如果 font 是 1,2,3,4 或 5,则使用内置字体for($i=0;$i<200;$i++) //加入干扰象素
{
$randcolor = ImageColorallocate($im,rand(0,255),rand(0,255),rand(0,255));
imagesetpixel($im, rand()%70 , rand()%30 , $randcolor);
}
ImagePNG($im);
ImageDestroy($im);
是要识别验证码,
通过模拟浏览器 提交post数据,楼主找到答案讲一下哦,
或者你上面别人实现了的网页是在那里啊,俺去看看
然后向二楼那样用<IMG SRC="YZM.PHP">显示出来然后用SESION做对比。。
require(ROOT_PATH . 'includes/cls_captcha.php');$img = new captcha(ROOT_PATH . 'data/captcha/', $_CFG['captcha_width'], $_CFG['captcha_height']);
@ob_end_clean(); //清除之前出现的多余输入
if (isset($_REQUEST['is_login']))
{
$img->session_word = 'captcha_login';
}
$img->generate_image();
比如csdn的登录图片路径是:
<img id="MzImgExpPwd" alt="" src="http://passport.csdn.net/ShowExPwd.aspx?temp=g242qwqw" complete="complete"/>
csdn的服务器在产生验证码图片的时候已经把值放入session中了吧,但是我写了一个表单提交登录,登不进去,是不是服务器对表单来源做了验证的??如果对表单来源没加验证限制应该能登入,你试一下,
登录名:
<input name="ctl00$CPH_Content$tb_LoginNameOrLoginEmail" title="请输入用户名或者邮箱" class="unnamed1" id="ctl00_CPH_Content_tb_LoginNameOrLoginEmail" style="width: 12em;" type="text" maxLength="50"/>
<br>
密码:
<input name="ctl00$CPH_Content$tb_Password" class="unnamed1" id="ctl00_CPH_Content_tb_Password" style="width: 12em;" type="password" maxLength="50" Validators="[object]"/>
<br>
验证码:
<input name="ctl00$CPH_Content$tb_ExPwd" class="unnamed1" id="ctl00_CPH_Content_tb_ExPwd" style="width: 56px;" type="text" maxLength="5" Validators="[object]"/>
<br>
<img id="MzImgExpPwd" alt="" src="http://passport.csdn.net/ShowExPwd.aspx?temp=g242qwqw" complete="complete"/>
<br>
<input type='submit' value='登录'>
</form>
2、把图片(本地保存的)显示给你的用户
3、用户输入以后,用保存的cookie和用户输入post到对方网站上
4、把对方网站返回的内容显示给用户
多谢iisbsd,我正是要实现这个功能,只是要抓取别人网站上的验证码来显示,现在碰到的问题是怎么在抓取网页时把cookie也保存下来,是不是要用到fsockopen()这样的函数呢?
建议你看看CURL,自己写HTTP客户端还是辛苦了点。
Referer和cookie都带上了,验证图片抓到了,但验证码还是不配套啊,总是提示“图片验证码校验失败”?!这么发referer和cookie没错吧:
curl_setopt($ch,CURLOPT_REFERER, 'http://www.xxx.com.cn/');
curl_setopt($ch,CURLOPT_COOKIE, 'JSESSIONID=LHwp64HQFnQ3XZdMG1FnBtB1LWRJV4QWgsbnv5YjjTvfvky0fCNT!1491821324');用sniffer抓网页数据研究了一整天,这个问题还没搞定,大虾们帮帮忙吧!
你看它的地址http://www.ems.com.cn/servlet/ImageCaptchaServlet,用的是servlet技术,又不是php
servlet我不太懂发到Java区去吧
这和java没关系,PHP能做到的
<?php
fclose(fopen('cookie.txt','w')); //文件 cookie.txt 用于存放取得的cookie
$cookiejar = realpath('cookie.txt');
$fp = fopen("example_homepage.txt", "w"); //文件 example_homepage.txt 用于存放取得的页面内容$ch = curl_init("http://www.ems.com.cn/servlet/ImageCaptchaServlet");
curl_setopt($ch, CURLOPT_FILE, $fp);
curl_setopt($ch, CURLOPT_COOKIEJAR, $cookiejar);
curl_setopt($ch, CURLOPT_HEADER, 0);
curl_exec($ch);
curl_close($ch);
fclose($fp);readfile($cookiejar); //查看取到的 cookie
//readfile("example_homepage.txt"); //查看取到的图片1、程序不能执行连续执行,否则校验码会变
2、需保存过渡文件后才能与用户交互
$cookiejar = realpath('cookie.txt');
$fp = fopen("example_homepage.txt", "w"); //文件 example_homepage.txt 用于存放取得的页面内容$ch = curl_init("http://www.ems.com.cn/servlet/ImageCaptchaServlet");
curl_setopt($ch, CURLOPT_FILE, $fp);
curl_setopt($ch, CURLOPT_COOKIEJAR, $cookiejar);
curl_setopt($ch, CURLOPT_HEADER, 0);
curl_exec($ch);
curl_close($ch);
fclose($fp);
//readfile($cookiejar); //查看取到的 cookie
//readfile("example_homepage.jpg"); //查看取到的图片
echo "<img src='example_homepage.txt'>";if($_POST){
$parm = array(BBF9402C4316F9C78DD8BAF=>$_POST['code'],
mailNum =>'EA739701017CS',//$_POST['number'],
myEmsbarCode=>0465570086207,//正则分析获取
reqCode=>browseBASE
);
$ch = curl_init("http://www.ems.com.cn/qcgzOutQueryAction.do");
curl_setopt($ch, CURLOPT_HEADER, 0);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($ch, CURLOPT_POST, 1);
curl_setopt($ch, CURLOPT_POSTFIELDS, http_build_query($parm));
$_source = curl_exec($ch);
curl_close($ch);
var_dump($_source);
exit;
}?>
39 楼回答的很完美,自己做个FORM表单把验证码图片 code 传回来就OK了
提交不再需要COOKIE
信息提示:页面停留时间过长导致邮件查询标志丢失,请刷新查询页面。
估计哪还有点问题?
查询页面 test_curl.php<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=gb2312">
<title>EMS快递查询</title>
</head>
<body>
<?php
fclose(fopen('cookie.txt','w')); //文件 cookie.txt 用于存放取得的cookie
$cookiejar = realpath('cookie.txt');
$fp = fopen("example_homepage.txt", "w"); //文件 example_homepage.txt 用于存放取得的页面内容
$ch = curl_init("http://www.ems.com.cn/servlet/ImageCaptchaServlet");
curl_setopt($ch, CURLOPT_FILE, $fp);
curl_setopt($ch, CURLOPT_COOKIESESSION, 1);
curl_setopt($ch, CURLOPT_COOKIEJAR, $cookiejar);
curl_setopt($ch, CURLOPT_COOKIEFILE, $cookiejar);
curl_setopt($ch, CURLOPT_HEADER, 0);
curl_exec($ch);
curl_close($ch);
fclose($fp);
//readfile($cookiejar); //查看取到的 cookie
//readfile("example_homepage.jpg"); //查看取到的图片
?>
<form action="testpost.php" method="post" name="form1">
快递号:<input name="mailNum" type="text" value="EA739701017CS" />(13位 首尾2位都是字母)
<input name="code" type="text" value="" />
<?php echo "<img src='example_homepage.txt'>";?>
<input type="submit" value="提交">
</form></body>
</html>
提交页面 testpost.php<?php
if($_POST){
//使用先前验证码的cookie文件
$cookiejar = realpath('cookie.txt');
//获取myEmsbarCode号 和验证码变量名
$ch = curl_init("http://www.ems.com.cn");
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_HEADER, 0);
curl_setopt($ch, CURLOPT_COOKIEFILE, $cookiejar);
curl_setopt($ch, CURLOPT_COOKIEJAR, $cookiejar);
$result = curl_exec($ch);
curl_close($ch);
preg_match("/<input type=\"hidden\" name=\"myEmsbarCode\" value=\"(.*)\"\/>/isU",$result,$myEmsbarCode);
preg_match("/<\/span><input name=\"(.*)\" type=\"text\"/isU",$result,$codename);
$parm = array($codename[1]=>$_POST['code'],
mailNum =>$_POST['mailNum'],
myEmsbarCode=>$myEmsbarCode[1],
reqCode=>'browseBASE'
);
//PRINT_R(http_build_query($parm));
//EXIT;
$ch = curl_init("http://www.ems.com.cn/qcgzOutQueryAction.do");
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($ch, CURLOPT_HEADER, 0);
curl_setopt($ch, CURLOPT_COOKIEFILE, $cookiejar);
curl_setopt($ch, CURLOPT_COOKIEJAR, $cookiejar);
curl_setopt($ch, CURLOPT_POST, 1);
curl_setopt($ch, CURLOPT_REFERER, "http://www.ems.com.cn");
curl_setopt($ch, CURLOPT_POSTFIELDS, http_build_query($parm));
$_source = curl_exec($ch);
curl_close($ch);
//搞定
var_dump($_source);
exit;
}
?>
file_put_contents('1.jpg',$img);
echo '<img src=1.jpg>';so easy