Skip to content

Sidecar: isolate downstream API options per request#3919

Merged
iNinja merged 2 commits into
AzureAD:masterfrom
soodt:tanujsood/sidecar-options-isolation
Jul 3, 2026
Merged

Sidecar: isolate downstream API options per request#3919
iNinja merged 2 commits into
AzureAD:masterfrom
soodt:tanujsood/sidecar-options-isolation

Conversation

@soodt

@soodt soodt commented Jul 3, 2026

Copy link
Copy Markdown
Contributor

Sidecar: isolate downstream API options per request

  • You've read the Contributor Guide and Code of Conduct.
  • You've included unit or integration tests for your change, where applicable.
  • You've included inline docs for your change, where applicable.
  • There's an open issue for the PR that you are making. If you'd like to propose a new feature or change, please open an issue to discuss the change or find an existing issue.

Summary of the changes (Less than 80 chars)

Description

The sidecar resolves DownstreamApiOptions from IOptionsMonitor.Get(apiName), which is a
process-wide singleton. Both the AuthorizationHeader* and DownstreamApi* endpoints could
apply request-scoped values onto that shared instance:

  • the options-override merge (MergeOptions) performs a shallow Clone() and then writes into
    the shared ExtraParameters / ExtraHeaderParameters / ExtraQueryParameters dictionaries, and
  • the agent-identity parameters (AgentIdentity / AgentUsername / AgentUserId) are applied
    in place.

Because Clone() is a shallow member copy, those dictionaries are shared with the singleton, so
request-scoped values could persist onto the shared options and affect subsequent requests, or
race under concurrency.

This change isolates the options up front. Both endpoints now call a new
DownstreamApiOptionsMerger.CloneForRequest immediately after resolving the options — before any
merge or agent-identity mutation. CloneForRequest clones the options and allocates fresh
ExtraParameters, ExtraHeaderParameters, and ExtraQueryParameters dictionaries when present,
so every request operates on a fully private copy and the singleton is never mutated.
Override-gating and logging behavior are unchanged, and MergeOptions is untouched. Scopes and
ManagedIdentity are only reassigned (never mutated in place) and are documented as such.

Testing

Adds SidecarOptionsIsolationTests covering: per-request isolation on both endpoints, the merge
path with pre-existing non-null singleton collections, concurrency with distinct agent identities,
and shallow-clone-vs-fresh-dictionary characterization. Full Sidecar.Tests suite passes (the
pre-existing cert/live-AAD integration tests remain environment-gated).

@soodt
soodt requested a review from a team as a code owner July 3, 2026 09:20
@iNinja
iNinja merged commit 69dea55 into AzureAD:master Jul 3, 2026
4 checks passed
This was referenced Jul 3, 2026
This was referenced Jul 15, 2026
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.

4 participants