Giter Site home page Giter Site logo

Comments (10)

bmflynn avatar bmflynn commented on May 28, 2024 1

@ansd Absolutely. I've made the change and our retries seem to be passing the same tests.

I think this issue is closable from my perspective. Thanks!

from rabbitmq-server.

kjnilsson avatar kjnilsson commented on May 28, 2024

did you enable the message_containers feature flag?

from rabbitmq-server.

bmflynn avatar bmflynn commented on May 28, 2024

Not explicitly, but it does show as "Enabled" in the management interface.

from rabbitmq-server.

lukebakken avatar lukebakken commented on May 28, 2024

@ansd and @kjnilsson discussed this internally and have found where the regression was introduced.

from rabbitmq-server.

bmflynn avatar bmflynn commented on May 28, 2024

from rabbitmq-server.

kjnilsson avatar kjnilsson commented on May 28, 2024

@bmflynn could you possibly explain a bit how you are using this feature? Collaborative editing of x- headers is a bit odd in my view. x- headers "belong" to the broker and using it this way feels somewhat odd.

It is very unlikely we'd provide the same feature for other protocols such as AMQP (1.0)

from rabbitmq-server.

bmflynn avatar bmflynn commented on May 28, 2024

Dead-lettering and the x-death['count'] value are used as part of a retry mechanism where a message with expiration is retried until x-death['count'] is greater than the maximum number of retries.

Essentially, when message handling fails the message properties (including headers) and data are published with a message expiration via an error exchange to a queue with the dead-letter exchange set to the original exchange. The message will remain in this queue to expire at which point it gets routed back to the original exchange and is retried. This mechanism continues until the original message is handled successfully or x-death['count'] reaches the configured maximum number of retries.

There is no editing of the x-headers other than the fact that they are part of the original message properties that are used as part of a new message that is sent to an error exchange.

What is the specific feature you are referring to? Do you mean it's unlikely that a death count, or the number of times a message is dead-lettered, will be available in AMQP 1.0?

from rabbitmq-server.

ansd avatar ansd commented on May 28, 2024

@bmflynn Starting with "message containers" in 3.13, we would like to treat any x- headers as belonging to the broker, meaning a client shouldn't publish messages with x- headers. (If a client does publish with x- headers, these headers won't be interpreted in any special way anymore as illustrated by your example).

You are right that this is a behavioural change compared to 3.12 and arguably a breaking change belonging to 4.0.
So, we could "fix" / revert to the 3.12 behaviour by having the broker parse incoming headers and therefore interpreting the x-death header coming from a publisher.
However, we very likely would remove such special interpretation again in RabbitMQ 4.0 (which probably ships end of this year).
Therefore, my question is: Could your client set a custom non x- header and just increment it itself when it re-publishes the message?

Here is an example based on yours:

Code example with custom header
import os
import time
from collections import namedtuple
from pprint import pprint

from pika import BasicProperties, BlockingConnection, URLParameters

Msg = namedtuple("Msg", ["method", "properties", "body"])

amqpurl = "amqp://localhost:5672"
exchange = "amq.topic"

start_queue = "start_queue"
dlx_exchange = "errors"
error_queue = "dead_letters"
routing_key = "test_retries"

data = "XXX"

conn = BlockingConnection(URLParameters(amqpurl))
ch = conn.channel()

ch.exchange_declare(dlx_exchange, "topic")
ch.queue_declare(error_queue)
ch.queue_bind(error_queue, dlx_exchange, "#")

ch.queue_declare(start_queue, arguments={"x-dead-letter-exchange": dlx_exchange})
ch.queue_bind(start_queue, exchange, routing_key)

print(f"first publish {exchange=} {routing_key=} {data=}")
ch.basic_publish(exchange, routing_key, data, properties=BasicProperties(expiration="500"))

# Wait for message to error out
print("waiting\n")
time.sleep(1)

first = Msg(*ch.basic_get(error_queue))
ch.basic_ack(first.method.delivery_tag)
print("Received:")
pprint(first.properties.headers)

print("Second publish")
Key = "my-retry-count"
# Increment the retry count if it exists
first.properties.headers[Key] = first.properties.headers.get(Key, 0) + 1
first.properties.expiration = "500"
ch.basic_publish(exchange, routing_key, data, properties=first.properties)

# Wait for message to expire again
print("waiting\n")
time.sleep(1)
second = Msg(*ch.basic_get(error_queue))
ch.basic_ack(second.method.delivery_tag)
print("Received:")
pprint(second.properties.headers)

print("Third publish")
first.properties.headers[Key] = first.properties.headers.get(Key, 0) + 1
first.properties.expiration = "500"
ch.basic_publish(exchange, routing_key, data, properties=first.properties)

# Wait for message to expire again
print("waiting\n")
time.sleep(1)
second = Msg(*ch.basic_get(error_queue))
ch.basic_ack(second.method.delivery_tag)
print("Received:")
pprint(second.properties.headers)

ch.close()
conn.close()

from rabbitmq-server.

Related Issues (20)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.