apache / apache/rocketmq

[Bug] Topic candidate selection races with concurrent cache eviction

Open
#10,892 3 comments 0 reactions 0 assignees View on GitHub
Dominant language
Java
Stars
22.6k
Forks
12k
Avg merge
3d 1h
Merged PRs (30d)
27

Description

### Runtime platform environment
All platforms; reproduced by a deterministic unit test on the current `develop` branch.

### RocketMQ version
`develop` at `e3458616d207ee636b1762f0f8dcf788a590d59d`.

### Describe the Bug
Both the Java producer and Proxy availability detectors select a cached topic by first checking whether a concurrent map is empty and then creating a new iterator and immediately calling `next()`.

If the final cache entry is evicted between the two operations, `next()` throws `NoSuchElementException`. The client path is `DefaultMQProducerImpl.pickTopic`; the Proxy has the same pattern in `TopicRouteService.pickTopic`.

### Steps to Reproduce
1. Populate the producer topic cache with one entry.
2. Simulate eviction immediately after `isEmpty()` returns false.
3. Invoke `pickTopic` through the availability detector helper.
4. Observe `NoSuchElementException`.

### Expected Behavior
A cache that becomes empty during candidate selection returns an empty `Optional`, causing the detector to report no candidate rather than throwing.

### Actual Behavior
Candidate selection throws before the detector can return a normal unavailable result.

### Proposed Fix
Use one iterator and check `hasNext()` before calling `next()` in both Client and Proxy implementations. Add a regression test for the Client implementation.

Contributor guide

Open the contributing guide

Research direction

Start at DefaultMQProducerImpl.pickTopic and the matching TopicRouteService.pickTopic implementation, then trace how the availability detector handles an empty Optional. Reproduce the eviction race with the deterministic unit-test setup described in the issue. Done means both implementations return an empty Optional when the cache empties during selection, with a regression test covering the Client path.

Written by the indexing model from the issue text.

Assessment

Tech stack
java
Domain
backend, distributed-systems
Issue type
Bug
Difficulty
3/5
Estimated time
1-2 days
Activity status
Quiet
Clarity
Clearly specified
Newbie friendliness
72/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.