撤回的微信消息真的看不到?78行Python代码帮你看穿一切!

640?wx_fmt=gif


导读:Python曾经对我说:"时日不多,赶紧用Python"。于是看到了一个基于python的微信开源库:itchat,玩了一天,做了一个程序,把私聊撤回的信息可以收集起来并发送到个人微信的文件传输助手,包括:


(1) who :谁发送的
(2) when :什么时候发送的消息
(3) what:什么信息
(4) which:哪一类信息,包括:文本、图片、语音、视频、分享、位置、附件
...


01 代码实现


# -*-encoding:utf-8-*-

import os

import re

import shutil

import time

import itchat

from itchat.content import *


# 说明:可以撤回的有文本文字、语音、视频、图片、位置、名片、分享、附件


# {msg_id:(msg_from,msg_to,msg_time,msg_time_rec,msg_type,msg_content,msg_share_url)}

msg_dict = {}


# 文件存储临时目录

rev_tmp_dir = "/home/alic/RevDir/"

if not os.path.exists(rev_tmp_dir): os.mkdir(rev_tmp_dir)


# 表情有一个问题 | 接受信息和接受note的msg_id不一致 巧合解决方案

face_bug = None



# 将接收到的消息存放在字典中,当接收到新消息时对字典中超时的消息进行清理 | 不接受不具有撤回功能的信息

# [TEXT, PICTURE, MAP, CARD, SHARING, RECORDING, ATTACHMENT, VIDEO, FRIENDS, NOTE]

@itchat.msg_register([TEXT, PICTURE, MAP, CARD, SHARING, RECORDING, ATTACHMENT, VIDEO])

def handler_receive_msg(msg):

    global face_bug

    # 获取的是本地时间戳并格式化本地时间戳 e: 2017-04-21 21:30:08

    msg_time_rec = time.strftime("%Y-%m-%d %H:%M:%S", time.localtime())

    # 消息ID

    msg_id = msg['MsgId']

    # 消息时间

    msg_time = msg['CreateTime']

    # 消息发送人昵称 | 这里也可以使用RemarkName备注 但是自己或者没有备注的人为None

    msg_from = (itchat.search_friends(userName=msg['FromUserName']))["NickName"]

    # 消息内容

    msg_content = None

    # 分享的链接

    msg_share_url = None

    if msg['Type'] == 'Text' \

            or msg['Type'] == 'Friends':

        msg_content = msg['Text']

    elif msg['Type'] == 'Recording' \

            or msg['Type'] == 'Attachment' \

            or msg['Type'] == 'Video' \

            or msg['Type'] == 'Picture':

        msg_content = r"" + msg['FileName']

        # 保存文件

        msg['Text'](rev_tmp_dir + msg['FileName'])

    elif msg['Type'] == 'Card':

        msg_content = msg['RecommendInfo']['NickName'] + r" 的名片"

    elif msg['Type'] == 'Map':

        x, y, location = re.search(

            "<location x=\"(.*?)\" y=\"(.*?)\".*label=\"(.*?)\".*", msg['OriContent']).group(1, 2, 3)

        if location is None:

            msg_content = r"纬度->" + x.__str__() + " 经度->" + y.__str__()

        else:

            msg_content = r"" + location

    elif msg['Type'] == 'Sharing':

        msg_content = msg['Text']

        msg_share_url = msg['Url']

    face_bug = msg_content

    # 更新字典

    msg_dict.update(

        {

            msg_id: {

                "msg_from": msg_from, "msg_time": msg_time, "msg_time_rec": msg_time_rec,

                "msg_type": msg["Type"],

                "msg_content": msg_content, "msg_share_url": msg_share_url

            }

        }

    )



# 收到note通知类消息,判断是不是撤回并进行相应操作

@itchat.msg_register([NOTE])

def send_msg_helper(msg):

    global face_bug

    if re.search(r"\<\!\[CDATA\[.*撤回了一条消息\]\]\>", msg['Content']) is not None:

        # 获取消息的id

        old_msg_id = re.search("\<msgid\>(.*?)\<\/msgid\>", msg['Content']).group(1)

        old_msg = msg_dict.get(old_msg_id, {})

        if len(old_msg_id) < 11:

            itchat.send_file(rev_tmp_dir + face_bug, toUserName='filehelper')

            os.remove(rev_tmp_dir + face_bug)

        else:

            msg_body = "告诉你一个秘密~" + "\n" \

                       + old_msg.get('msg_from') + " 撤回了 " + old_msg.get("msg_type") + " 消息" + "\n" \

                       + old_msg.get('msg_time_rec') + "\n" \

                       + "撤回了什么 ⇣" + "\n" \

                       + r"" + old_msg.get('msg_content')

            # 如果是分享存在链接

            if old_msg['msg_type'] == "Sharing": msg_body += "\n就是这个链接➣ " + old_msg.get('msg_share_url')


            # 将撤回消息发送到文件助手

            itchat.send(msg_body, toUserName='filehelper')

            # 有文件的话也要将文件发送回去

            if old_msg["msg_type"] == "Picture" \

                    or old_msg["msg_type"] == "Recording" \

                    or old_msg["msg_type"] == "Video" \

                    or old_msg["msg_type"] == "Attachment":

                file = '@fil@%s' % (rev_tmp_dir + old_msg['msg_content'])

                itchat.send(msg=file, toUserName='filehelper')

                os.remove(rev_tmp_dir + old_msg['msg_content'])

            # 删除字典旧消息

            msg_dict.pop(old_msg_id)



if __name__ == '__main__':

    itchat.auto_login(hotReload=True,enableCmdQR=2)

    itchat.run()

    


该程序可以直接在终端运行,在终端扫码成功够即可登录成功,同时也可以打包在window系统运行(注意修改一下路径,推荐使用相对路径)。


➜  ~ python wx.py

Getting uuid of QR code.

Downloading QR code.

Please scan the QR code to log in.

Please press confirm on your phone.

Loading the contact, this may take a little while.

�[3;J

Login successfully as AlicFeng

Start auto replying.



02 效果图


640?wx_fmt=png



03 itchat


上面都是编程逻辑的小事,我还是记录一下itchat微信这个开源库。


1. 简介


itchat是一个开源的微信个人号接口,使用python调用微信变得非常简单。简单是用itchat代码即可构建一个基于微信的即时通讯,更不错的体现在于方便扩展个人微信的在其他平台的更多通讯功能。


2. 安装


pip3 install itchat


3. itchat - Helloworld


仅仅三行代码发送一条信息给文件传输助手。


import itchat

itchat.auto_login(hotReload=True)

itchat.send('Hello AlicFeng', toUserName='filehelper')


4. 查看客户端


640?wx_fmt=png


学习最重要的还是API说明手册:


Github for itchat:

https://github.com/liduanwei/ItChat

中文API:

http://itchat.readthedocs.io/zh/latest/


来源:

https://www.jianshu.com/p/712d19374b2e

文章版权归原作者所有,转载仅供学习使用,不用于任何商业用途,如有侵权请留言联系删除,感谢合作。

640?wx_fmt=png

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/303404.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

lmbs PHP,PHP 清空 MySql 指定数据表中的所有数据

PHP 清空 MySql 指定数据表中的所有数据PHP 清空 MySql 指定数据表中的所有数据&#xff0c;在烈火小编在网上闲逛时&#xff0c;这是某技术博客的一篇文章&#xff0c;说是文章&#xff0c;并没有文字&#xff0c;只有代码&#xff0c;经过测试可以使用&#xff0c;现在分享给…

全网最通透的“闭包”认知 · 跨越语言

闭包作为前端面试的必考题目&#xff0c;常让1-3年工作经验的JavaScripter感到困惑&#xff0c;其实主流语言都有闭包。今天我们深入聊一聊[闭包]&#xff0c; 查缺补漏&#xff01;1. 以面试题 投石问路 2. 以C#闭包 庖丁解牛 3. 跨越语言 追本溯源 • 头等函数 •…

北大最神博士论文:为什么学校打印店老板大多是湖南人?

导读&#xff1a;北京大学社会学系博士冯军旗的一篇论文&#xff0c;虽然是话题看起来有些奇葩&#xff0c;但仍然考据严谨&#xff0c;很有价值。01 写在前面&#xff08;非论文部分&#xff09;多媒体出版行业中&#xff0c;充满油墨芬芳的印刷总是长盛不衰。特别是在大学校园…

技术分享 | jaeger链路日志实现

源宝导读&#xff1a;随着企业应用越来越复杂&#xff0c;内部的调用链条越来越长&#xff0c;性能问题也变得越来越难以定位和排查&#xff0c;为了应对此问题&#xff0c;我们在移动平台中引入了“jaeger调用链追踪工具”&#xff0c;帮助我们高效定位云端服务的性能问题。本…

IT资料,重磅来袭!

现在IT行业越来越火爆&#xff0c;技术的更新也越来越快&#xff0c;不好好充实自己的话&#xff0c;就会被淘汰。小编这几年一直有意识地收集IT行业相关的资料&#xff0c;现在已经拥有8G左右的资料&#xff0c;如区块链、Python、大数据、人工智能深度学习等方面的资料&#…

荐书 | 10本书给你计算机大师思维

《黑客与画家》作者&#xff1a;保罗格雷厄姆 / 译者&#xff1a;阮一峰美国互联网界如日中天的教父、哈佛大学离经叛道的博士保罗格雷厄姆著作&#xff01;一本书&#xff0c;你不曾想到的视角&#xff0c;彻底颠覆你对世界的认识&#xff01;美国亚马逊、纽约时报超级畅销书&…

php按时间分组的sql语句,(SQL语句)按指定时间段分组统计

---------------------------------------Author : liangCK 梁爱兰--Comment: 小梁 爱 兰儿--Date : 2010-01-02 16:47:10---------------------------------------> 生成测试数据: #tbCREATETABLE#tb(列名1varchar(12),时间datetime)INSERTINTO#tbSELECT03174190188,2009…

NET问答: 说说你对 LookupTKey, TElement 的看法 ?

咨询区 dan-gph&#xff1a;MSND 上对 Lookup 做了如下的解释。Lookup<TKey, TElement> 类似于 Dictionary<TKey,TValue>, 不同点在于 Dictionary<TKey, TValue> 中的key对应的是单个value&#xff0c;而 Lookup<TKey, TElement> 中的 key 对应的是一个…

最多金的编程语言Top10:Python第3,R第10,你猜第1是谁?

导读&#xff1a;如果你还在纠结选哪门编程语言来开启你的码农生涯&#xff0c;这将是你的最佳指南。本文绝非标题党&#xff0c;而是基于大量数据和为期两周的深入探究&#xff0c;在18年初&#xff0c;对IT行业的现状、趋势以及预测进行客观观察&#xff0c;让大家对编程语言…

[转贴]制作windows 2003自动安装盘-集成补丁/Raid及硬件驱动

从事网游行业的工作人员&#xff0c;如果一款游戏上线&#xff0c;必须上大量服务器。用品牌机引导盘装系统&#xff0c;再打个补丁&#xff0c;速度真让人不敢恭维。为了提高效率&#xff0c;就尝试制作一张集成系统补丁/RAID及硬件驱动自动安windows 2003系统盘。下面以品牌机…

4月 .NET 线上 Meetup,快来报名

点击蓝字关注我们.NET 6 preview 2 在3月11日已经发布&#xff0c;.NET 6 将是 .NET Core 3.1 之后的第一个 LTS 版本&#xff0c;也是微软开启全平台统一一个 .NET 计划以来的第一个 LTS 版本&#xff0c;意义不可谓不大&#xff0c;那么 .NET 5/6 又会带来哪些新特性呢&#…

NP完全性理论与近似算法

一、图灵机根据有限状态控制器的当前状态及每个读写头读到的带符号&#xff0c;图灵机的一个计算步可实现下面3个操作之一或全部。改变有限状态控制器中的状态。清除当前读写头下的方格中原有带符号并写上新的带符号。独立地将任何一个或所有读写头&#xff0c;向左移动一个方格…

阿里25k 百度25k,招WPF!

.NET5打通7大开发方向&#xff0c;CLR超高性能&#xff0c;.NET6支持Blazor嵌入WPF&#xff0c;还有MAUI跨平台UI解决方案&#xff0c;都是.NET的利好&#xff0c;也是WPF的利好。牛年跳槽季&#xff0c;.NET在客户端方向一骑绝尘&#xff0c;阿里影视、百度地图&#xff0c;以…

掌握神经网络模型的快捷方式

TensorFlow是Google基于DistBelief进行研发的第二代人工智能学习系统&#xff0c;其命名来源于本身的运行原理。Tensor&#xff08;张量&#xff09;意味着N维数组&#xff0c;Flow&#xff08;流&#xff09;意味着基于数据流图的计算&#xff0c;TensorFlow实际上就是张量从流…

.Net项目模板(Project Template)

你有没有这样的感觉&#xff0c;开启一个新项目时&#xff0c;总是做一堆体力活——项目的结构层次&#xff0c;常用日志库&#xff0c;OpenAPI库&#xff0c;ORM库&#xff0c;的引入&#xff0c;权限认证方式选择添加&#xff0c;配置文件重新归置存放等等。公共框架的部分总…

谈通过测试与失败测试

在软件测试技术中&#xff0c;现有的测试方法、测试技术中均未提及到通过测试与失败测试。 而在实际项目测试过程中&#xff0c;很多项目组却再应用该方法。虽然该方法被采用&#xff0c;但是很多人对通过测试与失败测试理解并不透侧&#xff0c;在实际使用过程中并未按统一的标…

100个微信小程序的源码公开分享

现在微信小程序越来越火&#xff0c;小编一直有意识地收集微信小程序源码&#xff0c;至今已经拥有100个小程序的源码&#xff0c;有gank、LOL战绩查询、百度小说、豆瓣电影、手势解锁等。现在&#xff0c;小编准备将这些资料免费分享给大家&#xff01;gankLOL战绩查询百度小说…

家里在一二线城市有很多套房是什么体验?答案太颠覆!

作者&#xff1a;匿名来源&#xff1a;知乎&#xff08;图片&#xff1a;网络&#xff09;“家里在一二线城市有很多套房是怎么的一种体验&#xff1f;”这是知乎上一个浏览超600万的话题。其中一个答案非常颠覆&#xff0c;获得高赞。作者的观点是否正确见仁见智&#xff0c;但…

希尔排序听起来有点难,其实很简单

前言直接插入排序当待排序数据的顺序和期望排序结果相反时&#xff0c;排序效率是最差的&#xff1b;上次聊到的折半插入排序只是减少有序列表的比较次数&#xff0c;而对于整体数据遍历次数还是没有得到优化&#xff1b;接下来要说的希尔排序就是针对整体数据进行优化&#xf…

等我敲完这行代码,就和你离婚!

工作是高端大气上档次&#xff0c;工资是低调奢华接地气&#xff01;我们叫做“程序猿”&#xff0c;也叫“攻城狮”&#xff01;但是往往城还没攻下来&#xff0c;我们的头发就先掉下来&#xff01;我们最喜欢听的一句话就是☟段子一“等我敲完这行代码&#xff0c;就和你离婚…