<jupyter_start><jupyter_text>如何使用和开发微信聊天机器人的系列教程 A workshop to develop & use an intelligent and interactive chat-bot in WeChat  WeChat is a popular social media app, which has more than 800 million monthly active users. http://www.KudosData.comby: <EMAIL>October 2018 : Update to support Python 3 in local machine, e.g. iss-vm.April 2017 ========== Scan the QR code to become trainer's friend in WeChat ========>>  第一课：使用微信问答机制 Lesson 1: Basic usage of WeChat Python API* 使用和开发微信个人号聊天机器人：一种Python编程接口 (Use WeChat Python API)* 用微信App扫QR码图片来自动登录 (Log-in, contact scan, and processing of text, image, file, video, etc)* 查找指定联系人或群组 (Scan ccontact list)* 发送信息（文字、图片、文件、音频、视频等） (Send message: text, image, file, voice, video, etc)* 接收信息 (Receive message, and keep 'listening')* 自动回复 (Receive message and then automaticaly reply)* 自定义复杂消息处理，例如：信息存档、回复群组中被@的消息 (Advanced message processing and reply)  Imports / 导入需要用到的一些功能程序库：<jupyter_code># from __future__ import unicode_literals, division
import time, datetime, requests, itchat
from itchat.content import *<jupyter_output>█<jupyter_text>* Log in using QR code image / 用微信App扫QR码图片来自动登录<jupyter_code># itchat.auto_login(hotReload=True) # hotReload=True: 退出程序后暂存登陆状态。即使程序关闭，一定时间内重新开启也可以不用重新扫码。
itchat.auto_login(enableCmdQR=-2) # enableCmdQR=-2: 命令行显示QR图片<jupyter_output>Getting uuid of QR code.
Downloading QR code.<jupyter_text>* Locate User or Group / 查找指定联系人或群组使用search_friends方法可以搜索用户，有几种搜索方式： 1.仅获取自己的用户信息 2.获取昵称'NickName'、微信号'Alias'、备注名'RemarkName'中的任何一项等于name键值的用户 3.获取分别对应相应键值的用户<jupyter_code># Check Self Info / 获取自己的用户信息，返回自己的属性字典
friend = itchat.search_friends()
print(friend)
print('NickName  : %s' % friend['NickName'])
print('Alias A-ID: %s' % friend['Alias'])
print('RemarkName: %s' % friend['RemarkName'])
print('UserName  : %s' % friend['UserName'])
# Locate User / 获取任何一项等于name键值的用户。
# 'NickName' 昵称, set by that friend, changeable
# 'Alias' ID微信号 = wechatAccount, one time set by that friend, cannot change
# 'RemarkName' 备注名, set by current login account owner, changeable by login account owner
# 注意：返回可能包含多个朋友。为什么呢？

friend = itchat.search_friends(name=u'Nick')
# friend = itchat.search_friends(name=u'<NAME>')
# friend = itchat.search_friends(name=u'<NAME>')
for i in range(0, len(friend)):
    print('NickName  : %s' % friend[i]['NickName'])
    print('Alias A-ID: %s' % friend[i]['Alias'])
    print('RemarkName: %s' % friend[i]['RemarkName'])
    print('UserName  : %s' % friend[i]['UserName'])
# Locate User / 获取分别对应相应键值的用户。

# friend = itchat.search_friends(nickName=u'Nick')
# friend = itchat.search_friends(wechatAccount=u'Nick')
friend = itchat.search_friends(remarkName=u'Nick')
# friend = itchat.search_friends(userName=u'Nick')
for i in range(0, len(friend)):
    print('NickName  : %s' % friend[i]['NickName'])
    print('Alias A-ID: %s' % friend[i]['Alias'])
    print('RemarkName: %s' % friend[i]['RemarkName'])
    print('UserName  : %s' % friend[i]['UserName'])
# Locate Group / 查找群组
# group = itchat.search_chatrooms(name=u'Data Science')
group = itchat.search_chatrooms(name=u'陪聊妹UAT')
for i in range(0, len(group)):
    print('NickName  : %s' % group[i]['NickName'])
    print('Alias A-ID: %s' % group[i]['Alias'])
    print('RemarkName: %s' % group[i]['RemarkName'])
    print('UserName  : %s' % group[i]['UserName'])
    print('Is Owner? : %s ( 0 for No | 1 for Yes )' % group[0]['IsOwner'])
    print('Is Admin? : %s' % group[i]['IsAdmin'])
    print('')<jupyter_output>NickName  : 酷豆陪聊妹UAT-R
Alias A-ID: 
RemarkName: 
UserName  : @@0da7017792ef60e01a21d7b882aad186edcc6fd00c68af34aef5cb48dc30e78c
Is Owner? : 0 ( 0 for No | 1 for Yes )
Is Admin? : None

NickName  : 酷豆陪聊妹UAT-B
Alias A-ID: 
RemarkName: 
UserName  : @@e30bd675e5aa2c2c84e853e262cdef876fa6fc7a0f72a219e25c374e58e9c03e
Is Owner? : 0 ( 0 for No | 1 for Yes )
Is Admin? : None

NickName  : 酷豆陪聊妹UAT-X
Alias A-ID: 
RemarkName: 
UserName  : @@559e081666244e73673bbbc03abbc27a9b83dbd2fe037284b795a8ade74e9590
Is Owner? : 0 ( 0 for No | 1 for Yes )
Is Admin? : None

NickName  : 酷豆陪聊妹UAT-S
Alias A-ID: 
RemarkName: 
UserName  : @@88c7ade51415a08a6ecd3556c186abce9ac7ed02<PASSWORD>7<PASSWORD>760<PASSWORD>7<PASSWORD>
Is Owner? : 0 ( 0 for No | 1 for Yes )
Is Admin? : None<jupyter_text>* Interactive Conversation : Send / 发送信息（文字、图片、文件、音频、视频等）<jupyter_code># Locate User / 获取分别对应相应键值的用户。

# friend = itchat.search_friends(nickName=u'白黑')
# friend = itchat.search_friends(wechatAccount=u'白黑')
# friend = itchat.search_friends(remarkName=u'白黑')
# friend = itchat.search_friends(userName=u'白黑')
friend = itchat.search_friends(name=u'白黑')
for i in range(0, len(friend)):
    print('NickName  : %s' % friend[i]['NickName'])
    print('Alias A-ID: %s' % friend[i]['Alias'])
    print('RemarkName: %s' % friend[i]['RemarkName'])
    print('UserName  : %s' % friend[i]['UserName'])
# Text / 文字
# English
reply = itchat.send(u'Nice to meet you in this course！\nTime Sent:\n{:%Y-%b-%d %H:%M:%S}'.format(datetime.datetime.now()), friend[0]['UserName']) 
# Chinese
# reply = itchat.send(u'别来无恙啊！\n发送时间:\n{:%Y-%b-%d %H:%M:%S}'.format(datetime.datetime.now()), friend[0]['UserName']) 
print(reply['BaseResponse']['ErrMsg'])
# Picture / 图片
reply = itchat.send_image('./reference/WeChat_SamGu_QR.png', friend[0]['UserName']) 
print(reply['BaseResponse']['ErrMsg'])
# Document / 文件
reply = itchat.send_file('./reference/logo.pdf', friend[0]['UserName']) 
print(reply['BaseResponse']['ErrMsg'])
# Audio / 音频（语音可以先转成MP3）
reply = itchat.send_file('./reference/audio.mp3', friend[0]['UserName']) 
print(reply['BaseResponse']['ErrMsg'])
# Video / 视频
reply = itchat.send_video('./reference/video.mp4', friend[0]['UserName']) 
print(reply['BaseResponse']['ErrMsg'])
# Locate Group / 查找群组
# group = itchat.search_chatrooms(name=u'Data Science')
group = itchat.search_chatrooms(name=u'陪聊妹UAT-S')
for i in range(0, len(group)):
    print('NickName  : %s' % group[i]['NickName'])
    print('Alias A-ID: %s' % group[i]['Alias'])
    print('RemarkName: %s' % group[i]['RemarkName'])
    print('UserName  : %s' % group[i]['UserName'])
    print('Is Owner? : %s ( 0 for No | 1 for Yes )' % group[0]['IsOwner'])
    print('Is Admin? : %s' % group[i]['IsAdmin'])
    print('')
# 发送信息去群组： group[0]['UserName']
# Text / 文字
# English
reply = itchat.send(u'Nice to meet you in this course！\nTime Sent:\n{:%Y-%b-%d %H:%M:%S}'.format(datetime.datetime.now()), group[0]['UserName']) 
# Chinese
# reply = itchat.send(u'别来无恙啊！\n发送时间:\n{:%Y-%b-%d %H:%M:%S}'.format(datetime.datetime.now()), group[0]['UserName']) 
print(reply['BaseResponse']['ErrMsg'])<jupyter_output>请求成功<jupyter_text>*  Interactive Conversation : Receive / 接收信息 显示发给自己的文本消息：<jupyter_code># itchat.auto_login(hotReload=True) # hotReload=True: 退出程序后暂存登陆状态。即使程序关闭，一定时间内重新开启也可以不用重新扫码。
@itchat.msg_register(itchat.content.TEXT)
def text_reply(msg):
    print(msg['Text'])
# 长期有效地运行（术语叫做：开始监听）
itchat.run()<jupyter_output><empty_output><jupyter_text>回复发给自己的文本消息：<jupyter_code># interupt, then re-login
itchat.auto_login(hotReload=True)
@itchat.msg_register(itchat.content.TEXT)
def text_reply(msg):
    print(msg['Text'])
    return u'Thank you! 谢谢亲[嘴唇]我收到 I received:\n' + msg['Text']
itchat.run()<jupyter_output><empty_output><jupyter_text>*  Interactive Conversation : Auto Mode / 自定义复杂消息处理，例如：信息存档、回复群组中被@的消息<jupyter_code># interupt, then re-login
itchat.auto_login(hotReload=True)
# 如果收到[TEXT, MAP, CARD, NOTE, SHARING]类的信息，会自动回复：
@itchat.msg_register([TEXT, MAP, CARD, NOTE, SHARING]) # 文字、位置、名片、通知、分享
def text_reply(msg):
    print(u'[ Terminal Info ] Thank you! 谢谢亲[嘴唇]我已收到 I received: [ %s ] %s From: %s' 
          % (msg['Type'], msg['Text'], msg['FromUserName']))
    itchat.send(u'Thank you! 谢谢亲[嘴唇]我已收到\nI received:\n[ %s ]\n%s' % (msg['Type'], msg['Text']), msg['FromUserName'])

# 如果收到[PICTURE, RECORDING, ATTACHMENT, VIDEO]类的信息，会自动保存：
@itchat.msg_register([PICTURE, RECORDING, ATTACHMENT, VIDEO]) # 图片、语音、文件、视频
def download_files(msg):
    msg['Text'](msg['FileName'])
    print(u'[ Terminal Info ] Thank you! 谢谢亲[嘴唇]我已收到 I received: [ %s ] %s From: %s' 
          % ({'Picture': 'img', 'Video': 'vid'}.get(msg['Type'], 'fil'), msg['FileName'], msg['FromUserName']))
    itchat.send(u'Thank you! 谢谢亲[嘴唇]我已收到\nI received:', msg['FromUserName'])
    return '@%s@%s' % ({'Picture': 'img', 'Video': 'vid'}.get(msg['Type'], 'fil'), msg['FileName'])

# 如果收到新朋友的请求，会自动通过验证添加加好友，并主动打个招呼：幸会幸会！Nice to meet you!
@itchat.msg_register(FRIENDS)
def add_friend(msg):
    print(u'[ Terminal Info ] New Friend Request 新朋友的请求，自动通过验证添加加好友 From: %s' % msg['RecommendInfo']['UserName']) 
    itchat.add_friend(**msg['Text']) # 该操作会自动将新好友的消息录入，不需要重载通讯录
    itchat.send_msg(u'幸会幸会！Nice to meet you!', msg['RecommendInfo']['UserName'])

# 在群里，如果收到@自己的文字信息，会自动回复：
@itchat.msg_register(TEXT, isGroupChat=True)
def text_reply(msg):
    if msg['isAt']:
        print(u'[ Terminal Info ] Group@Info 在群里收到@自己的文字信息: %s From: %s %s' 
              % (msg['Content'], msg['ActualNickName'], msg['FromUserName']))
        itchat.send(u'@%s\u2005I received: %s' % (msg['ActualNickName'], msg['Content']), msg['FromUserName'])

itchat.run()
# interupt, then logout
itchat.logout() # 安全退出<jupyter_output><empty_output>
{'fraction_non_alphanumeric': 0.17586733580624045, 'fraction_numerical': 0.021492472179794893, 'mean_word_length': 6.040706605222734, 'pattern_counts': {'":': 0, '<': 32, '<?xml version=': 0, '>': 34, 'https://': 0, 'lorem ipsum': 0, 'www.': 1, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 3, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'chain_length': '7', 'dir': 'jupyter-structured-clean-dedup', 'id': '132234', 'license': 'MIT', 'n_tokens_mistral': 4182, 'n_tokens_neox': 4195, 'n_words': 697, 'path': 'wechat_tool_py3_local/lesson_1_py3_local.ipynb', 'repo_name': 'telescopeuser/workshop_blog_py3_local', 'size': '9156'}