@immediately-run/sdk 0.21.0 → 0.23.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/boot.cjs +8 -4
- package/dist/boot.cjs.map +1 -1
- package/dist/boot.d.cts +22 -2
- package/dist/boot.d.ts +22 -2
- package/dist/boot.js +6 -3
- package/dist/boot.js.map +1 -1
- package/dist/components/Admonition.cjs +58 -0
- package/dist/components/Admonition.cjs.map +1 -0
- package/dist/components/Admonition.d.cts +24 -0
- package/dist/components/Admonition.d.ts +24 -0
- package/dist/components/Admonition.js +34 -0
- package/dist/components/Admonition.js.map +1 -0
- package/dist/components/Link.cjs +64 -0
- package/dist/components/Link.cjs.map +1 -0
- package/dist/components/Link.d.cts +10 -0
- package/dist/components/Link.d.ts +10 -0
- package/dist/components/Link.js +39 -0
- package/dist/components/Link.js.map +1 -0
- package/dist/components/MDXComponents.cjs +17 -38
- package/dist/components/MDXComponents.cjs.map +1 -1
- package/dist/components/MDXComponents.d.cts +13 -13
- package/dist/components/MDXComponents.d.ts +13 -13
- package/dist/components/MDXComponents.js +12 -35
- package/dist/components/MDXComponents.js.map +1 -1
- package/dist/components/WikiLink.cjs +44 -0
- package/dist/components/WikiLink.cjs.map +1 -0
- package/dist/components/WikiLink.d.cts +29 -0
- package/dist/components/WikiLink.d.ts +29 -0
- package/dist/components/WikiLink.js +20 -0
- package/dist/components/WikiLink.js.map +1 -0
- package/dist/index.d.cts +6 -3
- package/dist/index.d.ts +6 -3
- package/dist/mounts.cjs +16 -0
- package/dist/mounts.cjs.map +1 -1
- package/dist/mounts.d.cts +10 -1
- package/dist/mounts.d.ts +10 -1
- package/dist/mounts.js +13 -0
- package/dist/mounts.js.map +1 -1
- package/dist/version.cjs +1 -1
- package/dist/version.cjs.map +1 -1
- package/dist/version.d.cts +1 -1
- package/dist/version.d.ts +1 -1
- package/dist/version.js +1 -1
- package/dist/version.js.map +1 -1
- package/package.json +1 -1
package/dist/boot.cjs
CHANGED
|
@@ -21,7 +21,8 @@ __export(boot_exports, {
|
|
|
21
21
|
CATCH_ALL_ROUTING_SPEC: () => CATCH_ALL_ROUTING_SPEC,
|
|
22
22
|
DEFAULT_ROUTING_SPEC: () => DEFAULT_ROUTING_SPEC,
|
|
23
23
|
TinkerableApp: () => TinkerableApp,
|
|
24
|
-
boot: () => boot
|
|
24
|
+
boot: () => boot,
|
|
25
|
+
resolveMdxComponents: () => resolveMdxComponents
|
|
25
26
|
});
|
|
26
27
|
module.exports = __toCommonJS(boot_exports);
|
|
27
28
|
var import_jsx_runtime = require("react/jsx-runtime");
|
|
@@ -40,6 +41,7 @@ var import_routing = require("./routing");
|
|
|
40
41
|
var import_sandboxUtils = require("./sandboxUtils");
|
|
41
42
|
var import_TinkerableContext = require("./TinkerableContext");
|
|
42
43
|
var import_urlUtils = require("./urlUtils");
|
|
44
|
+
const resolveMdxComponents = (mdxComponents) => mdxComponents === void 0 ? import_MDXComponents.DEFAULT_MDX_COMPONENTS : typeof mdxComponents === "function" ? mdxComponents(import_MDXComponents.DEFAULT_MDX_COMPONENTS) : { ...import_MDXComponents.DEFAULT_MDX_COMPONENTS, ...mdxComponents };
|
|
43
45
|
const updateAlreadyApplied = (filesMetadata, update) => {
|
|
44
46
|
for (let [key, value] of Object.entries(update)) {
|
|
45
47
|
if (filesMetadata[key] !== value) {
|
|
@@ -108,7 +110,7 @@ const CATCH_ALL_ROUTING_SPEC = {
|
|
|
108
110
|
routes: [{ name: "AppRoot", pattern: /^.*$/, element: null }]
|
|
109
111
|
};
|
|
110
112
|
const boot = ({
|
|
111
|
-
mdxComponents
|
|
113
|
+
mdxComponents,
|
|
112
114
|
routingSpec,
|
|
113
115
|
children
|
|
114
116
|
} = {}) => {
|
|
@@ -116,11 +118,12 @@ const boot = ({
|
|
|
116
118
|
if (!rootElement) {
|
|
117
119
|
throw new Error("boot requires root HTML element to exist");
|
|
118
120
|
}
|
|
121
|
+
const resolvedComponents = resolveMdxComponents(mdxComponents);
|
|
119
122
|
const spec = routingSpec ?? (children ? CATCH_ALL_ROUTING_SPEC : DEFAULT_ROUTING_SPEC);
|
|
120
123
|
const moduleCache = new import_moduleCache.ModuleCache();
|
|
121
124
|
const root = (0, import_client.createRoot)(rootElement);
|
|
122
125
|
root.render(
|
|
123
|
-
/* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_react.StrictMode, { children: /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_moduleCache.ModuleCacheContextProvider, { moduleCache, children: /* @__PURE__ */ (0, import_jsx_runtime.jsxs)(import_MDXProvider.MDXProvider, { components:
|
|
126
|
+
/* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_react.StrictMode, { children: /* @__PURE__ */ (0, import_jsx_runtime.jsx)(import_moduleCache.ModuleCacheContextProvider, { moduleCache, children: /* @__PURE__ */ (0, import_jsx_runtime.jsxs)(import_MDXProvider.MDXProvider, { components: resolvedComponents, children: [
|
|
124
127
|
/* @__PURE__ */ (0, import_jsx_runtime.jsx)(BootMarkers, {}),
|
|
125
128
|
/* @__PURE__ */ (0, import_jsx_runtime.jsx)(TinkerableApp, { routingSpec: spec, children })
|
|
126
129
|
] }) }) })
|
|
@@ -131,6 +134,7 @@ const boot = ({
|
|
|
131
134
|
CATCH_ALL_ROUTING_SPEC,
|
|
132
135
|
DEFAULT_ROUTING_SPEC,
|
|
133
136
|
TinkerableApp,
|
|
134
|
-
boot
|
|
137
|
+
boot,
|
|
138
|
+
resolveMdxComponents
|
|
135
139
|
});
|
|
136
140
|
//# sourceMappingURL=boot.cjs.map
|
package/dist/boot.cjs.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/boot.tsx"],"sourcesContent":["import { FC, ReactNode, StrictMode, useEffect, useLayoutEffect, useState } from 'react';\nimport { createRoot } from 'react-dom/client';\n\nimport { emitMarkerOnce } from './markers';\n\nimport { ErrorNotFound } from './components/errors';\nimport { FileRouter } from './components/FileRouter';\nimport { MainContent } from './components/MainContent';\nimport { DEFAULT_MDX_COMPONENTS } from './components/MDXComponents';\nimport { getInitialContext, updateContext } from './contextUtils';\nimport { getInjectedMetadataEmitter, resolveMetadataSource } from './injectedBundler';\nimport { MDXProvider } from './MDXProvider';\nimport { ModuleCache, ModuleCacheContextProvider } from './moduleCache';\nimport { Router } from './routing';\nimport type { RoutingSpec } from './RoutingSpec';\nimport { FilesMetadata } from './sandboxTypes';\nimport { addListener } from './sandboxUtils';\nimport { TinkerableContext, TinkerableState } from './TinkerableContext';\nimport { FILES_PREFIX } from './urlUtils';\n\n/** Options for {@link boot}: MDX overrides, a route table, or an app root. */\nexport type BootProps = {\n mdxComponents?: Record<string, FC>;\n routingSpec?: RoutingSpec;\n /**\n * App root rendered directly inside the providers (with full navigation\n * context), instead of dispatching through a `routingSpec`. Render\n * `<Routes>`/`<Route>` here for fully dynamic routing — no catch-all rule\n * boilerplate. Takes precedence over `routingSpec` for what is rendered.\n */\n children?: ReactNode;\n};\n\nconst updateAlreadyApplied = (filesMetadata: FilesMetadata, update: FilesMetadata) => {\n for (let [key, value] of Object.entries(update)) {\n if (filesMetadata[key] !== value) {\n return false;\n }\n }\n return true;\n};\n\n/** The app shell {@link boot} renders: holds navigation state, subscribes to host\n * URL + metadata pushes, and renders `children` or the route `<Router />`. */\nexport const TinkerableApp = ({\n routingSpec,\n children,\n}: {\n routingSpec: RoutingSpec;\n children?: ReactNode;\n}) => {\n const [context, setContext] = useState<TinkerableState>(getInitialContext(routingSpec));\n useEffect(() => {\n const removeListener = addListener('urlchange', ({ url }) => {\n setContext((context) => {\n const updatedContext = updateContext(context, url);\n if (updatedContext !== context) {\n console.log(\n `[Sandbox] Updating path from ${context.navigationState.sandboxPath} to ${updatedContext.navigationState.sandboxPath}`\n );\n }\n return updatedContext;\n });\n });\n return removeListener;\n }, [setContext]);\n useEffect(() => {\n // Phase 5 dual-mode (SDK_PACKAGING_SPEC §4/§8): prefer the injected bundler's\n // metadata emitter (the live path, byte-identical); when the SDK is npm-fetched\n // with no injection, `event` is undefined so `addListener` receives\n // 'metadata-update' over the §4 transport instead, and `enable` is a no-op.\n const source = resolveMetadataSource(getInjectedMetadataEmitter());\n const dispose = addListener(\n 'metadata-update',\n ({ update }: Record<string, any>) => {\n setContext((prevContext) =>\n updateAlreadyApplied(prevContext.filesMetadata, update)\n ? prevContext\n : {\n ...prevContext,\n filesMetadata: {\n // TODO: file deletion!\n ...prevContext.filesMetadata,\n ...update,\n },\n }\n );\n },\n source.event\n );\n source.enable();\n return dispose;\n }, [setContext]);\n\n return (\n <TinkerableContext value={context}>\n {children ?? <Router />}\n </TinkerableContext>\n );\n};\n\n// Boot marker emitter (LOAD_PROFILING_SPEC §3, R3-46). Rendered at the top of the\n// app tree so its layout effect fires on the FIRST root-render commit: that instant\n// is `ir.fmp` (the content is in the DOM, about to paint) and the baseline for\n// `ir.interactive` (the host treats a forwarded `ir.interactive` as the root-commit\n// signal and resolves `max(commit, reportReady)` — LP2-3 — so this can only ever be\n// delayed by an app's `reportReady()`, never advanced). Emitted in canonical stream\n// order (fmp then interactive); idempotent per name (StrictMode-safe). Renders null.\nconst BootMarkers = (): null => {\n useLayoutEffect(() => {\n emitMarkerOnce('ir.fmp');\n emitMarkerOnce('ir.interactive');\n }, []);\n return null;\n};\n\n/** The default route table when `boot` is called with no `routingSpec`/`children`:\n * `/` → main content, `/files/<path>` → the file router, else not-found.\n * Re-expressed with path templates (SANDBOX_ROUTING_SPEC §7); the file path\n * surfaces under the `*` wildcard. The catch-all stays a raw RegExp — the\n * escape hatch — so it anchors `.+` (a non-empty path) exactly as before. */\nexport const DEFAULT_ROUTING_SPEC: RoutingSpec = {\n routes: [\n { name: 'MainContent', pattern: '/', element: <MainContent /> },\n { name: 'FileRouter', pattern: `${FILES_PREFIX}/*`, element: <FileRouter /> },\n { name: 'ErrorNotFound', pattern: /^(?<path>.+)$/, element: <ErrorNotFound /> },\n ],\n};\n\n/**\n * Matches any `sandboxPath` so navigation context can be built without a route\n * table. Used when {@link boot} is given `children` (the app owns dispatch via\n * `<Routes>`); the catch-all's `element` is never rendered (children are).\n */\nexport const CATCH_ALL_ROUTING_SPEC: RoutingSpec = {\n routes: [{ name: 'AppRoot', pattern: /^.*$/, element: null }],\n};\n\n/**\n * Mount an immediately.run app into the sandbox `#root`. The entry point every\n * app calls from `index.tsx`: wires the MDX, module-cache, and navigation\n * providers, then renders the route table (`routingSpec`) or your `children`.\n */\nexport const boot = ({\n mdxComponents = DEFAULT_MDX_COMPONENTS,\n routingSpec,\n children,\n}: BootProps = {}) => {\n const rootElement = document.getElementById('root');\n if (!rootElement) {\n throw new Error('boot requires root HTML element to exist');\n }\n // `children` own dispatch, so a catch-all keeps navigation working without a\n // table; otherwise fall back to the default file/main-content routes.\n const spec = routingSpec ?? (children ? CATCH_ALL_ROUTING_SPEC : DEFAULT_ROUTING_SPEC);\n const moduleCache = new ModuleCache();\n const root = createRoot(rootElement);\n root.render(\n <StrictMode>\n <ModuleCacheContextProvider moduleCache={moduleCache}>\n <MDXProvider components={mdxComponents}>\n <BootMarkers />\n <TinkerableApp routingSpec={spec}>{children}</TinkerableApp>\n </MDXProvider>\n </ModuleCacheContextProvider>\n </StrictMode>\n );\n};\n"],"mappings":"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","names":["context"]}
|
|
1
|
+
{"version":3,"sources":["../src/boot.tsx"],"sourcesContent":["import { FC, ReactNode, StrictMode, useEffect, useLayoutEffect, useState } from 'react';\nimport { createRoot } from 'react-dom/client';\n\nimport { emitMarkerOnce } from './markers';\n\nimport { ErrorNotFound } from './components/errors';\nimport { FileRouter } from './components/FileRouter';\nimport { MainContent } from './components/MainContent';\nimport { DEFAULT_MDX_COMPONENTS } from './components/MDXComponents';\nimport { getInitialContext, updateContext } from './contextUtils';\nimport { getInjectedMetadataEmitter, resolveMetadataSource } from './injectedBundler';\nimport { MDXProvider } from './MDXProvider';\nimport { ModuleCache, ModuleCacheContextProvider } from './moduleCache';\nimport { Router } from './routing';\nimport type { RoutingSpec } from './RoutingSpec';\nimport { FilesMetadata } from './sandboxTypes';\nimport { addListener } from './sandboxUtils';\nimport { TinkerableContext, TinkerableState } from './TinkerableContext';\nimport { FILES_PREFIX } from './urlUtils';\n\n/** A map of MDX component overrides, or a function that receives the platform\n * {@link DEFAULT_MDX_COMPONENTS} and returns the full map to use. */\nexport type MdxComponents =\n | Record<string, FC>\n | ((defaults: Record<string, FC>) => Record<string, FC>);\n\n/**\n * Resolve the effective MDX component map from a {@link BootProps.mdxComponents}\n * value (MARKDOWN_SYNTAX_SPEC §11.3):\n * - `undefined` → the platform {@link DEFAULT_MDX_COMPONENTS} (same reference).\n * - a **function** → the full-replace escape hatch, handed the defaults.\n * - a **map** → merged *over* the defaults (`{ ...defaults, ...map }`), so\n * overriding one component keeps the rest — the phantom-defaults invariant\n * (§11.2) that stops the MDX missing-reference guard from firing.\n */\nexport const resolveMdxComponents = (mdxComponents?: MdxComponents): Record<string, FC> =>\n mdxComponents === undefined\n ? (DEFAULT_MDX_COMPONENTS as Record<string, FC>)\n : typeof mdxComponents === 'function'\n ? mdxComponents(DEFAULT_MDX_COMPONENTS as Record<string, FC>)\n : { ...(DEFAULT_MDX_COMPONENTS as Record<string, FC>), ...mdxComponents };\n\n/** Options for {@link boot}: MDX overrides, a route table, or an app root. */\nexport type BootProps = {\n /**\n * MDX component overrides. A **map** is *merged over* the platform defaults\n * ({@link DEFAULT_MDX_COMPONENTS}) — so overriding `WikiLink` alone keeps the\n * default `a` and `Admonition` (MARKDOWN_SYNTAX_SPEC §11.3). Pass a **function**\n * `(defaults) => map` as the full-replace escape hatch when you want complete\n * control over the set.\n */\n mdxComponents?: MdxComponents;\n routingSpec?: RoutingSpec;\n /**\n * App root rendered directly inside the providers (with full navigation\n * context), instead of dispatching through a `routingSpec`. Render\n * `<Routes>`/`<Route>` here for fully dynamic routing — no catch-all rule\n * boilerplate. Takes precedence over `routingSpec` for what is rendered.\n */\n children?: ReactNode;\n};\n\nconst updateAlreadyApplied = (filesMetadata: FilesMetadata, update: FilesMetadata) => {\n for (let [key, value] of Object.entries(update)) {\n if (filesMetadata[key] !== value) {\n return false;\n }\n }\n return true;\n};\n\n/** The app shell {@link boot} renders: holds navigation state, subscribes to host\n * URL + metadata pushes, and renders `children` or the route `<Router />`. */\nexport const TinkerableApp = ({\n routingSpec,\n children,\n}: {\n routingSpec: RoutingSpec;\n children?: ReactNode;\n}) => {\n const [context, setContext] = useState<TinkerableState>(getInitialContext(routingSpec));\n useEffect(() => {\n const removeListener = addListener('urlchange', ({ url }) => {\n setContext((context) => {\n const updatedContext = updateContext(context, url);\n if (updatedContext !== context) {\n console.log(\n `[Sandbox] Updating path from ${context.navigationState.sandboxPath} to ${updatedContext.navigationState.sandboxPath}`\n );\n }\n return updatedContext;\n });\n });\n return removeListener;\n }, [setContext]);\n useEffect(() => {\n // Phase 5 dual-mode (SDK_PACKAGING_SPEC §4/§8): prefer the injected bundler's\n // metadata emitter (the live path, byte-identical); when the SDK is npm-fetched\n // with no injection, `event` is undefined so `addListener` receives\n // 'metadata-update' over the §4 transport instead, and `enable` is a no-op.\n const source = resolveMetadataSource(getInjectedMetadataEmitter());\n const dispose = addListener(\n 'metadata-update',\n ({ update }: Record<string, any>) => {\n setContext((prevContext) =>\n updateAlreadyApplied(prevContext.filesMetadata, update)\n ? prevContext\n : {\n ...prevContext,\n filesMetadata: {\n // TODO: file deletion!\n ...prevContext.filesMetadata,\n ...update,\n },\n }\n );\n },\n source.event\n );\n source.enable();\n return dispose;\n }, [setContext]);\n\n return (\n <TinkerableContext value={context}>\n {children ?? <Router />}\n </TinkerableContext>\n );\n};\n\n// Boot marker emitter (LOAD_PROFILING_SPEC §3, R3-46). Rendered at the top of the\n// app tree so its layout effect fires on the FIRST root-render commit: that instant\n// is `ir.fmp` (the content is in the DOM, about to paint) and the baseline for\n// `ir.interactive` (the host treats a forwarded `ir.interactive` as the root-commit\n// signal and resolves `max(commit, reportReady)` — LP2-3 — so this can only ever be\n// delayed by an app's `reportReady()`, never advanced). Emitted in canonical stream\n// order (fmp then interactive); idempotent per name (StrictMode-safe). Renders null.\nconst BootMarkers = (): null => {\n useLayoutEffect(() => {\n emitMarkerOnce('ir.fmp');\n emitMarkerOnce('ir.interactive');\n }, []);\n return null;\n};\n\n/** The default route table when `boot` is called with no `routingSpec`/`children`:\n * `/` → main content, `/files/<path>` → the file router, else not-found.\n * Re-expressed with path templates (SANDBOX_ROUTING_SPEC §7); the file path\n * surfaces under the `*` wildcard. The catch-all stays a raw RegExp — the\n * escape hatch — so it anchors `.+` (a non-empty path) exactly as before. */\nexport const DEFAULT_ROUTING_SPEC: RoutingSpec = {\n routes: [\n { name: 'MainContent', pattern: '/', element: <MainContent /> },\n { name: 'FileRouter', pattern: `${FILES_PREFIX}/*`, element: <FileRouter /> },\n { name: 'ErrorNotFound', pattern: /^(?<path>.+)$/, element: <ErrorNotFound /> },\n ],\n};\n\n/**\n * Matches any `sandboxPath` so navigation context can be built without a route\n * table. Used when {@link boot} is given `children` (the app owns dispatch via\n * `<Routes>`); the catch-all's `element` is never rendered (children are).\n */\nexport const CATCH_ALL_ROUTING_SPEC: RoutingSpec = {\n routes: [{ name: 'AppRoot', pattern: /^.*$/, element: null }],\n};\n\n/**\n * Mount an immediately.run app into the sandbox `#root`. The entry point every\n * app calls from `index.tsx`: wires the MDX, module-cache, and navigation\n * providers, then renders the route table (`routingSpec`) or your `children`.\n */\nexport const boot = ({\n mdxComponents,\n routingSpec,\n children,\n}: BootProps = {}) => {\n const rootElement = document.getElementById('root');\n if (!rootElement) {\n throw new Error('boot requires root HTML element to exist');\n }\n const resolvedComponents = resolveMdxComponents(mdxComponents);\n // `children` own dispatch, so a catch-all keeps navigation working without a\n // table; otherwise fall back to the default file/main-content routes.\n const spec = routingSpec ?? (children ? CATCH_ALL_ROUTING_SPEC : DEFAULT_ROUTING_SPEC);\n const moduleCache = new ModuleCache();\n const root = createRoot(rootElement);\n root.render(\n <StrictMode>\n <ModuleCacheContextProvider moduleCache={moduleCache}>\n <MDXProvider components={resolvedComponents}>\n <BootMarkers />\n <TinkerableApp routingSpec={spec}>{children}</TinkerableApp>\n </MDXProvider>\n </ModuleCacheContextProvider>\n </StrictMode>\n );\n};\n"],"mappings":"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","names":["context"]}
|
package/dist/boot.d.cts
CHANGED
|
@@ -2,9 +2,29 @@ import * as react_jsx_runtime from 'react/jsx-runtime';
|
|
|
2
2
|
import { FC, ReactNode } from 'react';
|
|
3
3
|
import { RoutingSpec } from './RoutingSpec.cjs';
|
|
4
4
|
|
|
5
|
+
/** A map of MDX component overrides, or a function that receives the platform
|
|
6
|
+
* {@link DEFAULT_MDX_COMPONENTS} and returns the full map to use. */
|
|
7
|
+
type MdxComponents = Record<string, FC> | ((defaults: Record<string, FC>) => Record<string, FC>);
|
|
8
|
+
/**
|
|
9
|
+
* Resolve the effective MDX component map from a {@link BootProps.mdxComponents}
|
|
10
|
+
* value (MARKDOWN_SYNTAX_SPEC §11.3):
|
|
11
|
+
* - `undefined` → the platform {@link DEFAULT_MDX_COMPONENTS} (same reference).
|
|
12
|
+
* - a **function** → the full-replace escape hatch, handed the defaults.
|
|
13
|
+
* - a **map** → merged *over* the defaults (`{ ...defaults, ...map }`), so
|
|
14
|
+
* overriding one component keeps the rest — the phantom-defaults invariant
|
|
15
|
+
* (§11.2) that stops the MDX missing-reference guard from firing.
|
|
16
|
+
*/
|
|
17
|
+
declare const resolveMdxComponents: (mdxComponents?: MdxComponents) => Record<string, FC>;
|
|
5
18
|
/** Options for {@link boot}: MDX overrides, a route table, or an app root. */
|
|
6
19
|
type BootProps = {
|
|
7
|
-
|
|
20
|
+
/**
|
|
21
|
+
* MDX component overrides. A **map** is *merged over* the platform defaults
|
|
22
|
+
* ({@link DEFAULT_MDX_COMPONENTS}) — so overriding `WikiLink` alone keeps the
|
|
23
|
+
* default `a` and `Admonition` (MARKDOWN_SYNTAX_SPEC §11.3). Pass a **function**
|
|
24
|
+
* `(defaults) => map` as the full-replace escape hatch when you want complete
|
|
25
|
+
* control over the set.
|
|
26
|
+
*/
|
|
27
|
+
mdxComponents?: MdxComponents;
|
|
8
28
|
routingSpec?: RoutingSpec;
|
|
9
29
|
/**
|
|
10
30
|
* App root rendered directly inside the providers (with full navigation
|
|
@@ -39,4 +59,4 @@ declare const CATCH_ALL_ROUTING_SPEC: RoutingSpec;
|
|
|
39
59
|
*/
|
|
40
60
|
declare const boot: ({ mdxComponents, routingSpec, children, }?: BootProps) => void;
|
|
41
61
|
|
|
42
|
-
export { type BootProps, CATCH_ALL_ROUTING_SPEC, DEFAULT_ROUTING_SPEC, TinkerableApp, boot };
|
|
62
|
+
export { type BootProps, CATCH_ALL_ROUTING_SPEC, DEFAULT_ROUTING_SPEC, type MdxComponents, TinkerableApp, boot, resolveMdxComponents };
|
package/dist/boot.d.ts
CHANGED
|
@@ -2,9 +2,29 @@ import * as react_jsx_runtime from 'react/jsx-runtime';
|
|
|
2
2
|
import { FC, ReactNode } from 'react';
|
|
3
3
|
import { RoutingSpec } from './RoutingSpec.js';
|
|
4
4
|
|
|
5
|
+
/** A map of MDX component overrides, or a function that receives the platform
|
|
6
|
+
* {@link DEFAULT_MDX_COMPONENTS} and returns the full map to use. */
|
|
7
|
+
type MdxComponents = Record<string, FC> | ((defaults: Record<string, FC>) => Record<string, FC>);
|
|
8
|
+
/**
|
|
9
|
+
* Resolve the effective MDX component map from a {@link BootProps.mdxComponents}
|
|
10
|
+
* value (MARKDOWN_SYNTAX_SPEC §11.3):
|
|
11
|
+
* - `undefined` → the platform {@link DEFAULT_MDX_COMPONENTS} (same reference).
|
|
12
|
+
* - a **function** → the full-replace escape hatch, handed the defaults.
|
|
13
|
+
* - a **map** → merged *over* the defaults (`{ ...defaults, ...map }`), so
|
|
14
|
+
* overriding one component keeps the rest — the phantom-defaults invariant
|
|
15
|
+
* (§11.2) that stops the MDX missing-reference guard from firing.
|
|
16
|
+
*/
|
|
17
|
+
declare const resolveMdxComponents: (mdxComponents?: MdxComponents) => Record<string, FC>;
|
|
5
18
|
/** Options for {@link boot}: MDX overrides, a route table, or an app root. */
|
|
6
19
|
type BootProps = {
|
|
7
|
-
|
|
20
|
+
/**
|
|
21
|
+
* MDX component overrides. A **map** is *merged over* the platform defaults
|
|
22
|
+
* ({@link DEFAULT_MDX_COMPONENTS}) — so overriding `WikiLink` alone keeps the
|
|
23
|
+
* default `a` and `Admonition` (MARKDOWN_SYNTAX_SPEC §11.3). Pass a **function**
|
|
24
|
+
* `(defaults) => map` as the full-replace escape hatch when you want complete
|
|
25
|
+
* control over the set.
|
|
26
|
+
*/
|
|
27
|
+
mdxComponents?: MdxComponents;
|
|
8
28
|
routingSpec?: RoutingSpec;
|
|
9
29
|
/**
|
|
10
30
|
* App root rendered directly inside the providers (with full navigation
|
|
@@ -39,4 +59,4 @@ declare const CATCH_ALL_ROUTING_SPEC: RoutingSpec;
|
|
|
39
59
|
*/
|
|
40
60
|
declare const boot: ({ mdxComponents, routingSpec, children, }?: BootProps) => void;
|
|
41
61
|
|
|
42
|
-
export { type BootProps, CATCH_ALL_ROUTING_SPEC, DEFAULT_ROUTING_SPEC, TinkerableApp, boot };
|
|
62
|
+
export { type BootProps, CATCH_ALL_ROUTING_SPEC, DEFAULT_ROUTING_SPEC, type MdxComponents, TinkerableApp, boot, resolveMdxComponents };
|
package/dist/boot.js
CHANGED
|
@@ -14,6 +14,7 @@ import { Router } from "./routing";
|
|
|
14
14
|
import { addListener } from "./sandboxUtils";
|
|
15
15
|
import { TinkerableContext } from "./TinkerableContext";
|
|
16
16
|
import { FILES_PREFIX } from "./urlUtils";
|
|
17
|
+
const resolveMdxComponents = (mdxComponents) => mdxComponents === void 0 ? DEFAULT_MDX_COMPONENTS : typeof mdxComponents === "function" ? mdxComponents(DEFAULT_MDX_COMPONENTS) : { ...DEFAULT_MDX_COMPONENTS, ...mdxComponents };
|
|
17
18
|
const updateAlreadyApplied = (filesMetadata, update) => {
|
|
18
19
|
for (let [key, value] of Object.entries(update)) {
|
|
19
20
|
if (filesMetadata[key] !== value) {
|
|
@@ -82,7 +83,7 @@ const CATCH_ALL_ROUTING_SPEC = {
|
|
|
82
83
|
routes: [{ name: "AppRoot", pattern: /^.*$/, element: null }]
|
|
83
84
|
};
|
|
84
85
|
const boot = ({
|
|
85
|
-
mdxComponents
|
|
86
|
+
mdxComponents,
|
|
86
87
|
routingSpec,
|
|
87
88
|
children
|
|
88
89
|
} = {}) => {
|
|
@@ -90,11 +91,12 @@ const boot = ({
|
|
|
90
91
|
if (!rootElement) {
|
|
91
92
|
throw new Error("boot requires root HTML element to exist");
|
|
92
93
|
}
|
|
94
|
+
const resolvedComponents = resolveMdxComponents(mdxComponents);
|
|
93
95
|
const spec = routingSpec ?? (children ? CATCH_ALL_ROUTING_SPEC : DEFAULT_ROUTING_SPEC);
|
|
94
96
|
const moduleCache = new ModuleCache();
|
|
95
97
|
const root = createRoot(rootElement);
|
|
96
98
|
root.render(
|
|
97
|
-
/* @__PURE__ */ jsx(StrictMode, { children: /* @__PURE__ */ jsx(ModuleCacheContextProvider, { moduleCache, children: /* @__PURE__ */ jsxs(MDXProvider, { components:
|
|
99
|
+
/* @__PURE__ */ jsx(StrictMode, { children: /* @__PURE__ */ jsx(ModuleCacheContextProvider, { moduleCache, children: /* @__PURE__ */ jsxs(MDXProvider, { components: resolvedComponents, children: [
|
|
98
100
|
/* @__PURE__ */ jsx(BootMarkers, {}),
|
|
99
101
|
/* @__PURE__ */ jsx(TinkerableApp, { routingSpec: spec, children })
|
|
100
102
|
] }) }) })
|
|
@@ -104,6 +106,7 @@ export {
|
|
|
104
106
|
CATCH_ALL_ROUTING_SPEC,
|
|
105
107
|
DEFAULT_ROUTING_SPEC,
|
|
106
108
|
TinkerableApp,
|
|
107
|
-
boot
|
|
109
|
+
boot,
|
|
110
|
+
resolveMdxComponents
|
|
108
111
|
};
|
|
109
112
|
//# sourceMappingURL=boot.js.map
|
package/dist/boot.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/boot.tsx"],"sourcesContent":["import { FC, ReactNode, StrictMode, useEffect, useLayoutEffect, useState } from 'react';\nimport { createRoot } from 'react-dom/client';\n\nimport { emitMarkerOnce } from './markers';\n\nimport { ErrorNotFound } from './components/errors';\nimport { FileRouter } from './components/FileRouter';\nimport { MainContent } from './components/MainContent';\nimport { DEFAULT_MDX_COMPONENTS } from './components/MDXComponents';\nimport { getInitialContext, updateContext } from './contextUtils';\nimport { getInjectedMetadataEmitter, resolveMetadataSource } from './injectedBundler';\nimport { MDXProvider } from './MDXProvider';\nimport { ModuleCache, ModuleCacheContextProvider } from './moduleCache';\nimport { Router } from './routing';\nimport type { RoutingSpec } from './RoutingSpec';\nimport { FilesMetadata } from './sandboxTypes';\nimport { addListener } from './sandboxUtils';\nimport { TinkerableContext, TinkerableState } from './TinkerableContext';\nimport { FILES_PREFIX } from './urlUtils';\n\n/** Options for {@link boot}: MDX overrides, a route table, or an app root. */\nexport type BootProps = {\n mdxComponents?: Record<string, FC>;\n routingSpec?: RoutingSpec;\n /**\n * App root rendered directly inside the providers (with full navigation\n * context), instead of dispatching through a `routingSpec`. Render\n * `<Routes>`/`<Route>` here for fully dynamic routing — no catch-all rule\n * boilerplate. Takes precedence over `routingSpec` for what is rendered.\n */\n children?: ReactNode;\n};\n\nconst updateAlreadyApplied = (filesMetadata: FilesMetadata, update: FilesMetadata) => {\n for (let [key, value] of Object.entries(update)) {\n if (filesMetadata[key] !== value) {\n return false;\n }\n }\n return true;\n};\n\n/** The app shell {@link boot} renders: holds navigation state, subscribes to host\n * URL + metadata pushes, and renders `children` or the route `<Router />`. */\nexport const TinkerableApp = ({\n routingSpec,\n children,\n}: {\n routingSpec: RoutingSpec;\n children?: ReactNode;\n}) => {\n const [context, setContext] = useState<TinkerableState>(getInitialContext(routingSpec));\n useEffect(() => {\n const removeListener = addListener('urlchange', ({ url }) => {\n setContext((context) => {\n const updatedContext = updateContext(context, url);\n if (updatedContext !== context) {\n console.log(\n `[Sandbox] Updating path from ${context.navigationState.sandboxPath} to ${updatedContext.navigationState.sandboxPath}`\n );\n }\n return updatedContext;\n });\n });\n return removeListener;\n }, [setContext]);\n useEffect(() => {\n // Phase 5 dual-mode (SDK_PACKAGING_SPEC §4/§8): prefer the injected bundler's\n // metadata emitter (the live path, byte-identical); when the SDK is npm-fetched\n // with no injection, `event` is undefined so `addListener` receives\n // 'metadata-update' over the §4 transport instead, and `enable` is a no-op.\n const source = resolveMetadataSource(getInjectedMetadataEmitter());\n const dispose = addListener(\n 'metadata-update',\n ({ update }: Record<string, any>) => {\n setContext((prevContext) =>\n updateAlreadyApplied(prevContext.filesMetadata, update)\n ? prevContext\n : {\n ...prevContext,\n filesMetadata: {\n // TODO: file deletion!\n ...prevContext.filesMetadata,\n ...update,\n },\n }\n );\n },\n source.event\n );\n source.enable();\n return dispose;\n }, [setContext]);\n\n return (\n <TinkerableContext value={context}>\n {children ?? <Router />}\n </TinkerableContext>\n );\n};\n\n// Boot marker emitter (LOAD_PROFILING_SPEC §3, R3-46). Rendered at the top of the\n// app tree so its layout effect fires on the FIRST root-render commit: that instant\n// is `ir.fmp` (the content is in the DOM, about to paint) and the baseline for\n// `ir.interactive` (the host treats a forwarded `ir.interactive` as the root-commit\n// signal and resolves `max(commit, reportReady)` — LP2-3 — so this can only ever be\n// delayed by an app's `reportReady()`, never advanced). Emitted in canonical stream\n// order (fmp then interactive); idempotent per name (StrictMode-safe). Renders null.\nconst BootMarkers = (): null => {\n useLayoutEffect(() => {\n emitMarkerOnce('ir.fmp');\n emitMarkerOnce('ir.interactive');\n }, []);\n return null;\n};\n\n/** The default route table when `boot` is called with no `routingSpec`/`children`:\n * `/` → main content, `/files/<path>` → the file router, else not-found.\n * Re-expressed with path templates (SANDBOX_ROUTING_SPEC §7); the file path\n * surfaces under the `*` wildcard. The catch-all stays a raw RegExp — the\n * escape hatch — so it anchors `.+` (a non-empty path) exactly as before. */\nexport const DEFAULT_ROUTING_SPEC: RoutingSpec = {\n routes: [\n { name: 'MainContent', pattern: '/', element: <MainContent /> },\n { name: 'FileRouter', pattern: `${FILES_PREFIX}/*`, element: <FileRouter /> },\n { name: 'ErrorNotFound', pattern: /^(?<path>.+)$/, element: <ErrorNotFound /> },\n ],\n};\n\n/**\n * Matches any `sandboxPath` so navigation context can be built without a route\n * table. Used when {@link boot} is given `children` (the app owns dispatch via\n * `<Routes>`); the catch-all's `element` is never rendered (children are).\n */\nexport const CATCH_ALL_ROUTING_SPEC: RoutingSpec = {\n routes: [{ name: 'AppRoot', pattern: /^.*$/, element: null }],\n};\n\n/**\n * Mount an immediately.run app into the sandbox `#root`. The entry point every\n * app calls from `index.tsx`: wires the MDX, module-cache, and navigation\n * providers, then renders the route table (`routingSpec`) or your `children`.\n */\nexport const boot = ({\n mdxComponents = DEFAULT_MDX_COMPONENTS,\n routingSpec,\n children,\n}: BootProps = {}) => {\n const rootElement = document.getElementById('root');\n if (!rootElement) {\n throw new Error('boot requires root HTML element to exist');\n }\n // `children` own dispatch, so a catch-all keeps navigation working without a\n // table; otherwise fall back to the default file/main-content routes.\n const spec = routingSpec ?? (children ? CATCH_ALL_ROUTING_SPEC : DEFAULT_ROUTING_SPEC);\n const moduleCache = new ModuleCache();\n const root = createRoot(rootElement);\n root.render(\n <StrictMode>\n <ModuleCacheContextProvider moduleCache={moduleCache}>\n <MDXProvider components={mdxComponents}>\n <BootMarkers />\n <TinkerableApp routingSpec={spec}>{children}</TinkerableApp>\n </MDXProvider>\n </ModuleCacheContextProvider>\n </StrictMode>\n );\n};\n"],"mappings":"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","names":["context"]}
|
|
1
|
+
{"version":3,"sources":["../src/boot.tsx"],"sourcesContent":["import { FC, ReactNode, StrictMode, useEffect, useLayoutEffect, useState } from 'react';\nimport { createRoot } from 'react-dom/client';\n\nimport { emitMarkerOnce } from './markers';\n\nimport { ErrorNotFound } from './components/errors';\nimport { FileRouter } from './components/FileRouter';\nimport { MainContent } from './components/MainContent';\nimport { DEFAULT_MDX_COMPONENTS } from './components/MDXComponents';\nimport { getInitialContext, updateContext } from './contextUtils';\nimport { getInjectedMetadataEmitter, resolveMetadataSource } from './injectedBundler';\nimport { MDXProvider } from './MDXProvider';\nimport { ModuleCache, ModuleCacheContextProvider } from './moduleCache';\nimport { Router } from './routing';\nimport type { RoutingSpec } from './RoutingSpec';\nimport { FilesMetadata } from './sandboxTypes';\nimport { addListener } from './sandboxUtils';\nimport { TinkerableContext, TinkerableState } from './TinkerableContext';\nimport { FILES_PREFIX } from './urlUtils';\n\n/** A map of MDX component overrides, or a function that receives the platform\n * {@link DEFAULT_MDX_COMPONENTS} and returns the full map to use. */\nexport type MdxComponents =\n | Record<string, FC>\n | ((defaults: Record<string, FC>) => Record<string, FC>);\n\n/**\n * Resolve the effective MDX component map from a {@link BootProps.mdxComponents}\n * value (MARKDOWN_SYNTAX_SPEC §11.3):\n * - `undefined` → the platform {@link DEFAULT_MDX_COMPONENTS} (same reference).\n * - a **function** → the full-replace escape hatch, handed the defaults.\n * - a **map** → merged *over* the defaults (`{ ...defaults, ...map }`), so\n * overriding one component keeps the rest — the phantom-defaults invariant\n * (§11.2) that stops the MDX missing-reference guard from firing.\n */\nexport const resolveMdxComponents = (mdxComponents?: MdxComponents): Record<string, FC> =>\n mdxComponents === undefined\n ? (DEFAULT_MDX_COMPONENTS as Record<string, FC>)\n : typeof mdxComponents === 'function'\n ? mdxComponents(DEFAULT_MDX_COMPONENTS as Record<string, FC>)\n : { ...(DEFAULT_MDX_COMPONENTS as Record<string, FC>), ...mdxComponents };\n\n/** Options for {@link boot}: MDX overrides, a route table, or an app root. */\nexport type BootProps = {\n /**\n * MDX component overrides. A **map** is *merged over* the platform defaults\n * ({@link DEFAULT_MDX_COMPONENTS}) — so overriding `WikiLink` alone keeps the\n * default `a` and `Admonition` (MARKDOWN_SYNTAX_SPEC §11.3). Pass a **function**\n * `(defaults) => map` as the full-replace escape hatch when you want complete\n * control over the set.\n */\n mdxComponents?: MdxComponents;\n routingSpec?: RoutingSpec;\n /**\n * App root rendered directly inside the providers (with full navigation\n * context), instead of dispatching through a `routingSpec`. Render\n * `<Routes>`/`<Route>` here for fully dynamic routing — no catch-all rule\n * boilerplate. Takes precedence over `routingSpec` for what is rendered.\n */\n children?: ReactNode;\n};\n\nconst updateAlreadyApplied = (filesMetadata: FilesMetadata, update: FilesMetadata) => {\n for (let [key, value] of Object.entries(update)) {\n if (filesMetadata[key] !== value) {\n return false;\n }\n }\n return true;\n};\n\n/** The app shell {@link boot} renders: holds navigation state, subscribes to host\n * URL + metadata pushes, and renders `children` or the route `<Router />`. */\nexport const TinkerableApp = ({\n routingSpec,\n children,\n}: {\n routingSpec: RoutingSpec;\n children?: ReactNode;\n}) => {\n const [context, setContext] = useState<TinkerableState>(getInitialContext(routingSpec));\n useEffect(() => {\n const removeListener = addListener('urlchange', ({ url }) => {\n setContext((context) => {\n const updatedContext = updateContext(context, url);\n if (updatedContext !== context) {\n console.log(\n `[Sandbox] Updating path from ${context.navigationState.sandboxPath} to ${updatedContext.navigationState.sandboxPath}`\n );\n }\n return updatedContext;\n });\n });\n return removeListener;\n }, [setContext]);\n useEffect(() => {\n // Phase 5 dual-mode (SDK_PACKAGING_SPEC §4/§8): prefer the injected bundler's\n // metadata emitter (the live path, byte-identical); when the SDK is npm-fetched\n // with no injection, `event` is undefined so `addListener` receives\n // 'metadata-update' over the §4 transport instead, and `enable` is a no-op.\n const source = resolveMetadataSource(getInjectedMetadataEmitter());\n const dispose = addListener(\n 'metadata-update',\n ({ update }: Record<string, any>) => {\n setContext((prevContext) =>\n updateAlreadyApplied(prevContext.filesMetadata, update)\n ? prevContext\n : {\n ...prevContext,\n filesMetadata: {\n // TODO: file deletion!\n ...prevContext.filesMetadata,\n ...update,\n },\n }\n );\n },\n source.event\n );\n source.enable();\n return dispose;\n }, [setContext]);\n\n return (\n <TinkerableContext value={context}>\n {children ?? <Router />}\n </TinkerableContext>\n );\n};\n\n// Boot marker emitter (LOAD_PROFILING_SPEC §3, R3-46). Rendered at the top of the\n// app tree so its layout effect fires on the FIRST root-render commit: that instant\n// is `ir.fmp` (the content is in the DOM, about to paint) and the baseline for\n// `ir.interactive` (the host treats a forwarded `ir.interactive` as the root-commit\n// signal and resolves `max(commit, reportReady)` — LP2-3 — so this can only ever be\n// delayed by an app's `reportReady()`, never advanced). Emitted in canonical stream\n// order (fmp then interactive); idempotent per name (StrictMode-safe). Renders null.\nconst BootMarkers = (): null => {\n useLayoutEffect(() => {\n emitMarkerOnce('ir.fmp');\n emitMarkerOnce('ir.interactive');\n }, []);\n return null;\n};\n\n/** The default route table when `boot` is called with no `routingSpec`/`children`:\n * `/` → main content, `/files/<path>` → the file router, else not-found.\n * Re-expressed with path templates (SANDBOX_ROUTING_SPEC §7); the file path\n * surfaces under the `*` wildcard. The catch-all stays a raw RegExp — the\n * escape hatch — so it anchors `.+` (a non-empty path) exactly as before. */\nexport const DEFAULT_ROUTING_SPEC: RoutingSpec = {\n routes: [\n { name: 'MainContent', pattern: '/', element: <MainContent /> },\n { name: 'FileRouter', pattern: `${FILES_PREFIX}/*`, element: <FileRouter /> },\n { name: 'ErrorNotFound', pattern: /^(?<path>.+)$/, element: <ErrorNotFound /> },\n ],\n};\n\n/**\n * Matches any `sandboxPath` so navigation context can be built without a route\n * table. Used when {@link boot} is given `children` (the app owns dispatch via\n * `<Routes>`); the catch-all's `element` is never rendered (children are).\n */\nexport const CATCH_ALL_ROUTING_SPEC: RoutingSpec = {\n routes: [{ name: 'AppRoot', pattern: /^.*$/, element: null }],\n};\n\n/**\n * Mount an immediately.run app into the sandbox `#root`. The entry point every\n * app calls from `index.tsx`: wires the MDX, module-cache, and navigation\n * providers, then renders the route table (`routingSpec`) or your `children`.\n */\nexport const boot = ({\n mdxComponents,\n routingSpec,\n children,\n}: BootProps = {}) => {\n const rootElement = document.getElementById('root');\n if (!rootElement) {\n throw new Error('boot requires root HTML element to exist');\n }\n const resolvedComponents = resolveMdxComponents(mdxComponents);\n // `children` own dispatch, so a catch-all keeps navigation working without a\n // table; otherwise fall back to the default file/main-content routes.\n const spec = routingSpec ?? (children ? CATCH_ALL_ROUTING_SPEC : DEFAULT_ROUTING_SPEC);\n const moduleCache = new ModuleCache();\n const root = createRoot(rootElement);\n root.render(\n <StrictMode>\n <ModuleCacheContextProvider moduleCache={moduleCache}>\n <MDXProvider components={resolvedComponents}>\n <BootMarkers />\n <TinkerableApp routingSpec={spec}>{children}</TinkerableApp>\n </MDXProvider>\n </ModuleCacheContextProvider>\n </StrictMode>\n );\n};\n"],"mappings":"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","names":["context"]}
|
|
@@ -0,0 +1,58 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __defProp = Object.defineProperty;
|
|
3
|
+
var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
|
|
4
|
+
var __getOwnPropNames = Object.getOwnPropertyNames;
|
|
5
|
+
var __hasOwnProp = Object.prototype.hasOwnProperty;
|
|
6
|
+
var __export = (target, all) => {
|
|
7
|
+
for (var name in all)
|
|
8
|
+
__defProp(target, name, { get: all[name], enumerable: true });
|
|
9
|
+
};
|
|
10
|
+
var __copyProps = (to, from, except, desc) => {
|
|
11
|
+
if (from && typeof from === "object" || typeof from === "function") {
|
|
12
|
+
for (let key of __getOwnPropNames(from))
|
|
13
|
+
if (!__hasOwnProp.call(to, key) && key !== except)
|
|
14
|
+
__defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
|
|
15
|
+
}
|
|
16
|
+
return to;
|
|
17
|
+
};
|
|
18
|
+
var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
|
|
19
|
+
var Admonition_exports = {};
|
|
20
|
+
__export(Admonition_exports, {
|
|
21
|
+
Admonition: () => Admonition
|
|
22
|
+
});
|
|
23
|
+
module.exports = __toCommonJS(Admonition_exports);
|
|
24
|
+
var import_jsx_runtime = require("react/jsx-runtime");
|
|
25
|
+
const TITLES = {
|
|
26
|
+
note: "Note",
|
|
27
|
+
tip: "Tip",
|
|
28
|
+
important: "Important",
|
|
29
|
+
warning: "Warning",
|
|
30
|
+
caution: "Caution"
|
|
31
|
+
};
|
|
32
|
+
const Admonition = ({
|
|
33
|
+
type = "note",
|
|
34
|
+
title,
|
|
35
|
+
children,
|
|
36
|
+
...rest
|
|
37
|
+
}) => {
|
|
38
|
+
const kind = String(type).toLowerCase();
|
|
39
|
+
const label = title ?? TITLES[kind] ?? TITLES.note;
|
|
40
|
+
return /* @__PURE__ */ (0, import_jsx_runtime.jsxs)(
|
|
41
|
+
"div",
|
|
42
|
+
{
|
|
43
|
+
className: `ir-admonition ir-admonition-${kind}`,
|
|
44
|
+
role: "note",
|
|
45
|
+
"data-admonition": kind,
|
|
46
|
+
...rest,
|
|
47
|
+
children: [
|
|
48
|
+
/* @__PURE__ */ (0, import_jsx_runtime.jsx)("p", { className: "ir-admonition-title", children: label }),
|
|
49
|
+
/* @__PURE__ */ (0, import_jsx_runtime.jsx)("div", { className: "ir-admonition-body", children })
|
|
50
|
+
]
|
|
51
|
+
}
|
|
52
|
+
);
|
|
53
|
+
};
|
|
54
|
+
// Annotate the CommonJS export names for ESM import in node:
|
|
55
|
+
0 && (module.exports = {
|
|
56
|
+
Admonition
|
|
57
|
+
});
|
|
58
|
+
//# sourceMappingURL=Admonition.cjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../../src/components/Admonition.tsx"],"sourcesContent":["import { ReactNode } from 'react';\n\n/** The GitHub admonition kinds the transpiler's `> [!TYPE]` plugin emits (R3-152). */\nexport type AdmonitionType = 'note' | 'tip' | 'important' | 'warning' | 'caution';\n\nconst TITLES: Record<string, string> = {\n note: 'Note',\n tip: 'Tip',\n important: 'Important',\n warning: 'Warning',\n caution: 'Caution',\n};\n\n/**\n * Default MDX `Admonition` component — the render target for the GitHub-style\n * `> [!NOTE]` blockquote-alert syntax (the transpiler remark plugin, R3-152,\n * compiles that syntax to `<Admonition type=\"note\">…</Admonition>`).\n *\n * It is registered in {@link DEFAULT_MDX_COMPONENTS} so an admonition renders\n * even in a plain-markdown repo that never calls `boot({ mdxComponents })` — the\n * MDX missing-reference guard never fires (MARKDOWN_SYNTAX_SPEC §11.2 phantom\n * defaults). The markup is semantic and accessible; **styling is intentionally\n * minimal** — an app supplies CSS targeting the `ir-admonition*` classes, or\n * overrides this component via `boot({ mdxComponents: { Admonition } })`\n * (MARKDOWN_SYNTAX_SPEC §12.3).\n */\nexport const Admonition = ({\n type = 'note',\n title,\n children,\n ...rest\n}: {\n type?: AdmonitionType | string;\n title?: ReactNode;\n children?: ReactNode;\n} & Omit<React.HTMLAttributes<HTMLDivElement>, 'title'>): ReactNode => {\n const kind = String(type).toLowerCase();\n const label = title ?? TITLES[kind] ?? TITLES.note;\n return (\n <div\n className={`ir-admonition ir-admonition-${kind}`}\n role=\"note\"\n data-admonition={kind}\n {...rest}\n >\n <p className=\"ir-admonition-title\">{label}</p>\n <div className=\"ir-admonition-body\">{children}</div>\n </div>\n );\n};\n"],"mappings":";;;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;AAuCI;AAlCJ,MAAM,SAAiC;AAAA,EACrC,MAAM;AAAA,EACN,KAAK;AAAA,EACL,WAAW;AAAA,EACX,SAAS;AAAA,EACT,SAAS;AACX;AAeO,MAAM,aAAa,CAAC;AAAA,EACzB,OAAO;AAAA,EACP;AAAA,EACA;AAAA,EACA,GAAG;AACL,MAIuE;AACrE,QAAM,OAAO,OAAO,IAAI,EAAE,YAAY;AACtC,QAAM,QAAQ,SAAS,OAAO,IAAI,KAAK,OAAO;AAC9C,SACE;AAAA,IAAC;AAAA;AAAA,MACC,WAAW,+BAA+B,IAAI;AAAA,MAC9C,MAAK;AAAA,MACL,mBAAiB;AAAA,MAChB,GAAG;AAAA,MAEJ;AAAA,oDAAC,OAAE,WAAU,uBAAuB,iBAAM;AAAA,QAC1C,4CAAC,SAAI,WAAU,sBAAsB,UAAS;AAAA;AAAA;AAAA,EAChD;AAEJ;","names":[]}
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
import { ReactNode } from 'react';
|
|
2
|
+
|
|
3
|
+
/** The GitHub admonition kinds the transpiler's `> [!TYPE]` plugin emits (R3-152). */
|
|
4
|
+
type AdmonitionType = 'note' | 'tip' | 'important' | 'warning' | 'caution';
|
|
5
|
+
/**
|
|
6
|
+
* Default MDX `Admonition` component — the render target for the GitHub-style
|
|
7
|
+
* `> [!NOTE]` blockquote-alert syntax (the transpiler remark plugin, R3-152,
|
|
8
|
+
* compiles that syntax to `<Admonition type="note">…</Admonition>`).
|
|
9
|
+
*
|
|
10
|
+
* It is registered in {@link DEFAULT_MDX_COMPONENTS} so an admonition renders
|
|
11
|
+
* even in a plain-markdown repo that never calls `boot({ mdxComponents })` — the
|
|
12
|
+
* MDX missing-reference guard never fires (MARKDOWN_SYNTAX_SPEC §11.2 phantom
|
|
13
|
+
* defaults). The markup is semantic and accessible; **styling is intentionally
|
|
14
|
+
* minimal** — an app supplies CSS targeting the `ir-admonition*` classes, or
|
|
15
|
+
* overrides this component via `boot({ mdxComponents: { Admonition } })`
|
|
16
|
+
* (MARKDOWN_SYNTAX_SPEC §12.3).
|
|
17
|
+
*/
|
|
18
|
+
declare const Admonition: ({ type, title, children, ...rest }: {
|
|
19
|
+
type?: AdmonitionType | string;
|
|
20
|
+
title?: ReactNode;
|
|
21
|
+
children?: ReactNode;
|
|
22
|
+
} & Omit<React.HTMLAttributes<HTMLDivElement>, "title">) => ReactNode;
|
|
23
|
+
|
|
24
|
+
export { Admonition, type AdmonitionType };
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
import { ReactNode } from 'react';
|
|
2
|
+
|
|
3
|
+
/** The GitHub admonition kinds the transpiler's `> [!TYPE]` plugin emits (R3-152). */
|
|
4
|
+
type AdmonitionType = 'note' | 'tip' | 'important' | 'warning' | 'caution';
|
|
5
|
+
/**
|
|
6
|
+
* Default MDX `Admonition` component — the render target for the GitHub-style
|
|
7
|
+
* `> [!NOTE]` blockquote-alert syntax (the transpiler remark plugin, R3-152,
|
|
8
|
+
* compiles that syntax to `<Admonition type="note">…</Admonition>`).
|
|
9
|
+
*
|
|
10
|
+
* It is registered in {@link DEFAULT_MDX_COMPONENTS} so an admonition renders
|
|
11
|
+
* even in a plain-markdown repo that never calls `boot({ mdxComponents })` — the
|
|
12
|
+
* MDX missing-reference guard never fires (MARKDOWN_SYNTAX_SPEC §11.2 phantom
|
|
13
|
+
* defaults). The markup is semantic and accessible; **styling is intentionally
|
|
14
|
+
* minimal** — an app supplies CSS targeting the `ir-admonition*` classes, or
|
|
15
|
+
* overrides this component via `boot({ mdxComponents: { Admonition } })`
|
|
16
|
+
* (MARKDOWN_SYNTAX_SPEC §12.3).
|
|
17
|
+
*/
|
|
18
|
+
declare const Admonition: ({ type, title, children, ...rest }: {
|
|
19
|
+
type?: AdmonitionType | string;
|
|
20
|
+
title?: ReactNode;
|
|
21
|
+
children?: ReactNode;
|
|
22
|
+
} & Omit<React.HTMLAttributes<HTMLDivElement>, "title">) => ReactNode;
|
|
23
|
+
|
|
24
|
+
export { Admonition, type AdmonitionType };
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
import { jsx, jsxs } from "react/jsx-runtime";
|
|
2
|
+
const TITLES = {
|
|
3
|
+
note: "Note",
|
|
4
|
+
tip: "Tip",
|
|
5
|
+
important: "Important",
|
|
6
|
+
warning: "Warning",
|
|
7
|
+
caution: "Caution"
|
|
8
|
+
};
|
|
9
|
+
const Admonition = ({
|
|
10
|
+
type = "note",
|
|
11
|
+
title,
|
|
12
|
+
children,
|
|
13
|
+
...rest
|
|
14
|
+
}) => {
|
|
15
|
+
const kind = String(type).toLowerCase();
|
|
16
|
+
const label = title ?? TITLES[kind] ?? TITLES.note;
|
|
17
|
+
return /* @__PURE__ */ jsxs(
|
|
18
|
+
"div",
|
|
19
|
+
{
|
|
20
|
+
className: `ir-admonition ir-admonition-${kind}`,
|
|
21
|
+
role: "note",
|
|
22
|
+
"data-admonition": kind,
|
|
23
|
+
...rest,
|
|
24
|
+
children: [
|
|
25
|
+
/* @__PURE__ */ jsx("p", { className: "ir-admonition-title", children: label }),
|
|
26
|
+
/* @__PURE__ */ jsx("div", { className: "ir-admonition-body", children })
|
|
27
|
+
]
|
|
28
|
+
}
|
|
29
|
+
);
|
|
30
|
+
};
|
|
31
|
+
export {
|
|
32
|
+
Admonition
|
|
33
|
+
};
|
|
34
|
+
//# sourceMappingURL=Admonition.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../../src/components/Admonition.tsx"],"sourcesContent":["import { ReactNode } from 'react';\n\n/** The GitHub admonition kinds the transpiler's `> [!TYPE]` plugin emits (R3-152). */\nexport type AdmonitionType = 'note' | 'tip' | 'important' | 'warning' | 'caution';\n\nconst TITLES: Record<string, string> = {\n note: 'Note',\n tip: 'Tip',\n important: 'Important',\n warning: 'Warning',\n caution: 'Caution',\n};\n\n/**\n * Default MDX `Admonition` component — the render target for the GitHub-style\n * `> [!NOTE]` blockquote-alert syntax (the transpiler remark plugin, R3-152,\n * compiles that syntax to `<Admonition type=\"note\">…</Admonition>`).\n *\n * It is registered in {@link DEFAULT_MDX_COMPONENTS} so an admonition renders\n * even in a plain-markdown repo that never calls `boot({ mdxComponents })` — the\n * MDX missing-reference guard never fires (MARKDOWN_SYNTAX_SPEC §11.2 phantom\n * defaults). The markup is semantic and accessible; **styling is intentionally\n * minimal** — an app supplies CSS targeting the `ir-admonition*` classes, or\n * overrides this component via `boot({ mdxComponents: { Admonition } })`\n * (MARKDOWN_SYNTAX_SPEC §12.3).\n */\nexport const Admonition = ({\n type = 'note',\n title,\n children,\n ...rest\n}: {\n type?: AdmonitionType | string;\n title?: ReactNode;\n children?: ReactNode;\n} & Omit<React.HTMLAttributes<HTMLDivElement>, 'title'>): ReactNode => {\n const kind = String(type).toLowerCase();\n const label = title ?? TITLES[kind] ?? TITLES.note;\n return (\n <div\n className={`ir-admonition ir-admonition-${kind}`}\n role=\"note\"\n data-admonition={kind}\n {...rest}\n >\n <p className=\"ir-admonition-title\">{label}</p>\n <div className=\"ir-admonition-body\">{children}</div>\n </div>\n );\n};\n"],"mappings":"AAuCI,SAME,KANF;AAlCJ,MAAM,SAAiC;AAAA,EACrC,MAAM;AAAA,EACN,KAAK;AAAA,EACL,WAAW;AAAA,EACX,SAAS;AAAA,EACT,SAAS;AACX;AAeO,MAAM,aAAa,CAAC;AAAA,EACzB,OAAO;AAAA,EACP;AAAA,EACA;AAAA,EACA,GAAG;AACL,MAIuE;AACrE,QAAM,OAAO,OAAO,IAAI,EAAE,YAAY;AACtC,QAAM,QAAQ,SAAS,OAAO,IAAI,KAAK,OAAO;AAC9C,SACE;AAAA,IAAC;AAAA;AAAA,MACC,WAAW,+BAA+B,IAAI;AAAA,MAC9C,MAAK;AAAA,MACL,mBAAiB;AAAA,MAChB,GAAG;AAAA,MAEJ;AAAA,4BAAC,OAAE,WAAU,uBAAuB,iBAAM;AAAA,QAC1C,oBAAC,SAAI,WAAU,sBAAsB,UAAS;AAAA;AAAA;AAAA,EAChD;AAEJ;","names":[]}
|
|
@@ -0,0 +1,64 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __defProp = Object.defineProperty;
|
|
3
|
+
var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
|
|
4
|
+
var __getOwnPropNames = Object.getOwnPropertyNames;
|
|
5
|
+
var __hasOwnProp = Object.prototype.hasOwnProperty;
|
|
6
|
+
var __export = (target, all) => {
|
|
7
|
+
for (var name in all)
|
|
8
|
+
__defProp(target, name, { get: all[name], enumerable: true });
|
|
9
|
+
};
|
|
10
|
+
var __copyProps = (to, from, except, desc) => {
|
|
11
|
+
if (from && typeof from === "object" || typeof from === "function") {
|
|
12
|
+
for (let key of __getOwnPropNames(from))
|
|
13
|
+
if (!__hasOwnProp.call(to, key) && key !== except)
|
|
14
|
+
__defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
|
|
15
|
+
}
|
|
16
|
+
return to;
|
|
17
|
+
};
|
|
18
|
+
var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
|
|
19
|
+
var Link_exports = {};
|
|
20
|
+
__export(Link_exports, {
|
|
21
|
+
InternalLink: () => InternalLink,
|
|
22
|
+
Link: () => Link
|
|
23
|
+
});
|
|
24
|
+
module.exports = __toCommonJS(Link_exports);
|
|
25
|
+
var import_jsx_runtime = require("react/jsx-runtime");
|
|
26
|
+
var import_react = require("react");
|
|
27
|
+
var import_routing = require("../routing");
|
|
28
|
+
var import_TinkerableContext = require("../TinkerableContext");
|
|
29
|
+
var import_urlUtils = require("../urlUtils");
|
|
30
|
+
const InternalLink = ({
|
|
31
|
+
href,
|
|
32
|
+
children,
|
|
33
|
+
...props
|
|
34
|
+
}) => {
|
|
35
|
+
const clickHandler = (0, import_react.useCallback)(
|
|
36
|
+
(e) => {
|
|
37
|
+
if (href) {
|
|
38
|
+
e.preventDefault();
|
|
39
|
+
(0, import_routing.navigate)(href);
|
|
40
|
+
}
|
|
41
|
+
},
|
|
42
|
+
[href]
|
|
43
|
+
);
|
|
44
|
+
return /* @__PURE__ */ (0, import_jsx_runtime.jsx)("a", { href, onClick: clickHandler, ...props, children });
|
|
45
|
+
};
|
|
46
|
+
const Link = ({
|
|
47
|
+
href,
|
|
48
|
+
children,
|
|
49
|
+
...properties
|
|
50
|
+
}) => {
|
|
51
|
+
const { outerHref, navigationState } = (0, import_react.use)(import_TinkerableContext.TinkerableContext);
|
|
52
|
+
if (href && (0, import_urlUtils.isInternalHref)(outerHref, href, navigationState)) {
|
|
53
|
+
const targetHref = (0, import_urlUtils.constructOuterUrl)(outerHref, href, navigationState);
|
|
54
|
+
return /* @__PURE__ */ (0, import_jsx_runtime.jsx)(InternalLink, { href: targetHref, ...properties, children });
|
|
55
|
+
} else {
|
|
56
|
+
return /* @__PURE__ */ (0, import_jsx_runtime.jsx)("a", { ...{ href, ...properties }, children });
|
|
57
|
+
}
|
|
58
|
+
};
|
|
59
|
+
// Annotate the CommonJS export names for ESM import in node:
|
|
60
|
+
0 && (module.exports = {
|
|
61
|
+
InternalLink,
|
|
62
|
+
Link
|
|
63
|
+
});
|
|
64
|
+
//# sourceMappingURL=Link.cjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../../src/components/Link.tsx"],"sourcesContent":["import { ReactNode, use, useCallback } from 'react';\nimport { navigate } from '../routing';\nimport { TinkerableContext } from '../TinkerableContext';\nimport { constructOuterUrl, isInternalHref } from '../urlUtils';\n\n/** An `<a>` that performs in-sandbox navigation on click (prevents the default\n * full-page load and routes via {@link navigate}). */\nexport const InternalLink = ({\n href,\n children,\n ...props\n}: React.DetailedHTMLProps<React.AnchorHTMLAttributes<HTMLAnchorElement>, HTMLAnchorElement>): ReactNode => {\n const clickHandler = useCallback(\n (e: any) => {\n if (href) {\n e.preventDefault();\n navigate(href);\n }\n },\n [href]\n );\n return (\n <a href={href} onClick={clickHandler} {...props}>\n {children}\n </a>\n );\n};\n\n/** A link that routes same-app hrefs through the sandbox router (as an\n * {@link InternalLink}) and renders external hrefs as a plain `<a>`. */\nexport const Link = ({\n href,\n children,\n ...properties\n}: React.DetailedHTMLProps<React.AnchorHTMLAttributes<HTMLAnchorElement>, HTMLAnchorElement>): ReactNode => {\n const { outerHref, navigationState } = use(TinkerableContext);\n if (href && isInternalHref(outerHref, href, navigationState)) {\n const targetHref = constructOuterUrl(outerHref, href, navigationState);\n return (\n <InternalLink href={targetHref} {...properties}>\n {children}\n </InternalLink>\n );\n } else {\n // create a regular link to external resource\n return <a {...{ href, ...properties }}>{children}</a>;\n }\n};\n"],"mappings":";;;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAsBI;AAtBJ,mBAA4C;AAC5C,qBAAyB;AACzB,+BAAkC;AAClC,sBAAkD;AAI3C,MAAM,eAAe,CAAC;AAAA,EAC3B;AAAA,EACA;AAAA,EACA,GAAG;AACL,MAA4G;AAC1G,QAAM,mBAAe;AAAA,IACnB,CAAC,MAAW;AACV,UAAI,MAAM;AACR,UAAE,eAAe;AACjB,qCAAS,IAAI;AAAA,MACf;AAAA,IACF;AAAA,IACA,CAAC,IAAI;AAAA,EACP;AACA,SACE,4CAAC,OAAE,MAAY,SAAS,cAAe,GAAG,OACvC,UACH;AAEJ;AAIO,MAAM,OAAO,CAAC;AAAA,EACnB;AAAA,EACA;AAAA,EACA,GAAG;AACL,MAA4G;AAC1G,QAAM,EAAE,WAAW,gBAAgB,QAAI,kBAAI,0CAAiB;AAC5D,MAAI,YAAQ,gCAAe,WAAW,MAAM,eAAe,GAAG;AAC5D,UAAM,iBAAa,mCAAkB,WAAW,MAAM,eAAe;AACrE,WACE,4CAAC,gBAAa,MAAM,YAAa,GAAG,YACjC,UACH;AAAA,EAEJ,OAAO;AAEL,WAAO,4CAAC,OAAG,GAAG,EAAE,MAAM,GAAG,WAAW,GAAI,UAAS;AAAA,EACnD;AACF;","names":[]}
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
import { ReactNode } from 'react';
|
|
2
|
+
|
|
3
|
+
/** An `<a>` that performs in-sandbox navigation on click (prevents the default
|
|
4
|
+
* full-page load and routes via {@link navigate}). */
|
|
5
|
+
declare const InternalLink: ({ href, children, ...props }: React.DetailedHTMLProps<React.AnchorHTMLAttributes<HTMLAnchorElement>, HTMLAnchorElement>) => ReactNode;
|
|
6
|
+
/** A link that routes same-app hrefs through the sandbox router (as an
|
|
7
|
+
* {@link InternalLink}) and renders external hrefs as a plain `<a>`. */
|
|
8
|
+
declare const Link: ({ href, children, ...properties }: React.DetailedHTMLProps<React.AnchorHTMLAttributes<HTMLAnchorElement>, HTMLAnchorElement>) => ReactNode;
|
|
9
|
+
|
|
10
|
+
export { InternalLink, Link };
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
import { ReactNode } from 'react';
|
|
2
|
+
|
|
3
|
+
/** An `<a>` that performs in-sandbox navigation on click (prevents the default
|
|
4
|
+
* full-page load and routes via {@link navigate}). */
|
|
5
|
+
declare const InternalLink: ({ href, children, ...props }: React.DetailedHTMLProps<React.AnchorHTMLAttributes<HTMLAnchorElement>, HTMLAnchorElement>) => ReactNode;
|
|
6
|
+
/** A link that routes same-app hrefs through the sandbox router (as an
|
|
7
|
+
* {@link InternalLink}) and renders external hrefs as a plain `<a>`. */
|
|
8
|
+
declare const Link: ({ href, children, ...properties }: React.DetailedHTMLProps<React.AnchorHTMLAttributes<HTMLAnchorElement>, HTMLAnchorElement>) => ReactNode;
|
|
9
|
+
|
|
10
|
+
export { InternalLink, Link };
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
import { jsx } from "react/jsx-runtime";
|
|
2
|
+
import { use, useCallback } from "react";
|
|
3
|
+
import { navigate } from "../routing";
|
|
4
|
+
import { TinkerableContext } from "../TinkerableContext";
|
|
5
|
+
import { constructOuterUrl, isInternalHref } from "../urlUtils";
|
|
6
|
+
const InternalLink = ({
|
|
7
|
+
href,
|
|
8
|
+
children,
|
|
9
|
+
...props
|
|
10
|
+
}) => {
|
|
11
|
+
const clickHandler = useCallback(
|
|
12
|
+
(e) => {
|
|
13
|
+
if (href) {
|
|
14
|
+
e.preventDefault();
|
|
15
|
+
navigate(href);
|
|
16
|
+
}
|
|
17
|
+
},
|
|
18
|
+
[href]
|
|
19
|
+
);
|
|
20
|
+
return /* @__PURE__ */ jsx("a", { href, onClick: clickHandler, ...props, children });
|
|
21
|
+
};
|
|
22
|
+
const Link = ({
|
|
23
|
+
href,
|
|
24
|
+
children,
|
|
25
|
+
...properties
|
|
26
|
+
}) => {
|
|
27
|
+
const { outerHref, navigationState } = use(TinkerableContext);
|
|
28
|
+
if (href && isInternalHref(outerHref, href, navigationState)) {
|
|
29
|
+
const targetHref = constructOuterUrl(outerHref, href, navigationState);
|
|
30
|
+
return /* @__PURE__ */ jsx(InternalLink, { href: targetHref, ...properties, children });
|
|
31
|
+
} else {
|
|
32
|
+
return /* @__PURE__ */ jsx("a", { ...{ href, ...properties }, children });
|
|
33
|
+
}
|
|
34
|
+
};
|
|
35
|
+
export {
|
|
36
|
+
InternalLink,
|
|
37
|
+
Link
|
|
38
|
+
};
|
|
39
|
+
//# sourceMappingURL=Link.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../../src/components/Link.tsx"],"sourcesContent":["import { ReactNode, use, useCallback } from 'react';\nimport { navigate } from '../routing';\nimport { TinkerableContext } from '../TinkerableContext';\nimport { constructOuterUrl, isInternalHref } from '../urlUtils';\n\n/** An `<a>` that performs in-sandbox navigation on click (prevents the default\n * full-page load and routes via {@link navigate}). */\nexport const InternalLink = ({\n href,\n children,\n ...props\n}: React.DetailedHTMLProps<React.AnchorHTMLAttributes<HTMLAnchorElement>, HTMLAnchorElement>): ReactNode => {\n const clickHandler = useCallback(\n (e: any) => {\n if (href) {\n e.preventDefault();\n navigate(href);\n }\n },\n [href]\n );\n return (\n <a href={href} onClick={clickHandler} {...props}>\n {children}\n </a>\n );\n};\n\n/** A link that routes same-app hrefs through the sandbox router (as an\n * {@link InternalLink}) and renders external hrefs as a plain `<a>`. */\nexport const Link = ({\n href,\n children,\n ...properties\n}: React.DetailedHTMLProps<React.AnchorHTMLAttributes<HTMLAnchorElement>, HTMLAnchorElement>): ReactNode => {\n const { outerHref, navigationState } = use(TinkerableContext);\n if (href && isInternalHref(outerHref, href, navigationState)) {\n const targetHref = constructOuterUrl(outerHref, href, navigationState);\n return (\n <InternalLink href={targetHref} {...properties}>\n {children}\n </InternalLink>\n );\n } else {\n // create a regular link to external resource\n return <a {...{ href, ...properties }}>{children}</a>;\n }\n};\n"],"mappings":"AAsBI;AAtBJ,SAAoB,KAAK,mBAAmB;AAC5C,SAAS,gBAAgB;AACzB,SAAS,yBAAyB;AAClC,SAAS,mBAAmB,sBAAsB;AAI3C,MAAM,eAAe,CAAC;AAAA,EAC3B;AAAA,EACA;AAAA,EACA,GAAG;AACL,MAA4G;AAC1G,QAAM,eAAe;AAAA,IACnB,CAAC,MAAW;AACV,UAAI,MAAM;AACR,UAAE,eAAe;AACjB,iBAAS,IAAI;AAAA,MACf;AAAA,IACF;AAAA,IACA,CAAC,IAAI;AAAA,EACP;AACA,SACE,oBAAC,OAAE,MAAY,SAAS,cAAe,GAAG,OACvC,UACH;AAEJ;AAIO,MAAM,OAAO,CAAC;AAAA,EACnB;AAAA,EACA;AAAA,EACA,GAAG;AACL,MAA4G;AAC1G,QAAM,EAAE,WAAW,gBAAgB,IAAI,IAAI,iBAAiB;AAC5D,MAAI,QAAQ,eAAe,WAAW,MAAM,eAAe,GAAG;AAC5D,UAAM,aAAa,kBAAkB,WAAW,MAAM,eAAe;AACrE,WACE,oBAAC,gBAAa,MAAM,YAAa,GAAG,YACjC,UACH;AAAA,EAEJ,OAAO;AAEL,WAAO,oBAAC,OAAG,GAAG,EAAE,MAAM,GAAG,WAAW,GAAI,UAAS;AAAA,EACnD;AACF;","names":[]}
|