Replace {@includeCode} with synced code fences

Migrate JSDoc and markdown documentation from `{@includeCode ./file#region}`
tags to inline code fences with `source="./file#region"` attributes.
Code examples are now visible directly in source files while remaining
type-checked via their `.examples.ts` source files.

Add `scripts/sync-snippets.ts` to extract code from `//#region` blocks
and sync it into labeled fences. Run with `npm run sync:snippets`.

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
This commit is contained in:
Jonathan Hefner 2026-01-22 17:30:43 -06:00
commit 58019a48ce
No known key found for this signature in database
GPG key ID: 0DA40AFD21043691
5 changed files with 1776 additions and 96 deletions

View file

@ -17,7 +17,19 @@
* @module @modelcontextprotocol/ext-apps/react
*
* @example Basic React App
* {@includeCode ./index.examples.tsx#index_basicReactApp}
* ```tsx source="./index.examples.tsx#index_basicReactApp"
* function MyApp() {
* const { app, isConnected, error } = useApp({
* appInfo: { name: "MyApp", version: "1.0.0" },
* capabilities: {},
* });
*
* if (error) return <div>Error: {error.message}</div>;
* if (!isConnected) return <div>Connecting...</div>;
*
* return <div>Connected!</div>;
* }
* ```
*/
export * from "./useApp";
export * from "./useAutoResize";

View file

@ -30,7 +30,17 @@ export interface UseAppOptions {
* @param app - The newly created `App` instance
*
* @example Register an event handler
* {@includeCode ./useApp.examples.tsx#useApp_registerHandler}
* ```tsx source="./useApp.examples.tsx#useApp_registerHandler"
* useApp({
* appInfo: { name: "MyApp", version: "1.0.0" },
* capabilities: {},
* onAppCreated: (app) => {
* app.ontoolresult = (result) => {
* console.log("Tool result:", result);
* };
* },
* });
* ```
*/
onAppCreated?: (app: App) => void;
}
@ -70,7 +80,39 @@ export interface AppState {
* timeouts, initialization handshake failures, or transport errors).
*
* @example Basic usage of useApp hook with common event handlers
* {@includeCode ./useApp.examples.tsx#useApp_basicUsage}
* ```tsx source="./useApp.examples.tsx#useApp_basicUsage"
* function MyApp() {
* const [hostContext, setHostContext] = useState<
* McpUiHostContext | undefined
* >(undefined);
*
* const { app, isConnected, error } = useApp({
* appInfo: { name: "MyApp", version: "1.0.0" },
* capabilities: {},
* onAppCreated: (app) => {
* app.ontoolinput = (input) => {
* console.log("Tool input:", input);
* };
* app.ontoolresult = (result) => {
* console.log("Tool result:", result);
* };
* app.ontoolcancelled = (params) => {
* console.log("Tool cancelled:", params.reason);
* };
* app.onerror = (error) => {
* console.log("Error:", error);
* };
* app.onhostcontextchanged = (params) => {
* setHostContext((prev) => ({ ...prev, ...params }));
* };
* },
* });
*
* if (error) return <div>Error: {error.message}</div>;
* if (!isConnected) return <div>Connecting...</div>;
* return <div>Theme: {hostContext?.theme}</div>;
* }
* ```
*
* @see {@link App.connect `App.connect`} for the underlying connection method
* @see {@link useAutoResize `useAutoResize`} for manual auto-resize control when using custom App options

View file

@ -20,7 +20,33 @@ import { App } from "../app";
* cause unnecessary effect re-runs; omit this parameter.
*
* @example Manual App creation with custom auto-resize control
* {@includeCode ./useAutoResize.examples.tsx#useAutoResize_manualApp}
* ```tsx source="./useAutoResize.examples.tsx#useAutoResize_manualApp"
* function MyComponent() {
* // For custom App options, create App manually instead of using useApp
* const [app, setApp] = useState<App | null>(null);
* const [error, setError] = useState<Error | null>(null);
*
* useEffect(() => {
* const myApp = new App(
* { name: "MyApp", version: "1.0.0" },
* {}, // capabilities
* { autoResize: false }, // Disable default auto-resize
* );
*
* const transport = new PostMessageTransport(window.parent, window.parent);
* myApp
* .connect(transport)
* .then(() => setApp(myApp))
* .catch((err) => setError(err));
* }, []);
*
* // Add manual auto-resize control
* useAutoResize(app);
*
* if (error) return <div>Connection failed: {error.message}</div>;
* return <div>My content</div>;
* }
* ```
*
* @see {@link App.setupSizeChangedNotifications `App.setupSizeChangedNotifications`} for the underlying implementation
* @see {@link useApp `useApp`} which enables auto-resize by default

View file

@ -15,10 +15,31 @@ import { McpUiTheme } from "../types";
* @returns The current theme ("light" or "dark")
*
* @example Conditionally render based on theme
* {@includeCode ./useDocumentTheme.examples.tsx#useDocumentTheme_conditionalRender}
* ```tsx source="./useDocumentTheme.examples.tsx#useDocumentTheme_conditionalRender"
* function MyApp() {
* const theme = useDocumentTheme();
*
* return <div>{theme === "dark" ? <DarkIcon /> : <LightIcon />}</div>;
* }
* ```
*
* @example Use with theme-aware styling
* {@includeCode ./useDocumentTheme.examples.tsx#useDocumentTheme_themedButton}
* ```tsx source="./useDocumentTheme.examples.tsx#useDocumentTheme_themedButton"
* function ThemedButton() {
* const theme = useDocumentTheme();
*
* return (
* <button
* style={{
* background: theme === "dark" ? "#333" : "#fff",
* color: theme === "dark" ? "#fff" : "#333",
* }}
* >
* Click me
* </button>
* );
* }
* ```
*
* @see {@link getDocumentTheme `getDocumentTheme`} for the underlying function
* @see {@link applyDocumentTheme `applyDocumentTheme`} to set the theme

View file

@ -26,7 +26,23 @@ import { McpUiHostContext } from "../types";
* If provided, styles and theme will be applied immediately on mount.
*
* @example
* {@includeCode ./useHostStyles.examples.tsx#useHostStyleVariables_basicUsage}
* ```tsx source="./useHostStyles.examples.tsx#useHostStyleVariables_basicUsage"
* function MyApp() {
* const { app } = useApp({
* appInfo: { name: "MyApp", version: "1.0.0" },
* capabilities: {},
* });
*
* // Apply host styles - pass initial context to apply styles from connect() immediately
* useHostStyleVariables(app, app?.getHostContext());
*
* return (
* <div style={{ background: "var(--color-background-primary)" }}>
* Hello!
* </div>
* );
* }
* ```
*
* @see {@link applyHostStyleVariables `applyHostStyleVariables`} for the underlying styles function
* @see {@link applyDocumentTheme `applyDocumentTheme`} for the underlying theme function
@ -89,7 +105,19 @@ export function useHostStyleVariables(
* If provided, fonts will be applied immediately on mount.
*
* @example Basic usage with useApp
* {@includeCode ./useHostStyles.examples.tsx#useHostFonts_basicUsage}
* ```tsx source="./useHostStyles.examples.tsx#useHostFonts_basicUsage"
* function MyApp() {
* const { app } = useApp({
* appInfo: { name: "MyApp", version: "1.0.0" },
* capabilities: {},
* });
*
* // Apply host fonts - pass initial context to apply fonts from connect() immediately
* useHostFonts(app, app?.getHostContext());
*
* return <div style={{ fontFamily: "var(--font-sans)" }}>Hello!</div>;
* }
* ```
*
* @see {@link applyHostFonts `applyHostFonts`} for the underlying fonts function
* @see {@link useHostStyleVariables `useHostStyleVariables`} for applying style variables and theme
@ -136,7 +164,23 @@ export function useHostFonts(
* Pass `app?.getHostContext()` to apply styles immediately on mount.
*
* @example
* {@includeCode ./useHostStyles.examples.tsx#useHostStyles_basicUsage}
* ```tsx source="./useHostStyles.examples.tsx#useHostStyles_basicUsage"
* function MyApp() {
* const { app } = useApp({
* appInfo: { name: "MyApp", version: "1.0.0" },
* capabilities: {},
* });
*
* // Apply all host styles - pass initial context to apply styles from connect() immediately
* useHostStyles(app, app?.getHostContext());
*
* return (
* <div style={{ background: "var(--color-background-primary)" }}>
* Hello!
* </div>
* );
* }
* ```
*
* @see {@link useHostStyleVariables `useHostStyleVariables`} for style variables and theme only
* @see {@link useHostFonts `useHostFonts`} for fonts only