Skip to content

Compliance tests assert Wolverine's configuration objects, not the broker's actual state #4559

Closed

Description

@jeremydmiller

Follow-up to #4520. Found while verifying that fix, which turned a tolerated inequivalent arg warning into a hard failure and immediately lit up 23 tests that had been green over a configuration that was never applied.

What happened

ProcessInlineFixture declared .DeclareQueue("quorum1") — a copy-paste from QuorumQueueFixture, and the only name in that fixture that is not an inline one. So it created quorum_queue_compliance's queue as classic. Whichever class ran second got a 406 PRECONDITION_FAILED - inequivalent arg 'x-queue-type', which the old tolerate-and-continue path swallowed, and quorum_queue_compliance then ran its entire 23-test suite against a classic queue.

The copy-paste is fixed in #4541. The part that is not fixed is why nothing noticed for as long as it existed.

The real problem

all_queues_are_declared_as_quorum (quorum_queue_compliance.cs:57) passed the whole time:

var queues = theSender.GetRuntime().Options.Transports
    .AllEndpoints().OfType<RabbitMqQueue>()
    .Where(x => x.Role == EndpointRole.Application)
    .ToArray();

queues.Any().ShouldBeTrue();
foreach (var mqQueue in queues)
{
    mqQueue.QueueType.ShouldBe(QueueType.quorum);   // Wolverine's config object
}

It asserts what Wolverine intended to declare. It never asks the broker what actually exists. QueueType is a property Wolverine set on its own endpoint object during configuration, so the assertion is true by construction — it would pass against a broker that was switched off.

That is worth generalising: a test named "all queues are declared as X" that cannot fail when the declaration was rejected is not testing the declaration.

Suggested fix

  1. Make all_queues_are_declared_as_quorum ask the broker. QueueDeclarePassiveAsync returns the existing queue, and the management API exposes x-queue-type; either is a real answer. RabbitMqQueue.CheckAsync() already opens an admin channel and calls QueueDeclarePassiveAsync, so the plumbing exists.

  2. Audit the sibling compliance assertions for the same shape — anything reading Options.Transports and asserting a value Wolverine itself set. A quick scan suggests this pattern is not unique to the quorum test.

  3. Stop sharing fixed queue names across fixtures. sending_raw_messages.cs:15-19 already carries this exact warning:

    CI marker: send_end_to_end_* tests fail in CI with PRECONDITION_FAILED "inequivalent arg 'x-dead-letter-exchange' for queue 'messages1'" — the queue persists across test runs with one DLX config and a later test tries to re-declare it without one. Skipping in CI via the Flaky filter; the real fix is to stop sharing fixed queue names like 'messages1' across tests (use Guid-suffixed names). See CI stabilization: tracer + monitor CI run #2618.

    RabbitTesting.NextQueueName() already exists and does exactly that. The remaining fixed names are quorum1/quorum2 (quorum_queue_compliance.cs:34,37,48), inline1/inline2 (process_inline_compliance.cs), and messages1 per the note above. Moving those to NextQueueName() removes the whole class of collision, and would also let CI stabilization: tracer + monitor CI run #2618's Flaky skip be dropped.

Why it matters now

Before #4541 this failure mode was silent by design — a mismatched declaration logged a warning and carried on. Now it throws, so any remaining shared fixed name is a hard CI failure rather than a quiet wrong-configuration. Item 3 is the one with a deadline attached.

🤖 Generated with Claude Code

Activity

  1. added a commit that references this issue on Sep 23, 2026
  2. added a commit that references this issue on Sep 24, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions