Repository navigation
Description
Environment
Master aab453f06dbd135da9b329ee153758ceac0e1834 (2.7.3-SNAPSHOT), Apache Dubbo gray routing using leastActive; project dependency Dubbo 3.2.14.
Problem
The new counting wrapper compares equal to its delegate in one direction only. Dubbo's retry reselection checks original directory invokers against its already-tried list, which can contain wrappers. This comparison fails and allows an already-tried provider back into the retry candidates, even when another provider is available.
Reproduction and observed result
An isolated probe exercised Dubbo 3.2.14's actual AbstractClusterInvoker.select implementation:
- Provide two available directory invokers A and B.
- Put an
InflightInvokerwrapping A in the already-tried list, representing a previous invocation attempt. - Use a deterministic load balancer returning a fresh counting wrapper around the first admitted candidate. This exposes whether reselection excludes A.
- Invoke the real cluster selector with both providers available.
Observed:
wrapper.equals(original) = true
original.equals(wrapper) = false
alreadyTried.contains(original) = false
selectedFailedProviderAgain = true
The load balancer is deterministic in this probe so the incorrect candidate admission is reproducible. No network RPC was executed.
Root cause
InflightInvoker.equals delegates equality for wrapper-to-original comparisons, but cannot change the original invoker's equality implementation. In AbstractClusterInvoker.reselect, the candidate being tested is an original directory invoker, so selected.contains(candidate) uses candidate.equals(wrapper) and does not exclude it.
ApacheDubboGrayLoadBalance introduces the wrapper on the least-active gray path. The current identity test covers wrapper-to-original equality and originalInvokers.contains(wrapper), which exercises the opposite comparison direction from retry reselection.
Expected behavior / acceptance
- Preserve canonical provider identity throughout Dubbo directory, selection, already-tried and invalidation bookkeeping. A one-sided equality override is insufficient for arbitrary invokers.
- With A already tried and B available, reselection excludes A and chooses B.
- Test against the actual cluster selection/reselection implementation, not only direct wrapper equality assertions.
- Preserve exactly-once inflight accounting for repeated invocation, completion, exceptions and cancellation where supported.
Validation boundary
Behavior reproduced with the project's actual Dubbo cluster implementation and counting wrapper, mocked directory invokers and a deterministic selector. This is not a live Dubbo failover integration test.
Activity
konlue commentedon Oct 27, 2026
/assign
fix(dubbo): count the committed provider in gray inflight accounting (a…
fix(dubbo): preserve the selected logical upstream in gray inflight a…
fix(dubbo): mark the full logical upstream identity in gray inflight …
fix(dubbo): keep provider identity through Dubbo bookkeeping and coun…