2.rabbitmq 工作队列

1. 生产者

#coding:utf8

import pika
import json
import sys

message = ''.join(sys.argv[1:]) or "hello word"

connection = pika.BlockingConnection(pika.ConnectionParameters(
               'localhost'))
channel = connection.channel()

channel.queue_declare(queue='task_queue',durable = True)# 消息持久化durable = True


channel.basic_publish(exchange='',
    routing_key='task_queue',
    body=message,
    properties=pika.BasicProperties(
        delivery_mode=2,#make message persistent 
    ))
print " [x] Sent 'Hello World!'"

connection.close()

2.消费者

# coding:utf8

import pika
import MySQLdb
import time
connection = pika.BlockingConnection(pika.ConnectionParameters(
    'localhost'))
channel = connection.channel()

channel.queue_declare(queue='task_queue',durable = True)


def callback(ch, method, properties, body):
    print("[x] received %r" % body)
    time.sleep(20)
    print("done")
    ch.basic_ack(delivery_tag=method.delivery_tag) # ack 消息成功确认

channel.basic_qos(prefetch_count=1)#公平分派
channel.basic_consume(callback,
                      queue='task_queue')
print("waiting for messages")
channel.start_consuming()

3.注意:

 

被遗忘的确认

错过basic_ack是一个常见的错误这是一个简单的错误,但后果是严重的。当您的客户端退出时,消息将被重新传递(这可能看起来像随机重新传递),但RabbitMQ将会占用越来越多的内存,因为它无法释放任何未经处理的消息。

为了调试这种错误,您可以使用rabbitmqctl 来打印messages_unacknowledged字段:

 

sudo rabbitmqctl list_queues name messages_ready messages_unacknowledged

在Windows上,删除sudo:

rabbitmqctl.bat list_queues name messages_ready messages_unacknowledged

3.2 

有关消息持久性的注释

将消息标记为持久性并不能完全保证消息不会丢失。虽然它告诉RabbitMQ将消息保存到磁盘,但是当RabbitMQ接受消息并且尚未保存消息时,仍然有一个短时间窗口。此外,RabbitMQ不会为每条消息执行fsync(2) - 它可能只是保存到缓存而不是真正写入磁盘。持久性保证不强,但对于我们简单的任务队列来说已经足够了。如果您需要更强的保证,那么您可以使用 发布者确认

posted @ 2018-09-20 11:45  myvic  阅读(144)  评论(0编辑  收藏  举报