简单的模拟:借用微信网页版,写个扫码页面,登录页面,实现简单的登录、联系人列表、发消息,收消息。

以下是笔记:

#!/usr/bin/env python
# coding:utf-8from flask import Flask, render_template, request, session, jsonify,redirect,url_for
import time, re, requests, json
from bs4 import BeautifulSoupapp = Flask(__name__)
app.debug = True
app.secret_key = "LSHM"  # 使用session必须要有key# xml转变字典函数
def xml_parser(text):dic = {}soup = BeautifulSoup(text, 'html.parser')div = soup.find(name='error')# for item in div.children(recursive=False): # 不使用children, 因为它会找文本, find_all则只找标签for item in div.find_all(recursive=False):  # 不使用递归,也就是只找儿子dic[item.name] = item.textreturn dic@app.route('/')
def home():return redirect(url_for('login'))@app.route('/login', methods=['GET', 'POST'])
def login():if request.method == "GET":ctime = str(int(time.time() * 1000))qrcode_url = "https://login.wx.qq.com/jslogin?appid=wx782c26e4c19acffb&redirect_uri=https%3A%2F%2Fwx.qq.com%2Fcgi-bin%2Fmmwebwx-bin%2Fwebwxnewloginpage&fun=new&lang=zh_CN&_={}".format(ctime)ret = requests.get(qrcode_url)# print(ret.text)qrcode = re.findall('uuid = "(.*)";', ret.text)[0]# print(qrcode)session['qrcode'] = qrcodereturn render_template("login.html", qr=qrcode)else:pass@app.route('/check_login')
def check_login():'''发送GET请求,检测是否已经扫码、登录https://login.wx.qq.com/cgi-bin/mmwebwx-bin/login?loginicon=true&uuid=IY02Sx7eyQ==&tip=0&r=-1908176756&_=1530916511143:return:'''response = {"code": 408}qrcode = session.get("qrcode")ctime = str(int(time.time() * 1000))check_url = "https://login.wx.qq.com/cgi-bin/mmwebwx-bin/login?loginicon=true&uuid={0}&tip=0&r=-1908176756&_={1}".format(qrcode, ctime)# time.sleep(10)ret = requests.get(check_url)# print(ret.text)if "window.code=201" in ret.text:  # 扫码成功src = re.findall("window.userAvatar = '(.*)';", ret.text)[0]response["code"] = 201response["src"] = srcelif "window.code=200" in ret.text:  # 确认登录redirect_uri = re.findall('window.redirect_uri="(.*)";', ret.text)[0]  # 获取重定向地址# 向上面的地址发送请求, 添加2个必要的参数redirect_uri = redirect_uri + "&fun=new&version=v2"ticket_ret = requests.get(redirect_uri)  # 获取凭证ticket_dict = xml_parser(ticket_ret.text)  # 拿到字典# print(ticket_dict)session["ticket_dict"] = ticket_dict  # 存入sessionsession["ticket_cookie"] = ticket_ret.cookies.get_dict()  # 保存cookie 给后面使用response["code"] = 200return jsonify(response)@app.route("/index")
def index():'''用户数据初始化https://wx.qq.com/cgi-bin/mmwebwx-bin/webwxinit?r=-1912609442&pass_ticket=v8tvMrwfudoYLl0dyHNIX5QtJe4BtO%252FGoffihP5Ion0oScWCAU%252F18Avj6ZL1rj%252B6:return:'''ticket_dict = session.get("ticket_dict")init_url = "https://wx.qq.com/cgi-bin/mmwebwx-bin/webwxinit?r=-1912609442&pass_ticket={0}".format(ticket_dict.get("pass_ticket"))data_dict = {"BaseRequest": {"DeviceID": "e261019482970229","Sid": ticket_dict.get("wxsid"),"Uin": ticket_dict.get("wxuin"),"Skey": ticket_dict.get("skey"),}}init_ret = requests.post(url=init_url,json=data_dict,  # Payload 对应传json# data=json_dumps(data_dict), # 使用这种方式,必须要带上headers# headers={#     'Content-Type':'application/json'# })init_ret.encoding = "utf-8"# print(init_ret.text)# print(init_ret.json()) # print(json.loads(init_ret.text))user_dict = init_ret.json()# print(user_dict)# for user in user_dict['ContactList']: # 最近 联系人列表#     print(user.get('NickName'))session["current_user"] = user_dict['User']# print(user_dict['SyncKey'])session["SyncKey"] = user_dict['SyncKey']# return "用户首页"return render_template('index.html', user_dict=user_dict)@app.route("/get_img")
def get_img():# 获取头像current_user = session.get("current_user")ticket_cookie = session.get("ticket_cookie")head_url = "https://wx.qq.com" + current_user["HeadImgUrl"]img_ret = requests.get(head_url, cookies=ticket_cookie, headers={"Content-Type": "image/jpeg"})return img_ret.content  # 直接返回字节@app.route("/user_list")
def user_list():ticket_dict = session.get("ticket_dict")ticket_cookie = session.get("ticket_cookie")ctime = int(time.time() * 1000)skey = ticket_dict.get('skey')user_list_url = "https://wx.qq.com/cgi-bin/mmwebwx-bin/webwxgetcontact?lang=zh_CN&r={0}&seq=0&skey={1}".format(ctime, skey)r1 = requests.get(user_list_url, cookies=ticket_cookie)r1.encoding = "utf-8"wx_user_dict = r1.json()print(wx_user_dict['MemberCount'])for item in wx_user_dict['MemberList']:print(item)return render_template("user_list.html", wx_user_dict=wx_user_dict)## 发消息的话:需要自己的UserName和对方的UserName
@app.route("/send", methods=["GET", "POST"])
def send():if request.method == "GET":return render_template('send.html')ticket_dict = session.get("ticket_dict")current_user = session["current_user"]from_user = current_user['UserName']to = request.form.get('to')content = request.form.get('content')ctime = str(time.time() * 1000)msg_url = "https://wx.qq.com/cgi-bin/mmwebwx-bin/webwxsendmsg?lang=zh_CN&pass_ticket={}".format(ticket_dict['pass_ticket'])data_dict = {"BaseRequest": {"DeviceID": "e261019482970229","Sid": ticket_dict.get("wxsid"),"Uin": ticket_dict.get("wxuin"),"Skey": ticket_dict.get("skey"),},"Msg": {"ClientMsgId": ctime,"FromUserName": from_user,"LocalID": ctime,"ToUserName": to,"Content": content,"Type": 1},"Scene": 0}ret = requests.post(url=msg_url,data=bytes(json.dumps(data_dict, ensure_ascii=False), encoding="utf-8"))print(ret.text)response ={}response['to'] = toresponse['content'] = contentresponse['status'] = "成功"return jsonify(response)@app.route("/recv", methods=["GET", "POST"])
def recv():# https://wx.qq.com/cgi-bin/mmwebwx-bin/webwxsync?sid={0}&skey={1}&pass_ticket={2}sync_url = "https://webpush.weixin.qq.com/cgi-bin/mmwebwx-bin/synccheck"synckey = session.get("SyncKey")# print(synckey['List'])ticket_dict = session.get("ticket_dict")ticket_cookie = session.get("ticket_cookie")ctime = str(int(time.time() * 1000))sync_data_list = []for item in synckey['List']:temp = "%s_%s" % (item['Key'], item['Val'])sync_data_list.append(temp)sync_data_str = "|".join(sync_data_list)sync_dict = {"r": ctime,"skey": ticket_dict['skey'],"sid": ticket_dict['wxsid'],"uin": ticket_dict['wxuin'],"deviceid": "e261019482970229","synckey": sync_data_str,}response_sync = requests.get(sync_url, params=sync_dict, cookies=ticket_cookie)# print(response_sync.text)if 'selector:"2"' in response_sync.text:# https://wx.qq.com/cgi-bin/mmwebwx-bin/webwxsync?sid={}&skey={}&lang=zh_CN&pass_ticket={}fetch_msg_url = "https://wx.qq.com/cgi-bin/mmwebwx-bin/webwxsync?sid={0}&skey={1}&lang=zh_CN&pass_ticket={2}".format(ticket_dict['wxsid'], ticket_dict['skey'], ticket_dict['pass_ticket'])form_data = {'BaseRequest': {'DeviceID': 'e261019482970229','Sid': ticket_dict['wxsid'],'Skey': ticket_dict['skey'],'Uin': ticket_dict['wxuin']},'SyncKey': synckey,'rr': ctime}response_fetch_msg = requests.post(fetch_msg_url,json=form_data,headers={'Connection':'keep-alive','Accept-Encoding':'gzip, deflate, br','X-Requested-With':'XMLHttpRequest','user-agent': 'Mozilla/5.0 (Windows NT 6.1; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/67.0.3396.99 Safari/537.36'},cookies=ticket_cookie,)response_fetch_msg.encoding = 'utf-8'res_fetch_msg_dict = response_fetch_msg.json()session["SyncKey"] = res_fetch_msg_dict['SyncKey']response={}if res_fetch_msg_dict:for item in res_fetch_msg_dict['AddMsgList']:response['content'] = item['Content']response['FromUserName'] = item['FromUserName']response['ToUserName'] = item['ToUserName']return jsonify(response)# return render_template("send.html", res_fetch_msg_dict=res_fetch_msg_dict)else:return "ok"if __name__ == '__main__':app.run()

运行项目(manage.py)后,将自动跳转到login页面,
扫码登录后,会获得个人信息,可以点击 查看所有联系人 ,然后可以在此页面点击 发消息 
进入发消息页面,目前只能按UserName来发,未实现按昵称发送。

如果有消息来,可以在收到消息部分看到对方的UserName和消息内容

已知问题:
收消息经常会卡住,
或者报错: requests.exceptions.ConnectionError: ('Connection aborted.', BadStatusLine('HTTP/1.1 0 -\r\n',))

找不出原因。

提交作业后,指导老师给予回复:

感觉自己还差得远呢。

1.我觉得你第26行代码没有必要存在的,你可以在27行代码哪里@app.route('/')加一个就好了2.我觉得你第33行代码那里还是有问题的,因为这么写字符串太长了不符合pep8规范不说也不好阅读,我觉得你可以定义成下面字典的格式,{'loginicon': 'true','uuid': session['qrcode'],'tip': 0,'r': '-2034746127',  # 时间戳取反'_': int(time.time() * 1000)
}response = requests.get(url=check_login_url, params=‘这个字典’) 这样代码是不是会很舒服3.还有你第53行代码是不是应该也是int(time.time()*1000)这样去写的?4.你的第72行代码是不是应该join一下去拼接。5.你的try处理还是没有6.你在@app.route("/recv")里是能够写更多的。比如图片语音消息的判断对不对,还有你在这里提交消息格式应该严格安装微信的来。7.代码的优化这里不多说什么了,有问题和我沟通。

转载于:https://www.cnblogs.com/FHBIAO/p/10174560.html

python爬虫基础_webwechat相关推荐

  1. python基础代码库-python爬虫基础教程:requests库(二)代码实例

    get请求 简单使用 import requests ''' 想要学习Python?Python学习交流群:973783996满足你的需求,资料都已经上传群文件,可以自行下载! ''' respons ...

  2. python基础知识整理-python爬虫基础知识点整理

    首先爬虫是什么? 网络爬虫(又被称为网页蜘蛛,网络机器人,在FOAF社区中间,更经常的称为网页追逐者),是一种按照一定的规则,自动的抓取万维网信息的程序或者脚本. 根据我的经验,要学习Python爬虫 ...

  3. python爬虫基础(一)~爬虫概念和架构

    目录 1. 爬虫 1.1 概念 1.2 分类 2. 爬虫架构 2.1 url管理器 2.2 网页(html)下载(download)器 2.2.1 urllib下载html源码 2.2.2 reque ...

  4. 掌握Python爬虫基础,仅需1小时!

    随着互联网的发展,google.百度等搜索引擎让我们获取信息愈加方便.但需求总会不断涌现,纯粹地借助百度等收集信息是远远不够的,因此编写爬虫爬取信息的重要性就越发凸显. 比如有人为了炒股,专门爬取了多 ...

  5. Day2:python爬虫基础学习(大嘘)

    Day2:python爬虫基础学习(大嘘)) 教材&参考: 学习过程 Sublime配置教程 下载&安装 语言(设置中文) 设置字体/配色 配置Python环境 使用python官方编 ...

  6. python爬虫——基础知识

    python爬虫--基础知识 一.网页基础知识 二.爬虫的思路 1.HTML文档(超文本) 三.ROBOTS协议 四.浏览器发送HTTP请求的过程 1.http请求过程 2.请求 五.SSL连接错误 ...

  7. 结构化数据丨Python爬虫基础入门系列(7)

    提示:文末有福利!最新Python爬虫资料/学习指南>>戳我直达 文章目录 前言 JSON 1. json.loads() 2. json.dumps() 3. json.dump() 4 ...

  8. python爬虫基础(二)

    文章目录 python爬虫 1.异步爬虫 异步爬虫之多进程and多线程(不建议使用) 异步爬虫之线程池and进程池(适当使用) 单线程+异步协程(推荐) 补充:回调函数 补充:yield 多任务异步协 ...

  9. Python爬虫基础-如何获取网页源代码

    Python爬虫基础-如何获取网页源代码 网络爬虫(Web Crawler),又称网页蜘蛛(Web Spider),是一种按照一定的规则,自动地抓取万维网信息的程序或者脚本.爬虫程序根据一组特定的规则 ...

最新文章

  1. python的image读取的图片是什么类型的-opencv python 读取图像/显示图像/保存图像...
  2. java日志处理汇总
  3. .net core中使用缓存(cache)
  4. 前端开发必须要了解的CSS原理
  5. java ocr linux_linux系统如何使用tess4j(java)进行ocr图片文字识别
  6. PHP三年15K,程序员月薪15K相亲三年才成功,被拒理由:这个薪资提鞋都嫌弃
  7. 11.15PMP试题每日一题
  8. (转自dflying chen)使用Anthem.NET 1.5中的FileUpload控件实现Ajax方式的文件上传
  9. Tensorflow学习笔记:使用线性回归进行简单分类
  10. 暴风影音3 Build version : 3.7.11.13 漏洞
  11. 走进小作坊(十四)----web2.0策略指南
  12. win10打开计算机出现马赛克,传授win10系统在线播放视频出现马赛克的技巧
  13. GIS数据在哪里下载
  14. NodeJS 服务 Docker 镜像极致优化指北
  15. Android开发:一个TextView中设置文字不同字体大小和颜色的2种高效方法
  16. Cookie、Session和Token(学习笔记)
  17. Oracle中用户角色权限管理
  18. python微信公众号翻译功能_自学Python笔记:给微信公众号搭建“成绩查询”功能...
  19. c语言一个文件里重复多次定义函数,C语言里的重复定义问题的解决方案
  20. paper 116:自然图像抠图/视频抠像技术梳理(image matting, video matting)

热门文章

  1. windows系统官网下载
  2. 360手机助手如何精简安卓手机系统
  3. 论文阅读《Adapted Deep Embeddings: A Synthesis of Methods for k-Shot Inductive Transfer Learning Tyler》
  4. mitmproxy的安装与使用学习记录(二)
  5. 代码高亮插件SyntaxHighlighter
  6. 马云天价请不动的中国顶级黑客
  7. matlab仿真电气连接,MATLAB-Simulink系统建模仿真工程系列电气装备专业技术人员继续教育...
  8. DIY民间蹭网利器(加强版)
  9. 电脑QQ的信息跟手机不同步的解决办法(2022.7)
  10. 打印机驱动中如何生成证书及签名