现在的日常生活已经离不开微信,本文将会抛砖引玉演示如何使用 Python 调用微信 API 做一些有意思的东西。
看完这一系列教程,你就能从头开始实现自己关于微信的想法。
本文为教程的第二部分,主要以微信控制器、群发助手、好友删除检测为例演示如何调用微信 API 。
Python 基础并不困难,所以即使没有这方面基础辅助搜索引擎也完全可以学习本教程。
关于本教程有任何建议或者疑问,都欢迎邮件与我联系( [email protected] ),或者在github上提出。
当然最近我们新建了一个 itchat 使用的交流群,欢迎加入: 549762872 。
这一系列教程从如何分析微信协议开始,第一部分教你如何从零开始获取并模拟扩展个人微信号所需要的协议。
第二部分将会就这些协议进行利用,以各项目为例介绍一些微信有意思功能的实现。
第三部分就协议的一些高级用法进行介绍,对框架做进一步介绍与扩展。
本文为教程的第二部分。
完成了本文的学习,你将会完成三个小项目:(出于方便二次阅读,括号中都放上了源码链接)
使用微信协议完成机器人较为平常,如果对具体细节感兴趣,可以添加个人号littlecodersh
并回复“源代码”。
本文主要基于微信 API 的第三方包 itchat ,你可以在项目主页获取更多信息。
本文是这一教程的第二部分,需要基本的 pip 可用的 Python 环境。
本教程使用的环境如下:
在项目主页上,专门有人就微信作为智能家居入口向我提出了很多想法。
如果微信可以作为控制器,就可以不必自制手机端客户端的麻烦。
其实这个需求实现起来非常简单,这里我借鉴了 yaphone 的RasWxMusicbox,使用了其中部分的代码作为演示。
这是一个通过微信控制电脑播放音乐的小项目,那么主要就是三个功能:
换成代码就是这样一个逻辑:
if msg == u'关闭':
close_music()
print(u'音乐已关闭')
if msg == u'帮助':
print(u'帮助信息')
else:
print(interact_select_song(msg))
那么现在需要解决的就是如何关闭音乐,如何选择音乐和如何使用微信交互。
关闭音乐我们这里使用打开空文件的方式,而选择音乐我们使用网易云音乐的 API 完成:
import os
# 通过该命令安装该 API : pip install NetEaseMusicApi
from NetEaseMusicApi import interact_select_song
with open('stop.mp3', 'w') as f: pass
def close_music():
os.startfile('stop.mp3')
而微信的调用可以通过 itchat 包简单的完成,这里要注意的是:
# 接上段程序
# 通过该命令安装该 API : pip install itchat
import itchat
@itchat.msg_register(itchat.content.TEXT)
def music_player(msg):
if msg['ToUserName'] != 'filehelper': return
if msg['Text'] == u'关闭':
close_music()
itchat.send(u'音乐已关闭', 'filehelper')
if msg['Text'] == u'帮助':
itchat.send(u'帮助信息', 'filehelper')
else:
itchat.send(interact_select_song(msg['Text']), 'filehelper')
itchat.auto_login(True)
itchat.send(HELP_MSG, 'filehelper')
itchat.run()
itchat 对常用功能都做好了封装,调用还是非常容易的。
完整的程序我放在了gist上面,使用时不要忘记安装第三方包。
通过与文件传输助手的交互,微信就能够轻松变成其他程序的入口。
在短信的时代,逢年过节都会需要接收和发送大量的短信。
虽然自己也看到短信就烦,但不发又怕会错过什么。
所以当时就产生了各式各样的群发工具,最简单的比如在消息中加入昵称,让人感觉不像群发。
不过可惜的是,微信自带的群发助手真的只是群发。
当然,稍加操作,一切皆有可能。
例如在消息中加入昵称:
get_friends
方法可以轻松获取所有的好友(好友首位是自己)itchat.send
改为print
即可#coding=utf8
import itchat, time
itchat.auto_login(True)
SINCERE_WISH = u'祝%s 新年快乐!'
friendList = itchat.get_friends(update=True)[1:]
for friend in friendList:
# 如果是演示目的,把下面的方法改为 print 即可
itchat.send(SINCERE_WISH % (friend['DisplayName']
or friend['NickName']), friend['UserName'])
time.sleep(.5)
又例如给特定的人发送特定的消息。
我们这里通过群聊实现,划定一个群聊,在群聊内则私信发送祝福。
update_chatroom
更新用户列表itchat.send
改为print
即可#coding=utf8
import itchat, time
itchat.auto_login(True)
REAL_SINCERE_WISH = u'祝%s 新年快乐!!'
chatroomName='wishgroup'
itchat.get_chatrooms(update=True)
chatrooms = itchat.search_chatrooms(name=chatroomName)
if chatrooms is None:
print(u'没有找到群聊:' + chatroomName)
else:
chatroom = itchat.update_chatroom(chatrooms[0]['UserName'])
for friend in chatroom['MemberList']:
friend = itchat.search_friends(userName=friend['UserName'])
# 如果是演示目的,把下面的方法改为 print 即可
itchat.send(REAL_SINCERE_WISH % (friend['DisplayName']
or friend['NickName']), friend['UserName'])
time.sleep(.5)
所以我的通讯录里会有从来不用的客户群、教师群什么的。
完整的程序我放在了gist上面,使用时不要忘记安装第三方包。
当然,为了防止误操作,完整程序中我把所有的itchat.send
换成了print
。
另外,不只有文字可以发送,文件、图片也都是可行的,具体操作见 itchat 的文档了。
itchat 获取微信可以获取到的各种内容也都非常方便。
其余的例如生日,节日什么的就看具体需求了。
有时候我们会想知道某个好友有没有删除自己或者把自己拉入黑名单。
这一操作使用 itchat 也会变的非常简单。
原理的话,在于将好友拉入群聊时,非好友和黑名单好友不会被拉入群聊。
所以群聊的返回值中就有了好友与你关系的数据。
另外,群聊在第一次产生普通消息时才会被除创建者以外的人发现的(系统消息不算普通消息)。
这样,就可以隐蔽的完成好友检测。
写成代码的话,这个操作就是这样的:(只是演示,不能运行,运行版本在段末)
chatroomUserName = '@1234567'
friend = itchat.get_friends()[1]
r = itchat.add_member_into_chatroom(chatroomUserName, [friend])
if r['BaseResponse']['ErrMsg'] == '':
status = r['MemberList'][0]['MemberStatus']
itchat.delete_member_from_chatroom(chatroom['UserName'], [friend])
return { 3: u'该好友已经将你加入黑名单。',
4: u'该好友已经将你删除。', }.get(status,
u'该好友仍旧与你是好友关系。')
其中,通过add_member_into_chatroom
操作获取我们需要的返回值,即可得到好友的状态。
同样的,这次我们也将文件传输助手作为终端,具体方法与控制器一节类似。
这次我们确定的交互方式是接收“名片”消息,并判断名片中的好友与自己的关系。
那么获取名片信息的内容可以这么写:
import itchat
@itchat.msg_register(itchat.content.CARD)
def get_friend(msg):
if msg['ToUserName'] != 'filehelper': return
friendStatus = get_friend_status(msg['RecommendInfo'])
itchat.send(friendStatus['NickName'], 'filehelper')
itchat.auto_login(True)
itchat.run()
那么我们所需要的所有部分就都解决了,下面将他们组合起来即可。
完整的程序我放在了gist上面,使用时不要忘记安装第三方包。
在网页版微信的接口受到限制之前完全可以批量进行这一操作,检测哪些好友删除了自己。
但目前显然操作存在频率限制,所以只能做一些变通了。
到这里这一篇文章的主要内容就结束了。
主要从微信作为终端使用、自定义的消息交互、微信协议研究三方面开了一个简单的头。
其余有一些过于大众,如机器人,就不再赘述。
而另一些,需要一定的基础或者不适合分享,就留给各位自行研究。
如果要留个悬念,可以想象添加好友的方法 status 传 2 ,轻松实现好友病毒式扩张。
利用微信的 API 可以做很多事情,文档我放在这里,祝好运!
希望读完这篇文章能对你有帮助,有什么不足之处万望指正(鞠躬)。
有什么想法或者想要关注我的更新,欢迎来Github上Star或者Fork。
161015
LittleCoder
EOF
1
AZLisme 2016-10-15 08:39:42 +08:00
send 方法只有 toUserName?
假如想给群聊发送消息怎么做呢?谢谢 |
2
AZLisme 2016-10-15 08:44:34 +08:00 via iPhone
研究出来了, ChatRoom 也有个特殊的 UserName
|
3
NxnXgpuPSfsIT OP 对的,我这里还处理了群聊消息发送消息人的对应 UserName ,在 ActualUserName 键里面。
|
5
NxnXgpuPSfsIT OP @likai 哈哈,好的
|
6
102400 2016-10-15 16:48:12 +08:00
这接口不太稳定,经常莫名其妙掉线
|
7
NxnXgpuPSfsIT OP |
8
102400 2016-10-15 16:58:59 +08:00
@NxnXgpuPSfsIT 难道是我服务器的问题?我看 log 都是接受某个消息时报错然后退出
|
9
NxnXgpuPSfsIT OP @102400 你可以把报错信息贴一下
|
10
102400 2016-10-15 17:03:57 +08:00
@NxnXgpuPSfsIT 另外,我用的是 QCloud ,我看一休里面很多人都是掉线
|
11
102400 2016-10-15 17:05:02 +08:00
@NxnXgpuPSfsIT 上个月的事了,试了后感觉不能长期做 Robot 后我就删了
|
12
NxnXgpuPSfsIT OP @102400 就从你的描述来看,是接收某个消息时报错。
就这个特征,比较可能的情况是你的调用出错抛出了异常。 我向你保证这个接口的稳定,如果你还有需求欢迎再次你尝试。 另,尝试的过程中碰到问题希望还是报 issue ,否则很可能产生不必要的误解。 |
13
102400 2016-10-15 17:15:22 +08:00
@NxnXgpuPSfsIT 我今晚试试用 py3 ,有问题再去加群报告?
|
14
NxnXgpuPSfsIT OP @102400 你看到的那个 issue 应该就是我开的专门处理这个问题的 issue ,你看一下最新进展,这个问题已经解决了。
|
15
NxnXgpuPSfsIT OP @102400 好,随时欢迎!
|
16
nellace 2016-10-15 17:36:53 +08:00
以前 star 这个项目 https://github.com/0x5e/wechat-deleted-friends
据说现在已经没办法看好友是否删除了 |
17
NxnXgpuPSfsIT OP @nellace 可以的,但是接口限制变得很严格,没法大批量的检测了。
|
18
pasturn 2016-10-15 20:47:42 +08:00 via iPhone
只想知道有没有能够实现自动定时转发某公众号的文章功能
|
19
zhangneww 2016-10-16 00:41:24 +08:00
我只想知道能够坚持在线多久
|
20
NxnXgpuPSfsIT OP |
21
coolloves 2016-10-16 08:36:59 +08:00 via Android
mark,感觉分享
|
22
Echoldman 2016-10-16 08:52:29 +08:00
教程会在 github 上更新吗
|
23
NxnXgpuPSfsIT OP @Echoldman 会在文档那里更新的
|
24
regent 2016-10-16 09:53:07 +08:00 via iPhone
谢谢,研究一下看
|
25
klausgao 2016-10-16 14:32:59 +08:00 via iPhone
楼主,我是在那条研究稳定在线的 issue 里的其中一位,现在也有半个月没掉线了😄
|
26
blueset 2016-10-16 18:08:24 +08:00
感谢楼主分享。忽然发现大概六七个月前 Fork 走魔改的那个微信 API 就是楼主的作品。当时还自己翻译了 Python 3 的版本,加了一些 Feature (终端二维码之类的)。
这次才发现半年来更新了不少,是时候重新 Pull 来更新了。 |
27
blueset 2016-10-16 18:15:55 +08:00
顺便问一下,微信网页 API 有提供那种重启后不会变的用户唯一 ID 吗?每次重启完之后用户的 UserName 都是不一样的。
|
28
NxnXgpuPSfsIT OP @klausgao 哈哈,好的,能解决这个问题都要感谢你们的支持!
|
29
NxnXgpuPSfsIT OP @blueset 魔改的功能和我后来加的差的不多呀,如果 pr 了多好呢!
目前好友的话可以通过 set_alias 设置昵称变相达到这个目的。 相对来说公众号的话这个功能就原生支持,我最近在写一个类似的项目 itchatmp ,可能能更方便的满足这个需求,这个项目可以在我的主页上找到。 |
30
blueset 2016-10-16 21:15:49 +08:00
@NxnXgpuPSfsIT 本来是想改完善些之后一起 PR 的,结果中间开始申请大学就耽误了。后来连同那个 Tunnel Bot 一起搁置在了那边,一直没有时间继续做。
|
31
NxnXgpuPSfsIT OP @blueset 好,之后有时间欢迎继续魔改了 pr
|
32
kangsgo 2016-10-17 00:01:26 +08:00
收藏了,非常感谢分享,虽然还没有看的特别明白,可能是新手的原因,改天认真阅读
|
33
xxstop 2016-10-17 12:33:27 +08:00
mark 正准备使用
|
35
GreatMartial 2016-10-18 00:19:40 +08:00 via Android
能写个微信内的语音助手吗?
我看着别人博客分享的代码,写了个语音输入,调用图灵机器人文字输出的项目,后边想改进一下,把返回的文字利用百度的语音合成 API 返回给微信,可是我自己写不出来,大大有兴趣做这个项目吗? |
36
NxnXgpuPSfsIT OP @oliver134 你可以开个 issue 把代码贴一下
|
37
NxnXgpuPSfsIT OP @GreatMartial 你想要写的话可以邮件或者加 q 群联系我,我给你一些指导
|
38
GreatMartial 2016-10-18 12:17:39 +08:00
@NxnXgpuPSfsIT 谢谢大大回复,我加 qq 群咨询你 O(∩_∩)O
|
39
baiyuexingchen 2017-10-03 10:35:00 +08:00
现在有新的版本删除好友的代码吗
|