You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
v3.0.0-rc.1 is tagged. GA closes the breaking-change window, and v2 is GA so nothing breaking lands there either. There are currently a dozen-plus open issues that change exported signatures or observable contracts, and several of them mutate the same symbols. Taken in filing order, they would break the same exported functions two or three times inside one release window.
This issue is a sequencing proposal, not new scope. Every item below is an existing issue.
Status refreshed against main @ ff26996. Tiers 2, 3 and 5 are done; Tier 1 is 6/9 with only the scope half and #873 left. Original analysis kept below where it still applies.
Tier 1 — the auth cluster: one break, or three
These issues all mutate the same small set of exported symbols in registry/remote/auth and registry/remote/credentials.
The proposed order held up.#1380 → #1381 → #1385 → #1382 + #1383 → #1384 landed in that sequence, and no exported signature in the cluster was broken twice.
What is left
#1451 and #1376 are the scope half, and they still collide: both rewrite WithScopesForHost / AppendScopesForHost / GetScopesForHost. They should land as one change, not two. #1385's part of that collision is already resolved.
#873 is no longer blocked, and no longer breaking. Its stated dependency — "must be defined after#1382, or its key type is wrong on arrival" — is discharged. With the key type settled, every caller of credentials.Store uses exactly one of its three methods (NewCredentialFunc → Get, Login → Put, Logout → Delete), so the split is mechanical and source-compatible for callers and implementers alike. The issue body has been updated with the current scope.
Decided: the granular getter is keyed by serverAddress string, not properties.Resource. A Resource-keyed store interface would break every third-party store while pushing the Resource → server-address mapping into each implementation, and it does not resolve #1431 (a return-shape problem) or #1453 (already handled by #1457). If it is ever wanted it can be added additively as an optional ResourceGetter. Rationale recorded in the issue.
#873 also now carries the NamespaceMatcher embed fix — see #1455 below.
Follow-on issues the cluster produced
Namespaced credentials turned out to have consequences beyond the signatures. These were filed during the Tier 1 work and are part of finishing it:
Tier 2 — finish the registry.Reference deprecation ✅
#1387 and #1386 are closed (#1392, #1393). #1394 item 5 (the layering) remains part of that open design issue.
The silent-hazard concern was addressed as suggested: internal/interfaces now carries both ReferenceParser and LegacyReferenceParser, and content.go tries each in turn (content.go:61,68), so a third-party Target on the old signature still matches and still gets scope hints. The transition period is in place; the release note for when it is removed is still owed.
Tier 3 — security fixes that change parse output ✅
#1388 and #1389 were fixed together by normalizing the registry host case in properties.NewReference (#1402), closing both fail-open bypasses with one change, as proposed. #1390 landed in #1397. #1396 is fixed.
Tier 4 — semantics and defaults
Each of these is defensible either way; the point is that not deciding is itself a decision once GA ships. This is now the tier with the most left in it.
Tier 5 — remove dead API while removal is still free ✅
#1374 is closed. #1394 item 1 is folded into that open design issue.
Explicitly not in the GA window
Additive, internal, or backward-compatible — ship whenever: #1395 findings 3-10, #1227, #1245, #576, #947, #986, #338, #126, #957, #949 (loosening only), #1361, #4. #898 is mostly additive (PackManifestOptions is a struct); only the panic-to-error change and any algorithm allowlist would break.
#1294 still deserves a call-out: oci.Store.GC hangs forever on a shadowed variable in gcIndex. Pure bugfix, non-breaking, and it should go in regardless of this sequencing. Still open.
Why this issue exists
v3.0.0-rc.1is tagged. GA closes the breaking-change window, andv2is GA so nothing breaking lands there either. There are currently a dozen-plus open issues that change exported signatures or observable contracts, and several of them mutate the same symbols. Taken in filing order, they would break the same exported functions two or three times inside one release window.This issue is a sequencing proposal, not new scope. Every item below is an existing issue.
Tier 1 — the auth cluster: one break, or three
These issues all mutate the same small set of exported symbols in
registry/remote/authandregistry/remote/credentials.ResourcetypeClient.DoAppendRepositoryScopeCredentialFunc/TokenParamsLogin/Logouthost-keyedScopeResourcecredentialsinterfaceThe proposed order held up. #1380 → #1381 → #1385 → #1382 + #1383 → #1384 landed in that sequence, and no exported signature in the cluster was broken twice.
What is left
#1451 and #1376 are the scope half, and they still collide: both rewrite
WithScopesForHost/AppendScopesForHost/GetScopesForHost. They should land as one change, not two. #1385's part of that collision is already resolved.#873 is no longer blocked, and no longer breaking. Its stated dependency — "must be defined after #1382, or its key type is wrong on arrival" — is discharged. With the key type settled, every caller of
credentials.Storeuses exactly one of its three methods (NewCredentialFunc→Get,Login→Put,Logout→Delete), so the split is mechanical and source-compatible for callers and implementers alike. The issue body has been updated with the current scope.Decided: the granular getter is keyed by
serverAddress string, notproperties.Resource. AResource-keyed store interface would break every third-party store while pushing theResource→ server-address mapping into each implementation, and it does not resolve #1431 (a return-shape problem) or #1453 (already handled by #1457). If it is ever wanted it can be added additively as an optionalResourceGetter. Rationale recorded in the issue.#873 also now carries the
NamespaceMatcherembed fix — see #1455 below.Follow-on issues the cluster produced
Namespaced credentials turned out to have consequences beyond the signatures. These were filed during the Tier 1 work and are part of finishing it:
credentialspackage (decided) #873: one of its two options adds a method to whatever interface Introduce more granular interface intocredentialspackage (decided) #873 defines.credHelpersentirely. PR fix(credentials): use the host's credential helper for a namespaced key #1457 open. Makes namespaced login unusable for ECR/GAR until fixed.dbb5bb4), landingNamespaceMatcher interface { Store; MatchesNamespace(string) bool }. It merged ahead of Introduce more granular interface intocredentialspackage (decided) #873, so it embeds the fullStorewhere it should embed the granular getter. Not a problem yet: the interface is not inv3.0.0-rc.1, so narrowing it costs nothing today. The fix has been folded into Introduce more granular interface intocredentialspackage (decided) #873's scope. It needs to happen before GA.Tier 2 — finish the
registry.Referencedeprecation ✅#1387 and #1386 are closed (#1392, #1393). #1394 item 5 (the layering) remains part of that open design issue.
The silent-hazard concern was addressed as suggested:
internal/interfacesnow carries bothReferenceParserandLegacyReferenceParser, andcontent.gotries each in turn (content.go:61,68), so a third-partyTargeton the old signature still matches and still gets scope hints. The transition period is in place; the release note for when it is removed is still owed.Tier 3 — security fixes that change parse output ✅
#1388, #1389, #1390 and #1396 are all closed.
#1388 and #1389 were fixed together by normalizing the registry host case in
properties.NewReference(#1402), closing both fail-open bypasses with one change, as proposed. #1390 landed in #1397. #1396 is fixed.Tier 4 — semantics and defaults
Each of these is defensible either way; the point is that not deciding is itself a decision once GA ships. This is now the tier with the most left in it.
oras.Copy()follow manifests specified in thelayersor theblobsfield? #401 — 🔲 shouldCopy()follow manifests in thelayers/blobsfield? Milestoned v3.0.0, open since 2023. Traversal semantics are much harder to change post-GA.MaxWait: 3 * time.Second(retry/policy.go) effectively neutersRetry-Afteron 429s. Raising it makes retried operations take materially longer.defaultConcurrency = 3(copy.go), measured ~5.5x slower than 32 on a latency-bound 40-layer copy. Raising the default is an observable behaviour change. Finding 1 (the pooled 1 MiB buffer) landed in perf(content): actually use the pooled 1 MiB copy buffer #1418; the rest of that audit is non-breaking and can ship anytime.Tier 5 — remove dead API while removal is still free ✅
#1374 is closed. #1394 item 1 is folded into that open design issue.
Explicitly not in the GA window
Additive, internal, or backward-compatible — ship whenever: #1395 findings 3-10, #1227, #1245, #576, #947, #986, #338, #126, #957, #949 (loosening only), #1361, #4. #898 is mostly additive (
PackManifestOptionsis a struct); only the panic-to-error change and any algorithm allowlist would break.#1294 still deserves a call-out:
oci.Store.GChangs forever on a shadowed variable ingcIndex. Pure bugfix, non-breaking, and it should go in regardless of this sequencing. Still open.What is actually left before GA
credentialspackage (decided) #873 — decided, not yet implemented. Carries theNamespaceMatcherembed fix that feat(auth): let the store own the namespace walk when it matches namespaces #1455 left behind: free to change while unreleased, breaking once GA ships it. auth: credential precedence is unspecified when the most-specific namespace match has no credentials #1431 is worth settling first soGetteris not defined twice, but does not block.oras.Copy()follow manifests specified in thelayersor theblobsfield? #401, Retry MaxWait 3 seconds is too short! Jitter for 429/TooManyRequests? #1210, Performance audit: 10 findings in the copy engine, content stores, and registry client #1395 finding 2) — decide rather than let GA decide.