导读
最近在项目中需要将一些数据传输到另外一个程序里面以供调用,两个程序都处于同一服务器上,传输的内容少,但是频率很频繁,使用 HTTP 的方式虽然会方便一点,但是会占用一部分网络带宽,若是遇到服务器网络拥挤堵塞,就会导致消息无法发送,或者消息能发送,但是接收方无法接收的问题。于是想到使用 RabbitMQ 这一消息中间件。
要使用RabbitMQ功能,需要配合pika库。安装:
pip install pika
之前写过一个简单的 RabbitMQ demo可供参考,连接方式采用 BlockingConnection,gitee地址 。
项目框架使用Tornado,需要发布消息。一开始不熟悉pika库的使用方法,查了pika官方文档,只有简单的消费者代码示例,也查了其他作者发布的文档,讲述关于 TornadoConnection 内容的文章极少,来来回回都是那几行代码, 并且写的是消费者对象,并不具备参考性。
但是其中一篇文章给了我非常关键的提示,文章链接:链接地址 。
代码开始
一、先创建一个pika连接对象,在 MQHandler.py 文件里面
有关于pika库的相关API解释,可参考pika的官方文档,这里不做解释。
import pika
from pika.adapters.tornado_connection import TornadoConnection
class PikaClient:
def __init__(self, io_loop):
self.host = "127.0.0.1"
self.port = 5672
self.username = "guest"
self.password = "guest"
self.io_loop = io_loop
self.connected = False
self.connecting = False
self.connection = None
self.channel = None
def connect(self):
if self.connecting:
return
self.connecting = True
cred = pika.PlainCredentials(username=self.username, password=self.password)
param = pika.ConnectionParameters(self.host, self.port, "/", credentials=cred)
self.connection = TornadoConnection(param, custom_ioloop=self.io_loop, on_open_callback=self.on_connected)
self.connection.add_on_open_error_callback(self.err)
self.connection.add_on_close_callback(self.on_closed)
def err(self, conn):
print('pika error!')
def on_connected(self, conn):
print('pika connected')
self.connected = True
self.connection = conn
self.connection.channel(on_open_callback=self.on_channel_open)
def on_channel_open(self, channel):
print(channel)
channel.exchange_declare(exchange="test", durable=True) # 交换机、持久化
self.channel = channel
def on_closed(self, conn, c):
print('pika close!')
self.io_loop.stop()
二、web 接口代码示例,在 TestHandler.py 里,可以将数据放入到消息队列里面
import json
import pika
from tornado.web import RequestHandler
class TestProduct(RequestHandler):
def post(self):
data = json.loads(self.request.body)
print(f"推送内容:{data}")
self.application.pika.channel.basic_publish(exchange="test", routing_key="id", body=self.request.body, properties=pika.BasicProperties(delivery_mode=2)) # 1-消息非持久化,2-持久化
print("推送成功。")
三、程序入口运行文件 main.py
import tornado.web
import tornado.ioloop
from tornado_demo.MQHandler import PikaClient
from tornado_demo.api.TestHandler import TestProduct
def make_app():
handlers = [
("/api/test", TestProduct)
]
app = tornado.web.Application(handlers=handlers, debug=True)
return app
def run():
ioloop = tornado.ioloop.IOLoop.instance()
app = make_app()
app.pika = PikaClient(ioloop)
app.pika.connect()
app.listen(8888, "0.0.0.0")
ioloop.start()
结尾
这里的代码只围绕在Tornado框架里使用pika库的示例,希望可以帮助到大家。