失眠网,内容丰富有趣,生活中的好帮手!
失眠网 > 用Python自动识别验证码(完整教程 陆续更新12306验证码识别 抢票)

用Python自动识别验证码(完整教程 陆续更新12306验证码识别 抢票)

时间:2020-10-11 16:02:05

相关推荐

用Python自动识别验证码(完整教程 陆续更新12306验证码识别 抢票)

1.古诗文网验证码识别

2.fateadm_api.py(识别需要的配置,建议放在同一文件夹下) 调用api接口

全部源代码和相关配置,已古诗文网验证码识别为例,进行学习,代码中有相关说明,每一步都有详细注释,我的个人信息已隐藏。

1.古诗文网验证码识别

开发者账号密码可以申请

import requestsfrom lxml import etreefrom fateadm_api import FateadmApidef TestFunc(imgPath,codyType):pd_id = "xxxxxx"#用户中心页可以查询到pd信息pd_key= "xxxxxxxx"app_id= "xxxxxxx"#开发者分成用的账号,在开发者中心可以查询到app_key = "xxxxxxx"#识别类型,#具体类型可以查看官方网站的价格页选择具体的类型,不清楚类型的,可以咨询客服pred_type = codyTypeapi = FateadmApi(app_id, app_key, pd_id, pd_key)# 查询余额balance = api.QueryBalcExtend() # 直接返余额# api.QueryBalc()# 通过文件形式识别:file_name = imgPath# 多网站类型时,需要增加src_url参数,具体请参考api文档: /web/#/1?page_id=6result = api.PredictFromFileExtend(pred_type,file_name) # 直接返回识别结果#rsp = api.PredictFromFile(pred_type, file_name) # 返回详细识别结果'''# 如果不是通过文件识别,则调用Predict接口:# result = api.PredictExtend(pred_type,data) # 直接返回识别结果rsp = api.Predict(pred_type,data)# 返回详细的识别结果'''# just_flag = False# if just_flag :#if rsp.ret_code == 0:# #识别的结果如果与预期不符,可以调用这个接口将预期不符的订单退款# # 退款仅在正常识别出结果后,无法通过网站验证的情况,请勿非法或者滥用,否则可能进行封号处理# api.Justice( rsp.request_id)#card_id = "123"#card_key = "123"#充值#api.Charge(card_id, card_key)#LOG("print in testfunc")return result# if __name__ == "__main__":#TestFunc()headers = {'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/86.0.4240.193 Safari/537.36'}url = '/user/login.aspx?from=/user/collect.aspx'page_text = requests.get(url,headers = headers).texttree = etree.HTML(page_text)code_img_src = '' + tree.xpath('//*[@id="imgCode"]/@src')[0]img_data = requests.get(code_img_src,headers = headers).contentwith open('./code.jpg','wb') as fp:fp.write(img_data)code_text = TestFunc('code.jpg',30400)print('识别结果为:' + code_text)code_text = TestFunc('code.jpg',30400)print('识别结果为:' + code_text)

fateadm_api.py(识别需要的配置,建议放在同一文件夹下)

调用api接口

# coding=utf-8import os,sysimport hashlibimport timeimport jsonimport requestsFATEA_PRED_URL = ""def LOG(log):# 不需要测试时,注释掉日志就可以了print(log)log = Noneclass TmpObj():def __init__(self):self.value = Noneclass Rsp():def __init__(self):self.ret_code = -1self.cust_val = 0.0self.err_msg = "succ"self.pred_rsp = TmpObj()def ParseJsonRsp(self, rsp_data):if rsp_data is None:self.err_msg= "http request failed, get rsp Nil data"returnjrsp= json.loads( rsp_data)self.ret_code = int(jrsp["RetCode"])self.err_msg = jrsp["ErrMsg"]self.request_id= jrsp["RequestId"]if self.ret_code == 0:rslt_data = jrsp["RspData"]if rslt_data is not None and rslt_data != "":jrsp_ext = json.loads( rslt_data)if "cust_val" in jrsp_ext:data = jrsp_ext["cust_val"]self.cust_val = float(data)if "result" in jrsp_ext:data = jrsp_ext["result"]self.pred_rsp.value= datadef CalcSign(pd_id, passwd, timestamp):md5= hashlib.md5()md5.update((timestamp + passwd).encode())csign = md5.hexdigest()md5= hashlib.md5()md5.update((pd_id + timestamp + csign).encode())csign = md5.hexdigest()return csigndef CalcCardSign(cardid, cardkey, timestamp, passwd):md5= hashlib.md5()md5.update(passwd + timestamp + cardid + cardkey)return md5.hexdigest()def HttpRequest(url, body_data, img_data=""):rsp = Rsp()post_data = body_datafiles = {'img_data':('img_data',img_data)}header= {'User-Agent': 'Mozilla/5.0',}rsp_data = requests.post(url, post_data,files=files ,headers=header)rsp.ParseJsonRsp( rsp_data.text)return rspclass FateadmApi():# API接口调用类# 参数(appID,appKey,pdID,pdKey)def __init__(self, app_id, app_key, pd_id, pd_key):self.app_id= app_idif app_id is None:self.app_id = ""self.app_key = app_keyself.pd_id= pd_idself.pd_key= pd_keyself.host = FATEA_PRED_URLdef SetHost(self, url):self.host = url## 查询余额# 参数:无# 返回值:# rsp.ret_code:正常返回0# rsp.cust_val:用户余额# rsp.err_msg:异常时返回异常详情#def QueryBalc(self):tm= str( int(time.time()))sign = CalcSign( self.pd_id, self.pd_key, tm)param = {"user_id": self.pd_id,"timestamp":tm,"sign":sign}url= self.host + "/api/custval"rsp= HttpRequest(url, param)if rsp.ret_code == 0:LOG("query succ ret: {} cust_val: {} rsp: {} pred: {}".format( rsp.ret_code, rsp.cust_val, rsp.err_msg, rsp.pred_rsp.value))else:LOG("query failed ret: {} err: {}".format( rsp.ret_code, rsp.err_msg.encode('utf-8')))return rsp## 查询网络延迟# 参数:pred_type:识别类型# 返回值:# rsp.ret_code:正常返回0# rsp.err_msg:异常时返回异常详情#def QueryTTS(self, pred_type):tm= str( int(time.time()))sign = CalcSign( self.pd_id, self.pd_key, tm)param = {"user_id": self.pd_id,"timestamp":tm,"sign":sign,"predict_type":pred_type,}if self.app_id != "":#asign = CalcSign(self.app_id, self.app_key, tm)param["appid"]= self.app_idparam["asign"]= asignurl= self.host + "/api/qcrtt"rsp= HttpRequest(url, param)if rsp.ret_code == 0:LOG("query rtt succ ret: {} request_id: {} err: {}".format( rsp.ret_code, rsp.request_id, rsp.err_msg))else:LOG("predict failed ret: {} err: {}".format( rsp.ret_code, rsp.err_msg.encode('utf-8')))return rsp## 识别验证码# 参数:pred_type:识别类型 img_data:图片的数据# 返回值:# rsp.ret_code:正常返回0# rsp.request_id:唯一订单号# rsp.pred_rsp.value:识别结果# rsp.err_msg:异常时返回异常详情#def Predict(self, pred_type, img_data, head_info = ""):tm= str( int(time.time()))sign = CalcSign( self.pd_id, self.pd_key, tm)param = {"user_id": self.pd_id,"timestamp": tm,"sign": sign,"predict_type": pred_type,"up_type": "mt"}if head_info is not None or head_info != "":param["head_info"] = head_infoif self.app_id != "":#asign = CalcSign(self.app_id, self.app_key, tm)param["appid"]= self.app_idparam["asign"]= asignurl= self.host + "/api/capreg"files = img_datarsp= HttpRequest(url, param, files)if rsp.ret_code == 0:LOG("predict succ ret: {} request_id: {} pred: {} err: {}".format( rsp.ret_code, rsp.request_id, rsp.pred_rsp.value, rsp.err_msg))else:LOG("predict failed ret: {} err: {}".format( rsp.ret_code, rsp.err_msg))if rsp.ret_code == 4003:#lack of moneyLOG("cust_val <= 0 lack of money, please charge immediately")return rsp## 从文件进行验证码识别# 参数:pred_type;识别类型 file_name:文件名# 返回值:# rsp.ret_code:正常返回0# rsp.request_id:唯一订单号# rsp.pred_rsp.value:识别结果# rsp.err_msg:异常时返回异常详情#def PredictFromFile( self, pred_type, file_name, head_info = ""):with open(file_name, "rb") as f:data = f.read()return self.Predict(pred_type,data,head_info=head_info)## 识别失败,进行退款请求# 参数:request_id:需要退款的订单号# 返回值:# rsp.ret_code:正常返回0# rsp.err_msg:异常时返回异常详情## 注意:# Predict识别接口,仅在ret_code == 0时才会进行扣款,才需要进行退款请求,否则无需进行退款操作# 注意2:# 退款仅在正常识别出结果后,无法通过网站验证的情况,请勿非法或者滥用,否则可能进行封号处理#def Justice(self, request_id):if request_id == "":#returntm= str( int(time.time()))sign = CalcSign( self.pd_id, self.pd_key, tm)param = {"user_id": self.pd_id,"timestamp":tm,"sign":sign,"request_id":request_id}url= self.host + "/api/capjust"rsp= HttpRequest(url, param)if rsp.ret_code == 0:LOG("justice succ ret: {} request_id: {} pred: {} err: {}".format( rsp.ret_code, rsp.request_id, rsp.pred_rsp.value, rsp.err_msg))else:LOG("justice failed ret: {} err: {}".format( rsp.ret_code, rsp.err_msg.encode('utf-8')))return rsp## 充值接口# 参数:cardid:充值卡号 cardkey:充值卡签名串# 返回值:# rsp.ret_code:正常返回0# rsp.err_msg:异常时返回异常详情#def Charge(self, cardid, cardkey):tm= str( int(time.time()))sign = CalcSign( self.pd_id, self.pd_key, tm)csign = CalcCardSign(cardid, cardkey, tm, self.pd_key)param = {"user_id": self.pd_id,"timestamp":tm,"sign":sign,'cardid':cardid,'csign':csign}url= self.host + "/api/charge"rsp= HttpRequest(url, param)if rsp.ret_code == 0:LOG("charge succ ret: {} request_id: {} pred: {} err: {}".format( rsp.ret_code, rsp.request_id, rsp.pred_rsp.value, rsp.err_msg))else:LOG("charge failed ret: {} err: {}".format( rsp.ret_code, rsp.err_msg.encode('utf-8')))return rsp### 充值,只返回是否成功# 参数:cardid:充值卡号 cardkey:充值卡签名串# 返回值:充值成功时返回0##def ExtendCharge(self, cardid, cardkey):return self.Charge(cardid,cardkey).ret_code### 调用退款,只返回是否成功# 参数:request_id:需要退款的订单号# 返回值:退款成功时返回0## 注意:# Predict识别接口,仅在ret_code == 0时才会进行扣款,才需要进行退款请求,否则无需进行退款操作# 注意2:# 退款仅在正常识别出结果后,无法通过网站验证的情况,请勿非法或者滥用,否则可能进行封号处理##def JusticeExtend(self, request_id):return self.Justice(request_id).ret_code### 查询余额,只返回余额# 参数:无# 返回值:rsp.cust_val:余额##def QueryBalcExtend(self):rsp = self.QueryBalc()return rsp.cust_val### 从文件识别验证码,只返回识别结果# 参数:pred_type;识别类型 file_name:文件名# 返回值:rsp.pred_rsp.value:识别的结果##def PredictFromFileExtend( self, pred_type, file_name, head_info = ""):rsp = self.PredictFromFile(pred_type,file_name,head_info)return rsp.pred_rsp.value### 识别接口,只返回识别结果# 参数:pred_type:识别类型 img_data:图片的数据# 返回值:rsp.pred_rsp.value:识别的结果##def PredictExtend(self,pred_type, img_data, head_info = ""):rsp = self.Predict(pred_type,img_data,head_info)return rsp.pred_rsp.valuedef TestFunc():pd_id = "128292"#用户中心页可以查询到pd信息pd_key= "bASHdc/12ISJOX7pV3qhPr2ntQ6QcEkV"app_id= "100001"#开发者分成用的账号,在开发者中心可以查询到app_key = "123456"#识别类型,#具体类型可以查看官方网站的价格页选择具体的类型,不清楚类型的,可以咨询客服pred_type = "30400"api = FateadmApi(app_id, app_key, pd_id, pd_key)# 查询余额balance = api.QueryBalcExtend() # 直接返余额# api.QueryBalc()# 通过文件形式识别:file_name = 'img.gif'# 多网站类型时,需要增加src_url参数,具体请参考api文档: /web/#/1?page_id=6# result = api.PredictFromFileExtend(pred_type,file_name) # 直接返回识别结果rsp = api.PredictFromFile(pred_type, file_name) # 返回详细识别结果'''# 如果不是通过文件识别,则调用Predict接口:# result = api.PredictExtend(pred_type,data) # 直接返回识别结果rsp = api.Predict(pred_type,data)# 返回详细的识别结果'''just_flag = Falseif just_flag :if rsp.ret_code == 0:#识别的结果如果与预期不符,可以调用这个接口将预期不符的订单退款# 退款仅在正常识别出结果后,无法通过网站验证的情况,请勿非法或者滥用,否则可能进行封号处理api.Justice( rsp.request_id)#card_id = "123"#card_key = "123"#充值#api.Charge(card_id, card_key)LOG("print in testfunc")if __name__ == "__main__":TestFunc()

关于Python技术储备

学好 Python 不论是就业还是做副业赚钱都不错,但要学会 Python 还是要有一个学习规划。最后大家分享一份全套的 Python 学习资料,给那些想学习 Python 的小伙伴们一点帮助!

一、Python所有方向的学习路线

Python所有方向的技术点做的整理,形成各个领域的知识点汇总,它的用处就在于,你可以按照上面的知识点去找对应的学习资源,保证自己学得较为全面。(文末获取!)

温馨提示:篇幅有限,已打包文件夹,获取方式在“文末”!!!

二、Python必备开发工具

三、精品Python学习书籍

当我学到一定基础,有自己的理解能力的时候,会去阅读一些前辈整理的书籍或者手写的笔记资料,这些笔记详细记载了他们对一些技术点的理解,这些理解是比较独到,可以学到不一样的思路。

四、Python视频合集

观看零基础学习视频,看视频学习是最快捷也是最有效果的方式,跟着视频中老师的思路,从基础到深入,还是很容易入门的。

五、实战案例

光学理论是没用的,要学会跟着一起敲,要动手实操,才能将自己的所学运用到实际当中去,这时候可以搞点实战案例来学习。

六、Python练习题

检查学习结果。

七、面试资料

我们学习Python必然是为了找到高薪的工作,下面这些面试题是来自阿里、腾讯、字节等一线互联网大厂最新的面试资料,并且有阿里大佬给出了权威的解答,刷完这一套面试资料相信大家都能找到满意的工作。

这份完整版的Python全套学习资料已经上传CSDN,朋友们如果需要可以微信扫描下方CSDN官方认证二维码免费领取【保证100%免费

如果觉得《用Python自动识别验证码(完整教程 陆续更新12306验证码识别 抢票)》对你有帮助,请点赞、收藏,并留下你的观点哦!

本内容不代表本网观点和政治立场,如有侵犯你的权益请联系我们处理。
网友评论
网友评论仅供其表达个人看法,并不表明网站立场。