Skip to content

Treat an unchanged map/list component as wire-compatible in diff#119

Merged
ghostdogpr merged 1 commit into
mainfrom
fix/wire-compat-map-equality
Jul 9, 2026
Merged

Treat an unchanged map/list component as wire-compatible in diff#119
ghostdogpr merged 1 commit into
mainfrom
fix/wire-compat-map-equality

Conversation

@ghostdogpr

Copy link
Copy Markdown
Owner

Problem

wireCompatibleScalars recurses into map<K,V> (and repeated) requiring both components to be wire-compatible:

case (Type.MapType(k1, v1), Type.MapType(k2, v2)) => wireCompatibleScalars(k1, k2) && wireCompatibleScalars(v1, v2)

but it had no equality short-circuit. For a component that is unchanged yet is not a member of any wireCompatibleScalarGroups (e.g. a string map key), the recursive call fell through to the group-membership check, which returns false — so an unchanged sibling dragged the whole verdict to incompatible.

Concrete case

map<string, int32> counts = 1;map<string, int64> counts = 1; is a genuinely wire-compatible value widening (map entries are sub-messages; the value field stays varint). But wireCompatibleScalars(String, String) returned false, so the change was classified Error in Wire mode — failing diff --fail-on error on a safe change. The mirror map<int32, string>map<int64, string> (key widening) failed identically.

Fix

Short-circuit identical components: case (a, b) if a == b => true. An unchanged component is trivially wire-compatible with itself, letting the map/list recursion succeed when only a genuinely wire-compatible component changed.

Test

ProtoDiffSpec: both map key- and value-widening cases assert Severity.Info in Wire mode. Red before the fix (Error), green after. Full ProtoDiffSpec (79) green.

wireCompatibleScalars recursed into map and list types requiring both components
to be wire-compatible, but had no equality short-circuit. An unchanged component
that is not a member of a wire-compatible scalar group (e.g. a string map key)
returned false, dragging the whole verdict to incompatible. So a genuinely
wire-safe map value widening such as map<string,int32> -> map<string,int64>
was reported as an Error in Wire mode, failing CI on a safe change.

Short-circuit identical components to wire-compatible.
@ghostdogpr ghostdogpr merged commit 85f7572 into main Jul 9, 2026
3 checks passed
@ghostdogpr ghostdogpr deleted the fix/wire-compat-map-equality branch July 9, 2026 06:21
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