如何用python70行写出一个微信机器人

前几天朋友给我发了一篇文章 [干货] 基于 itchat, 用 Python 玩微信.
看了下还挺有趣的,本打算完成这篇文章作者未完成的需求,后又稍加修改。

现已完成的功能

1.每天早上发送天气信息到指定的微信上面。
2.跟上面差不多,每天定时发送消息到制定微信,消息自定义
3.私聊给机器人发送(时间),机器人会回复当前时间。
4.群聊给机器人发送(时间),机器人会回复当前时间。


解析天气api

首先完成定时发送天气信息的条件就是,手头得有天气信息,所以我们需要获取天气信息,下面是api http://wthrcdn.etouch.cn/weather_mini?city=
比如获取北京的天气情况 后面就加上北京 http://wthrcdn.etouch.cn/weather_mini?city=北京
返回Json格式 utf-8编码 会返回前一天以及最近一周的天气
这里我们需要引用
import requests
下面是解析的代码

r = requests.get('http://wthrcdn.etouch.cn/weather_mini?city=%E5%91%BC%E5%85%B0')
    tqjson = r.json()
    rgx = re.compile("\<\!\[CDATA\[(.*?)\]\]\>")#正则
    high = tqjson['data']['forecast'][0]['high']#最高温
    low = tqjson['data']['forecast'][0]['low']#最低温
    type = tqjson['data']['forecast'][0]['type']#天气类型 晴 多云等
    fengxiang = tqjson['data']['forecast'][0]['fengxiang']#风向
    fengli = rgx.search(tqjson['data']['forecast'][0]['fengli']).group(1).replace('<','小于').replace('>','大于')
    tishi = tqjson['data']['ganmao'];#提示感冒等信息
    msg = '今日天气:'+ type +'\n最高温度:'+ high + '\n最低温度:' + low + '\n风向:' + fengxiang + "    " + fengli + '\n' + tishi

msg就是需要发送到微信上面的信息了

发送消息

天气信息已经有了,接下来就该要发送了。
首先先创建一个字典保存用户名和id,以后用来 备注姓名查询用户id
代码如下

friends = itchat.get_friends()[0:]
    friends_name = {}
    for i in friends:
        if i["RemarkName"]:
            if i["RemarkName"] not in friends_name:
                friends_name[i["RemarkName"]] = i["UserName"]
    return friends_name

接下来就是发送
itchat.send_msg(msg, friends_name["刘警暄"])
上面这条就是把msg发送个 ‘刘警暄’ (刘警暄 是我微信好友的一个备注,前面的字典就是用备注来查询用户id的)

定时发送

现在发送已经可以了,还差定时发送,开始ChaBug发布文章的作者思路是 while 死循环
每循环一次sleep 60毫秒 也就是一分钟,之后判断 小时和分钟是否位想要发送的时间
如果while循环会堵塞线程,导致itchat.run无法运行,也就是过一段时间就会掉线
并且 要是那样写就只能定时发送消息 干不了别的了,比如获取消息之后判断等等。
解决方法如下

def send_time():
    #print('Hello Timer!')
    time_now = time.strftime('%H%M',time.localtime(time.time()))
    #print(time_now)
    if int(time_now) == 600:
        itchat.send_msg(init_tq(), init_friends()["刘警暄"])#发送天气信息
    if int(time_now) == 1130:
        itchat.send_msg('十一点半了该吃午饭了', init_friends()["刘警暄"])
    if int(time_now) == 1330:
        itchat.send_msg('下午一点半了,上班啦.', init_friends()["刘警暄"])
    if int(time_now) == 1725:
        itchat.send_msg('还有五分钟就下班啦,收拾东西准备撤啦.', init_friends()["刘警暄"])
    global timer
    timer = threading.Timer(60, send_time)#每分钟判断一次
    timer.start()

timer = threading.Timer(1, send_time)
timer.start()

这样一来我们的每天定时发送就完成了,但是还是有一个问题,今天发送的跟明天发送的数据是一样的,数据没有刷新。
这个问题后面会解决。


自动回复

获取私聊消息并回复

作为一个机器人,不会对话怎么能行?
所以 我们要让他 活起来~
首先是获取私聊发送的消息

@itchat.msg_register([TEXT, MAP, CARD, NOTE, SHARING])#处理私聊
def text_reply(msg):

之后开始判断
if msg['Type'] == 'Text':#如果消息类型是文本
if msg['Text'] == '时间':如果文本内容为时间两个字

   `itchat.send(u'当前时间: %s' % time.strftime('%Y-%m-%d%H:%M:%S',time.localtime(time.time())),msg['FromUserName'])#向发送者回复时间信息`

获取群聊消息并回复

代码跟上面差不多,获取群聊消息代码如下
@itchat.msg_register(TEXT, isGroupChat=True)#处理群聊
def text_reply(msg):
之后开始判断
if msg['Type'] == 'Text':#如果消息类型是文本
if msg['Text'] == '时间':如果文本内容为时间两个字

   `itchat.send(u'当前时间: %s' % time.strftime('%Y-%m-%d%H:%M:%S',time.localtime(time.time())),msg['FromUserName'])#向发送者回复时间信息`

成品代码如下:

#coding=utf8
import requests
import re
import itchat
from itchat.content import *
from time import sleep
import time
import threading

def lc():
    print('登录成功')
def ec():
    print('帐号退出')
def init_tq():
    r = requests.get('http://wthrcdn.etouch.cn/weather_mini?city=%E5%91%BC%E5%85%B0')
    tqjson = r.json()
    rgx = re.compile("\<\!\[CDATA\[(.*?)\]\]\>")#正则
    high = tqjson['data']['forecast'][0]['high']#最高温
    low = tqjson['data']['forecast'][0]['low']#最低温
    type = tqjson['data']['forecast'][0]['type']#天气类型 晴 多云等
    fengxiang = tqjson['data']['forecast'][0]['fengxiang']#风向
    fengli = rgx.search(tqjson['data']['forecast'][0]['fengli']).group(1).replace('<','小于').replace('>','大于')
    tishi = tqjson['data']['ganmao'];#提示感冒等信息
    msg = '今日天气:'+ type +'\n最高温度:'+ high + '\n最低温度:' + low + '\n风向:' + fengxiang + "    " + fengli + '\n' + tishi
    return msg
    #天气解析结束
    #创建一个字典保存用户名称和id
def init_friends():
    friends = itchat.get_friends()[0:]
    friends_name = {}
    for i in friends:
        if i["RemarkName"]:
            if i["RemarkName"] not in friends_name:
                friends_name[i["RemarkName"]] = i["UserName"]
    return friends_name
    #初始化结束
def send_time():
    #print('Hello Timer!')
    time_now = time.strftime('%H%M',time.localtime(time.time()))
    #print(time_now)
    if int(time_now) == 600:
        itchat.send_msg(init_tq(), init_friends()["刘警暄"])#发送天气信息
    if int(time_now) == 1130:
        itchat.send_msg('十一点半了该吃午饭了', init_friends()["刘警暄"])
    if int(time_now) == 1330:
        itchat.send_msg('下午一点半了,上班啦.', init_friends()["刘警暄"])
    if int(time_now) == 1725:
        itchat.send_msg('还有五分钟就下班啦,收拾东西准备撤啦.', init_friends()["刘警暄"])
    global timer
    timer = threading.Timer(60, send_time)#每分钟判断一次
    timer.start()

timer = threading.Timer(1, send_time)
timer.start()

@itchat.msg_register([TEXT, MAP, CARD, NOTE, SHARING])#处理私聊
def text_reply(msg):
    #print(msg['FromUserName']+":"+msg['Text'])
    if msg['Type'] == 'Text':
        if msg['Text'] == '时间':
            itchat.send(u'当前时间: %s' % time.strftime('%Y-%m-%d %H:%M:%S',time.localtime(time.time())),msg['FromUserName'])
#print('%s: %s' % (msg['Type'], msg['Text']), msg['FromUserName'])
@itchat.msg_register(TEXT, isGroupChat=True)#处理群聊
def text_reply(msg):
    if msg['Text'] == '时间':
        itchat.send(u'当前时间: %s' % time.strftime('%Y-%m-%d %H:%M:%S',time.localtime(time.time())),msg['FromUserName'])
itchat.auto_login(hotReload=True,enableCmdQR=2,loginCallback=lc, exitCallback=ec)
itchat.run(True)
Last modification:May 24th, 2018 at 03:57 pm
If you think my article is useful to you, please feel free to appreciate

One comment

  1. hysteria

    Sever酱不错的~~微信要一直登陆着

Leave a Comment