Skip to content

Avoid the per-request rotation copy in round-robin address selection#2230

Open
pavel-ptashyts wants to merge 2 commits into
AsyncHttpClient:mainfrom
maygemdev:fix/round-robin-rotate-alloc
Open

Avoid the per-request rotation copy in round-robin address selection#2230
pavel-ptashyts wants to merge 2 commits into
AsyncHttpClient:mainfrom
maygemdev:fix/round-robin-rotate-alloc

Conversation

@pavel-ptashyts

Copy link
Copy Markdown
Contributor

RoundRobinAddressSelector.rotateBy allocated a fresh ArrayList (backing array of size n) plus two subList views on every multi-IP round-robin request whose selected index != 0 — i.e. (n-1)/n of requests for an n-IP host — just to present the resolved addresses in round-robin failover order.

Return a lightweight read-only view (RotatedView, one small wrapper over the resolved list + a start index) instead of copying: element i maps to resolved.get((index + i) mod size). All consumers only read the result (get/size/iteration — NettyChannelConnector's failover loop and deprioritizeCooling), and the resolved list is not mutated after being wrapped, so no copy is needed. index == 0 and single-IP hosts still return the resolved list unchanged (no allocation), as before.

Only affects the opt-in LoadBalance.ROUND_ROBIN path. Existing selector tests (rotation order/evenness/failover completeness) pass unchanged; adds tests asserting the full element-by-element rotation order and that the returned view is read-only.

No API change: rotateBy and RotatedView are private; rotate()'s signature is unchanged.

RoundRobinAddressSelector.rotateBy allocated a fresh ArrayList (backing array of size n) plus two subList views on every multi-IP round-robin request whose selected index != 0 — i.e. (n-1)/n of requests for an n-IP host — just to present the resolved addresses in round-robin failover order.

Return a lightweight read-only view (RotatedView, one small wrapper over the resolved list + a start index) instead of copying: element i maps to resolved.get((index + i) mod size). All consumers only read the result (get/size/iteration — NettyChannelConnector's failover loop and deprioritizeCooling), and the resolved list is not mutated after being wrapped, so no copy is needed. index == 0 and single-IP hosts still return the resolved list unchanged (no allocation), as before.

Only affects the opt-in LoadBalance.ROUND_ROBIN path. Existing selector tests (rotation order/evenness/failover completeness) pass unchanged; adds tests asserting the full element-by-element rotation order and that the returned view is read-only.

No API change: rotateBy and RotatedView are private; rotate()'s signature is unchanged.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant