基于 XMPP 的 Gtalk 机器人 [email_address] 2010.9.4
缘起:                    1, 手动更新测试仓库的 SVN      给同事用           2, 在 BlackBerry 上快速访问服务器     给自己用           3, 安排菜谱,讲笑话     给媳...
既然大家都有 Gtalk 那我们就来做个贴心的“小萝莉”机器人吧  ^_&
HOW? 当然是“可爱的 Python”   +   XMPP   了
Python !!!    你懂的,咱就先说 XMPP 吧 ~~
XMPP :原名 Jabber               eXtensible Messaging Presence Protocol               可扩展的消息状态协议               用于 Gtalk 就是基于 ...
XMPP 的架构?              简单来说,就是 Client-Server , Server-Server            一个分散型的通信网络哦            复杂来说, $%^&#*#$
拜托 ,我们只是想要写一个贴心的 Bot 而已。。。 Z.Q 大妈教导过我们, Python 是拿来 用 的,让我们 快乐 的朝目标前进就好  ~~~
出发之前的一些基础: JID : XMPP 的 client 端和 server 端统称为 XMPP 实体,用 JID 作为一个全局唯一的标识符。 格式为: node@domain/resource zhoo.xuan@ngosoft.com/...
出发之前的一些基础: xmpp 的消息传递系统包括三种内容: 1, 消息( Message ),普通的对话留言
出发之前的一些基础: xmpp 的消息传递系统包括三种内容: 2, 联机状态( Presence ),用户广播的”在线状态“和可用性
出发之前的一些基础: xmpp 的消息传递系统包括三种内容: 3, 信息 / 查询请求( Iq ),允许 XMPP 实体发起请求,并接受返回的响应
出发之前的一些基础: xmpp stanza : xmpp  节。是以 xml 表达的最小的信息项,每个 stanza 都有以下的公共属性: from:   源 xmpp 实体的 JID to:   目标 xmpp 实体的 JID id:   ...
从之前可以看出, XMPP 是基于 XML 流的。 Fuck~ 让我们自己处理的话太繁琐,幸好 python 有众多的功能模块,我们用   xmpppy
import xmpp jid = xmpp.JID('bot@gmail.com/python') message = xmpp.Message('say something') presence = xmpp.Presence('I'm a...
问题一,该如何让我的 bot 登录呢? jid = 'bot@gmail.com' pwd = 'password' jid_instance = xmpp.JID(jid) cl = xmpp.client(jid_instance.getD...
问题二,该如何让我的 bot 持续在线? status = xmpp.Presence(status=' 小萝莉 ') cl.sendInitPresence() cl.send(status) while 1:      cl.Process...
问题三,如何给 bot 注册 handler ? cl.RegisterHandler('message', message_handler) cl.RegisterHandler('presence', presence_handler) c...
问题四,如何让 bot 处理添加好友的请求? 所谓的添加好友,其实就是两个实体的互相”订阅“。 此信息为 presence 类型: cl.send(xmpp.Presence(to='xx@xx.xx', typ=' subscribe '))...
问题五,如何让 bot 处理我们发给她的信息? 发给 bot 的信息   ===>   要传递的指令 因此要先把这些指令和发送者提取出来 def message_handler(self, conn, mess):      who = mes...
client ==> (message)==>message_handler==>cmd_xxx 对发送信息的处理流程
def cmd_xxx(self, args):      # 功能部分      cl.send(xmpp.Message(who, reply))
出现了一个问题: 选择执行 cmd_xxx() 函数的时候,由于 xxx 是一个可变化的值,改如何实现?       解决方法:使用 commands[xxx]() 来做函数的选择。 commands={'xxx':func, ...} 可是,...
解决办法:定义一个 register_commands() 的函数,让其在 __init__() 中执行,动态的检测 class 中存在的 cmd_xxx 函数,并给 commands 赋值。         def register_comm...
并且,我们并不在每个 cmd_ 函数中设置 "_is_command" 属性,而是使用 @ 修饰符来加工 cmd_ 函数,为其设置属性。 def botcommands(*args):      func = args[0]...
def bootcommands(*args):        func = args[0]        setattr(func, '_is_command', True)        return func 使用修饰符函数,来建立我们的...
问题六,怎样知道 bot 的工作情况? 定义一个 log 函数,把每次 handler 的结果记录到文件中去
到目前为止,我们自己的 bot 小框架就算是完成了,粗略回顾一下: client-->connect-->auth-->register_handler              verify_request-->presence_handle...
但杯具的是,我还有一些遗留问题没有处理完: 1,log 系统因为编码的原因,暂时只能用英文凑合着 2, 这个 bot 没有写为 daemon 进程,退出终端后, bot 会跟着”死去“。目前的解决办法是跑在 screen 里   -_&! 有没...
bot 的雏形搞完了,可最初的功能还没实现呢 ~~ 目前只写了两个 cmd_ 函数   cmd_help      打印帮助信息 cmd_server   基于 xmpp 来控制服务器 cmd_work    与 server 类同,都是在 s...
问题 & 讨论 推荐: http://xmpppy.sourceforge.net http://code.google.com/p/pygtalkrobot/ http://www.ibm.com/developerworks/cn/xml/...
END  Thanks  ;) @roamin9 [email_address]
Upcoming SlideShare
Loading in …5
×

基于XMPP的Gtalk机器人

8,028 views

Published on

Published in: Self Improvement
  • Be the first to comment

基于XMPP的Gtalk机器人

  1. 1. 基于 XMPP 的 Gtalk 机器人 [email_address] 2010.9.4
  2. 2. 缘起:                   1, 手动更新测试仓库的 SVN     给同事用          2, 在 BlackBerry 上快速访问服务器     给自己用          3, 安排菜谱,讲笑话     给媳妇用   ;)
  3. 3. 既然大家都有 Gtalk 那我们就来做个贴心的“小萝莉”机器人吧 ^_&
  4. 4. HOW? 当然是“可爱的 Python”   +   XMPP   了
  5. 5. Python !!!    你懂的,咱就先说 XMPP 吧 ~~
  6. 6. XMPP :原名 Jabber              eXtensible Messaging Presence Protocol              可扩展的消息状态协议              用于 Gtalk 就是基于 XMPP 协议,并对协议进行了扩充 Google Wave 也是,虽然“出师未捷身先死”   Orz 延伸阅读   http://knb.im/67y
  7. 7. XMPP 的架构?              简单来说,就是 Client-Server , Server-Server            一个分散型的通信网络哦            复杂来说, $%^&#*#$
  8. 8. 拜托 ,我们只是想要写一个贴心的 Bot 而已。。。 Z.Q 大妈教导过我们, Python 是拿来 用 的,让我们 快乐 的朝目标前进就好 ~~~
  9. 9. 出发之前的一些基础: JID : XMPP 的 client 端和 server 端统称为 XMPP 实体,用 JID 作为一个全局唯一的标识符。 格式为: node@domain/resource zhoo.xuan@ngosoft.com/xxxx   就是我了   -_-
  10. 10. 出发之前的一些基础: xmpp 的消息传递系统包括三种内容: 1, 消息( Message ),普通的对话留言
  11. 11. 出发之前的一些基础: xmpp 的消息传递系统包括三种内容: 2, 联机状态( Presence ),用户广播的”在线状态“和可用性
  12. 12. 出发之前的一些基础: xmpp 的消息传递系统包括三种内容: 3, 信息 / 查询请求( Iq ),允许 XMPP 实体发起请求,并接受返回的响应
  13. 13. 出发之前的一些基础: xmpp stanza : xmpp 节。是以 xml 表达的最小的信息项,每个 stanza 都有以下的公共属性: from:   源 xmpp 实体的 JID to:   目标 xmpp 实体的 JID id:   这次对话的可选标识符 type:  stanza 的可选子类型
  14. 14. 从之前可以看出, XMPP 是基于 XML 流的。 Fuck~ 让我们自己处理的话太繁琐,幸好 python 有众多的功能模块,我们用   xmpppy
  15. 15. import xmpp jid = xmpp.JID('bot@gmail.com/python') message = xmpp.Message('say something') presence = xmpp.Presence('I'm at NGOsoft.com ') iq = xmpp.Iq() 对象简单明了,开工 ~
  16. 16. 问题一,该如何让我的 bot 登录呢? jid = 'bot@gmail.com' pwd = 'password' jid_instance = xmpp.JID(jid) cl = xmpp.client(jid_instance.getDomain(), debug[] ) cl.connect() cl.auth(jid_instance.getNode(), pwd)
  17. 17. 问题二,该如何让我的 bot 持续在线? status = xmpp.Presence(status=' 小萝莉 ') cl.sendInitPresence() cl.send(status) while 1:      cl.Process(1) send 函数可以用来发送三种类型的内容
  18. 18. 问题三,如何给 bot 注册 handler ? cl.RegisterHandler('message', message_handler) cl.RegisterHandler('presence', presence_handler) cl.RegisterHandler('iq', iq_handler) 一旦 bot 收到这三种类型的内容,就交由响应的 handler 函数来处理。
  19. 19. 问题四,如何让 bot 处理添加好友的请求? 所谓的添加好友,其实就是两个实体的互相”订阅“。 此信息为 presence 类型: cl.send(xmpp.Presence(to='xx@xx.xx', typ=' subscribe ')) cl.send(xmpp.Presence(to='xx@xx.xx', typ=' subscribed '))
  20. 20. 问题五,如何让 bot 处理我们发给她的信息? 发给 bot 的信息   ===>   要传递的指令 因此要先把这些指令和发送者提取出来 def message_handler(self, conn, mess):      who = mess.getFrom()      content = mess.getBody()      处理 content ,获得 cmd 和 arguments      if cmd in commands:          cmd_xxx(arguments)    #commands 为命令列表                                                #cmd_xxx 为命令函数
  21. 21. client ==> (message)==>message_handler==>cmd_xxx 对发送信息的处理流程
  22. 22. def cmd_xxx(self, args):      # 功能部分      cl.send(xmpp.Message(who, reply))
  23. 23. 出现了一个问题: 选择执行 cmd_xxx() 函数的时候,由于 xxx 是一个可变化的值,改如何实现?      解决方法:使用 commands[xxx]() 来做函数的选择。 commands={'xxx':func, ...} 可是,如何能动态的生成 commands{ } ?      
  24. 24. 解决办法:定义一个 register_commands() 的函数,让其在 __init__() 中执行,动态的检测 class 中存在的 cmd_xxx 函数,并给 commands 赋值。         def register_commands(self):      self.commands={}      for name, value in inspect.getmembers(self):          if inspect.ismethod(value) and          getattr(value, '_is_method', Falsa):              self.commands[name] = value
  25. 25. 并且,我们并不在每个 cmd_ 函数中设置 "_is_command" 属性,而是使用 @ 修饰符来加工 cmd_ 函数,为其设置属性。 def botcommands(*args):      func = args[0]      setattr(func, '_is_command', True)      return func @botcommands def cmd_xxx():
  26. 26. def bootcommands(*args):       func = args[0]       setattr(func, '_is_command', True)       return func 使用修饰符函数,来建立我们的 commands system
  27. 27. 问题六,怎样知道 bot 的工作情况? 定义一个 log 函数,把每次 handler 的结果记录到文件中去
  28. 28. 到目前为止,我们自己的 bot 小框架就算是完成了,粗略回顾一下: client-->connect-->auth-->register_handler              verify_request-->presence_handler-->log              message-->message_handler-->cmd_xx-->log   添加新的 cmd 功能: @botcommands() def cmd_xx(): Perfect   ;)
  29. 29. 但杯具的是,我还有一些遗留问题没有处理完: 1,log 系统因为编码的原因,暂时只能用英文凑合着 2, 这个 bot 没有写为 daemon 进程,退出终端后, bot 会跟着”死去“。目前的解决办法是跑在 screen 里   -_&! 有没有好的建议?
  30. 30. bot 的雏形搞完了,可最初的功能还没实现呢 ~~ 目前只写了两个 cmd_ 函数   cmd_help     打印帮助信息 cmd_server   基于 xmpp 来控制服务器 cmd_work   与 server 类同,都是在 server 端执行命令,只是要用脚本配合罢了 但是给媳妇用的 cmd_eat 和 cmd_joy 还没想好如何来实现,是从网上抓数据,还是用本地的数据库呢? Orz
  31. 31. 问题 & 讨论 推荐: http://xmpppy.sourceforge.net http://code.google.com/p/pygtalkrobot/ http://www.ibm.com/developerworks/cn/xml/tutorials/x-realtimeXMPPtut/index.html
  32. 32. END  Thanks  ;) @roamin9 [email_address]

×