| FazBrowse GitHub Viewer | Trending | | Home |
| Tools: [Download Repo ZIP] [Original HTTPS Page] |
An allOf over two distinct recursive components merges into a node whose recursion the in-flight guard anchors at the result being built: the value is right (a cycle in the input is a cycle in the merged output) but the edge carries no $ref, and a ref-less cycle has no serialized form, so 'oasdiff flatten' overflowed the stack marshaling it. The merge now records every edge the guard anchors, and MergeSpec names their targets: a target that is a named component gets that name, and an anonymous target is hoisted into components.schemas under a generated AllOfMergedN name. Names are assigned in the document's walk order, so identical inputs produce identical output. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01QDvUFsg5nu1NBWQffErGDw
Codecov Report❌ Patch coverage is 90.47619% with 4 lines in your changes missing coverage. Please review.
@@ Coverage Diff @@
## main #1240 +/- ##
==========================================
- Coverage 92.26% 92.26% -0.01%
==========================================
Files 345 345
Lines 14277 14312 +35
==========================================
+ Hits 13173 13205 +32
- Misses 1104 1107 +3
Flags with carried forward coverage won't be shown. Click here to find out more. ☔ View full report in Codecov by Harness.
|
Sorry, something went wrong.
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01QDvUFsg5nu1NBWQffErGDw
| Back | FazBrowse Home | New Git URL |
Closes the limitation documented in #1233: an allOf over two distinct recursive components still crashed oasdiff flatten with a stack overflow.
Why this shape resisted #1233
allOf: [$ref NodeA, $ref NodeB], each recursive, merges a child set with two distinct schemas — no lone schema to reuse — so flattenSchemas must run, and its in-flight guard anchors the recursive edge at the result being built. The anchor's value is semantically right: the merged node's recursion is the merged node itself (merge(A,B) recursively equals merge(A,B)). What's wrong is only the representation: the merged node is anonymous, the edge carries no $ref, and a ref-less cycle has no serialized form.
The fix: give the anchor a name
The fixture now flattens to:
with the inline occurrence referencing it, and NodeA/NodeB untouched.
Scope note: the naming pass runs in MergeSpec (it needs the components map); the schema-level Merge API is unchanged and can still produce in-memory ref-less cycles for library callers, which the diff's in-flight guard (#1231) handles.
Regression test asserts the hoisted name, the shared identity between the inline node and the component, a successful marshal of the whole document, and byte-identical output across two loads. Full suite and lint pass; breaking --flatten-allof on the shape stays green as before.