[yarpc-go][OSS] Add iterator method alternative for yarpc HeaderNames #2407
+93
−2
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
Description
TLDR
With this change, services will spend less CPU cycles when getting the header names for a given yarpc call.
What
This diff introduces
HeaderNamesAll()for theCallstruct andAll()for theHeaderstruct. This returns an iterator to the caller.How
Uses
seq2iterators over manual looping + pre-sizing slice + sorting.How to use
With this change, services using
yarpchave a work around for iterating through the list ofHeaderNamesIterwith something like this:Best Practices
If you don't need a sorted list of header strings, and just want to iterate through the header names, this API is for you.
Type of Change
[ ] Breaking API Change
[ ] Breaking Semantic or Runtime Change
[x] Internal Implementation Change
[ ] Dependency Update (please also multi-select on whether this upgrade is breaking)
[ ] Code clean up / Refactoring
[ ] No code change (e.g. adding documentation)
Risk Level
[ ]
HIGH[ ]
MED[x]
LOWReasoning:
Change are related to adding a new iterator method. Any breakage will be caught during compilation and CI.
Potential Impact of Failure
Low.
Reasoning:
Change are related to a new iterator method. Any breakage will be caught during compilation and CI. This change will not impact at runtime even if it is not caught in CI.
Benchmarks
Benchmarking shows significant reduction in latencies, allocations and memory when there's more than 1 headers, when using iterators
Reasoning
For a single header,
HeaderNamesItershows a 47% latency increase (96ns → 141ns), 150% more memory usage (16B → 40B), and 200% more allocations (1 → 3) compared toHeaderNames because the iterator's fixed overhead dominates at this scale: whileHeaderNamessimply allocates a single-element slice and returns it with no sorting cost,HeaderNamesItermust create three closures (the method's return closure capturing theCallreceiver, theHeaders.ItemsIterclosure capturing the map, and the iterator state machine), execute multiple function calls through these closures, and perform yield checks - overhead that only becomes worthwhile when amortized across larger header counts whereHeaderNameswould suffer from O(n log n) sorting costs and growing slice allocations.Test
CI tests here.