Python操作RabbitMQ服务器实现消息队列的路由功能


Posted in Python onJune 29, 2016

Python使用Pika库(安装:sudo pip install pika)可以操作RabbitMQ消息队列服务器(安装:sudo apt-get install rabbitmq-server),这里我们来看一下MQ相关的路由功能。

路由键的实现

比如有一个需要给所有接收端发送消息的场景,但是如果需要自由定制,有的消息发给其中一些接收端,有些消息发送给另外一些接收端,要怎么办呢?这种情况下就要用到路由键了。

路由键的工作原理:每个接收端的消息队列在绑定交换机的时候,可以设定相应的路由键。发送端通过交换机发送信息时,可以指明路由键 ,交换机会根据路由键把消息发送到相应的消息队列,这样接收端就能接收到消息了。

这边继上一篇,还是用send.py和receive.py来模拟实现路由键的功能。send.py表示发送端,receive.py表示接收端。实例的功能就是将info、warning、error三种级别的信息发送到不同的接收端。

send.py代码分析

#!/usr/bin/env python
#coding=utf8
import pika
 
connection = pika.BlockingConnection(pika.ConnectionParameters(
        'localhost'))
channel = connection.channel()
 
#定义交换机,设置类型为direct
channel.exchange_declare(exchange='messages', type='direct')
 
#定义三个路由键
routings = ['info', 'warning', 'error']
 
#将消息依次发送到交换机,并设置路由键
for routing in routings:
  message = '%s message.' % routing
  channel.basic_publish(exchange='messages',
             routing_key=routing,
             body=message)
  print message
 
connection.close()

receive.py代码分析

#!/usr/bin/env python
#coding=utf8
import pika, sys
 
connection = pika.BlockingConnection(pika.ConnectionParameters(
        'localhost'))
channel = connection.channel()
 
#定义交换机,设置类型为direct
channel.exchange_declare(exchange='messages', type='direct')
 
#从命令行获取路由键参数,如果没有,则设置为info
routings = sys.argv[1:]
if not routings:
  routings = ['info']
 
#生成临时队列,并绑定到交换机上,设置路由键
result = channel.queue_declare(exclusive=True)
queue_name = result.method.queue
for routing in routings:
  channel.queue_bind(exchange='messages',
            queue=queue_name,
            routing_key=routing)
 
def callback(ch, method, properties, body):
  print " [x] Received %r" % (body,)
 
channel.basic_consume(callback, queue=queue_name, no_ack=True)
 
print ' [*] Waiting for messages. To exit press CTRL+C'
channel.start_consuming()

打开两个终端,一个运行代码python receive.py info warning,表示只接收info和warning的消息。另外一个终端运行send.py,可以观察到接收终端只接收到了info和warning的消息。如果打开多个终端运行receive.py,并传入不同的路由键参数,可以看到更明显的效果。

当接收端正在运行时,可以使用rabbitmqctl list_bindings来查看绑定情况。

路由键模糊匹配
路由键模糊匹配,就是可以使用正则表达式,和常用的正则表示式不同,这里的话“#”表示所有、全部的意思;“*”只匹配到一个词。看完示例就能明白了。

这边继上面的例子,还是用send.py和receive.py来实现路由键模糊匹配的功能。send.py表示发送端,receive.py表示接收端。实例的功能大概是这样:比如你有个知心好朋友,不管开心、伤心、工作上的还是生活上的事情都可以和她说;还有一些朋友可以分享开心的事情;还有一些朋友,你可以把不开心的事情和她说。

send.py代码分析

因为要进行路由键模糊匹配,所以交换机的类型要设置为topic,设置为topic,就可以使用#,*的匹配符号了。

#!/usr/bin/env python
#coding=utf8
import pika
 
connection = pika.BlockingConnection(pika.ConnectionParameters(
        'localhost'))
channel = connection.channel()
 
#定义交换机,设置类型为topic
channel.exchange_declare(exchange='messages', type='topic')
 
#定义路由键
routings = ['happy.work', 'happy.life', 'sad.work', 'sad.life']
 
#将消息依次发送到交换机,并设定路由键
for routing in routings:
  message = '%s message.' % routing
  channel.basic_publish(exchange='messages',
             routing_key=routing,
             body=message)
  print message
 
connection.close()

上例中定义了四种类型的消息,容易理解,就不解释了,然后依次发送出去。

receive.py代码分析

同样,交换机的类型要设定为topic就可以了。从命令行接收参数的功能稍微调整了一下,就是没有参数时报错退出。

#!/usr/bin/env python
#coding=utf8
import pika, sys
 
connection = pika.BlockingConnection(pika.ConnectionParameters(
        'localhost'))
channel = connection.channel()
 
#定义交换机,设置类型为topic
channel.exchange_declare(exchange='messages', type='topic')
 
#从命令行获取路由参数,如果没有,则报错退出
routings = sys.argv[1:]
if not routings:
  print >> sys.stderr, "Usage: %s [routing_key]..." % (sys.argv[0],)
  exit()
 
#生成临时队列,并绑定到交换机上,设置路由键
result = channel.queue_declare(exclusive=True)
queue_name = result.method.queue
for routing in routings:
  channel.queue_bind(exchange='messages',
            queue=queue_name,
            routing_key=routing)
 
def callback(ch, method, properties, body):
  print " [x] Received %r" % (body,)
 
channel.basic_consume(callback, queue=queue_name, no_ack=True)
 
print ' [*] Waiting for messages. To exit press CTRL+C'
channel.start_consuming()

打开四个终端,一个运行如下,表示任何事情都可以和她说:

python receive.py "#"

另外一个终端 运行如下,表示可以和她分享开心的事:

python receive.py "happy.*"

第三个运行如下,表示工作上的事情可以和她分享:

python receive.py "*.work"

最后一个运行python send.py。结果不难想象出来,就不贴出来了。

Python 相关文章推荐
使用graphics.py实现2048小游戏
Mar 10 Python
Python输出由1,2,3,4组成的互不相同且无重复的三位数
Feb 01 Python
python中实现字符串翻转的方法
Jul 11 Python
在Python中pandas.DataFrame重置索引名称的实例
Nov 06 Python
python 使用turtule绘制递归图形(螺旋、二叉树、谢尔宾斯基三角形)
May 30 Python
Pandas中DataFrame的分组/分割/合并的实现
Jul 16 Python
PyTorch加载预训练模型实例(pretrained)
Jan 17 Python
ansible动态Inventory主机清单配置遇到的坑
Jan 19 Python
pycharm 更改创建文件默认路径的操作
Feb 15 Python
keras .h5转移动端的.tflite文件实现方式
May 25 Python
Python Selenium自动化获取页面信息的方法
Aug 31 Python
Python 实现PS滤镜的旋涡特效
Dec 03 Python
Python通过RabbitMQ服务器实现交换机功能的实例教程
Jun 29 #Python
Python+Pika+RabbitMQ环境部署及实现工作队列的实例教程
Jun 29 #Python
Python的消息队列包SnakeMQ使用初探
Jun 29 #Python
Python中线程的MQ消息队列实现以及消息队列的优点解析
Jun 29 #Python
深入理解Python中装饰器的用法
Jun 28 #Python
Python中的迭代器与生成器高级用法解析
Jun 28 #Python
Python设计足球联赛赛程表程序的思路与简单实现示例
Jun 28 #Python
You might like
模板引擎正则表达式调试小技巧
2011/07/20 PHP
PHP错误提示的关闭方法详解
2013/06/23 PHP
PHP7基于curl实现的上传图片功能
2018/05/11 PHP
laravel 创建命令行命令的图文教程
2019/10/23 PHP
Jquery实现点击切换图片并隐藏显示内容(2种方法实现)
2013/04/11 Javascript
node.js中的fs.rmdir方法使用说明
2014/12/16 Javascript
jQuery实现鼠标单击网页文字后在文本框显示的方法
2015/05/06 Javascript
JS特效实现图片自动播放并可控的效果
2015/07/31 Javascript
javascript密码强度校验代码(两种方法)
2015/08/10 Javascript
JavaScript转换与解析JSON方法实例详解
2015/11/24 Javascript
解决js页面滚动效果scrollTop在FireFox与Chrome浏览器间的兼容问题的方法
2015/12/03 Javascript
浅谈Javascript数组(推荐)
2016/05/17 Javascript
利用jquery实现瀑布流3种案例
2016/09/18 Javascript
js初始化验证实例详解
2016/11/26 Javascript
jquery操作ID带有变量的节点实例
2016/12/07 Javascript
javascript实现页面滚屏效果
2017/01/17 Javascript
bootstrap datetimepicker 日期插件在火狐下出现一条报错信息的原因分析及解决办法
2017/03/08 Javascript
vue.js 底部导航栏 一级路由显示 子路由不显示的解决方法
2018/03/09 Javascript
vue 下列表侧滑操作实例代码详解
2018/07/24 Javascript
JS 封装父页面子页面交互接口的实例代码
2019/06/25 Javascript
Python中MySQLdb和torndb模块对MySQL的断连问题处理
2015/11/09 Python
python多进程共享变量
2016/04/06 Python
Python进阶之尾递归的用法实例
2018/01/31 Python
Python实现的远程登录windows系统功能示例
2018/06/21 Python
PYQT5实现控制台显示功能的方法
2019/06/25 Python
详解python3中用HTMLTestRunner.py报ImportError: No module named 'StringIO'如何解决
2019/08/27 Python
python GUI库图形界面开发之PyQt5信号与槽的高级使用技巧(自定义信号与槽)详解与实例
2020/03/06 Python
解决python父线程关闭后子线程不关闭问题
2020/04/25 Python
keras.utils.to_categorical和one hot格式解析
2020/07/02 Python
三八红旗手先进事迹材料
2014/05/13 职场文书
学习之星事迹材料
2014/05/17 职场文书
反对邪教标语
2014/06/30 职场文书
《我爱祖国》演讲稿1000字
2014/09/26 职场文书
2014年小学德育工作总结
2014/12/05 职场文书
如何书写民事调解协议书?
2019/06/25 职场文书
详解Python描述符的工作原理
2021/06/11 Python