fix(theme): support multiple x-codeSamples per language (#1204)#1459
Merged
fix(theme): support multiple x-codeSamples per language (#1204)#1459
Conversation
Allow multiple x-codeSamples entries that share the same `lang` to render
as distinct inner tabs disambiguated by their `label`. Previously this
crashed with `Duplicate values "Python, Python" found in <Tabs>` because
`mergeCodeSampleLanguage` used `lang` as the per-sample identity, and the
inner CodeTab's `value` and React `key` collided.
- Build a unique id per sample (`${lang}-${label}` or `${lang}-${index}`)
with a defensive collision suffix so duplicate-label specs render two
visually identical tabs instead of crashing.
- Fix two stale-key bugs in CodeSnippets/index.tsx (`lang.sample` and
`lang.variant` used singular defaults inside `.map` iterations).
- Reset `selectedSample` when the active language changes so the inner
tab strip falls back to the new language's first sample.
- Add `themeConfig.api.hideGeneratedSnippets` (default `false`,
opt-in) to suppress Postman-generated snippets per-operation,
per-language whenever `x-codeSamples` are provided for that language
on that operation. Closes #1036 for users who opt in.
- Add unit tests for `mergeCodeSampleLanguage` covering single-sample,
multi-sample with/without labels, and duplicate-label collision.
- Expand the demo `petstore.yaml` x-codeSamples fixture to exercise all
five paths.
- Document multi-sample usage and the new flag in vendor-extensions.mdx.
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
|
Size Change: +12.8 kB (+0.56%) Total Size: 2.31 MB 📦 View Changed
ℹ️ View Unchanged
|
|
Visit the preview URL for this PR (updated for commit a83a00a): https://docusaurus-openapi-36b86--pr1459-jvinjuwv.web.app (expires Fri, 15 May 2026 16:19:09 GMT) 🔥 via Firebase Hosting GitHub Action 🌎 Sign: bf293780ee827f578864d92193b8c2866acd459f |
…amples The inner x-codeSamples CodeTabs was passing the global selectedSample state as defaultValue for every outer language tab. When selectedSample held an id from a different language (e.g. "Python-KeyPair Auth" while rendering the C# tab), Docusaurus's <Tabs> validation threw: "<Tabs> has a defaultValue 'Python-KeyPair Auth' but none of its children has the corresponding value. Available values are: C#-0." Guard the defaultValue so each language's inner tabs only adopt selectedSample when the id belongs to that language's samples; otherwise fall back to the language's first sample. Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
Adds demo/examples/tests/codeSamples.yaml with one path per supported shape of the x-codeSamples extension so each can be inspected in isolation in the demo's /tests/* sidebar: - /no-samples — control, generated tabs only - /single-sample-no-label — fallback indexed id - /single-sample-with-label — lang-label id - /multiple-samples-with-labels — primary #1204 case - /multiple-samples-no-labels — indexed-id fallback for multi-sample - /duplicate-label-collision — defensive collision suffix - /mixed-languages — verifies cross-language defaultValue scoping - /unmatched-language — sample for a lang not in languageTabs is dropped Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
…pets The previous placement inserted hideGeneratedSnippets between the existing schemaExpansion JSDoc and its declaration, which orphaned the schemaExpansion documentation (TypeScript binds JSDoc to the next declaration; stacked JSDoc blocks only attach the second). Move hideGeneratedSnippets to the end of the api block so each field keeps its own documentation. Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
The full matrix of x-codeSamples shapes (no-label, with-label, multi-with-labels, multi-no-labels, duplicate-label collision) is now covered by demo/examples/tests/codeSamples.yaml. Keep petstore.yaml focused on the realistic reference experience: original C# + PHP samples plus three Python entries demonstrating the multi-sample-per- language path that closes #1204. Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
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.
Summary
x-codeSamplesentries that share alangto render as distinct inner tabs disambiguated by theirlabel. Previously this crashed withDocusaurus error: Duplicate values "Python, Python" found in <Tabs>(issue Allow more than one x-codeSample #1204).CodeSnippets/index.tsxthat used the singularlang.sample/lang.variantdefaults inside.mapiterations, plus seedselectedSampleon language change so the inner tab strip resolves correctly when switching outer tabs.themeConfig.api.hideGeneratedSnippets(defaultfalse) to suppress Postman-generated snippets per-operation, per-language wheneverx-codeSamplesare provided. Closes Remove autogenerated code samples when using x-codesamples #1036 for users who opt in.Behavior
x-codeSamplesx-codeSamplesper langfalse(default)x-codeSamplesper langlabelhideGeneratedSnippets: true+ custom samples for a langThe
samplesarray now stores synthetic ids (${lang}-${label}or${lang}-${index}) instead of barelangstrings. These ids are internal — used as Tabvalue, Reactkey, and the lookup key forsamplesSources. User-visible labels still come fromsamplesLabels. Duplicatelang+labelentries in a spec receive a defensive numeric suffix so the page renders instead of crashing (the visible labels remain identical — author's bug to fix, but no hard failure).Files
packages/docusaurus-theme-openapi-docs/src/theme/ApiExplorer/CodeSnippets/languages.ts— unique sample id generation with collision suffixpackages/docusaurus-theme-openapi-docs/src/theme/ApiExplorer/CodeSnippets/index.tsx— key bug fixes,selectedSamplereset, conditional generated blockpackages/docusaurus-theme-openapi-docs/src/types.d.ts— newthemeConfig.api.hideGeneratedSnippetsfieldpackages/docusaurus-theme-openapi-docs/src/theme/ApiExplorer/CodeSnippets/languages.test.ts— new unit suite (7 tests)demo/examples/petstore.yaml— fixture exercising all five paths (single no-label, single with-label, multi with distinct labels, multi without labels, duplicate-label collision)demo/docs/vendor-extensions.mdx— documentation for multi-sample usage and the new flagTest plan
yarn jest packages/docusaurus-theme-openapi-docs/src/theme/ApiExplorer/CodeSnippets/languages.test.ts— 7/7 passtsc --noEmiton the theme package — cleanyarn workspace demo start) and verify on the addPet operation:Authtabs (defensive collision case) without crashingthemeConfig.api.hideGeneratedSnippets: true, the HTTP/REQUESTS/etc. block disappears for Python/PowerShell/Java/PHP/C# but remains for languages without custom samples (e.g. cURL)Related issues
🤖 Generated with Claude Code