docs: generate complete UI component reference
This commit is contained in:
@@ -11,6 +11,24 @@ const pages = join(root, "app", "pages");
|
|||||||
const packagePages = join(pages, "packages");
|
const packagePages = join(pages, "packages");
|
||||||
mkdirSync(packagePages, { recursive: true });
|
mkdirSync(packagePages, { recursive: true });
|
||||||
|
|
||||||
|
interface UiComponentReference {
|
||||||
|
count: number;
|
||||||
|
components: Array<{
|
||||||
|
name: string;
|
||||||
|
mount: string;
|
||||||
|
category: string;
|
||||||
|
purpose: string;
|
||||||
|
props: Array<{ name: string; type: string; required: boolean; default: string | null }>;
|
||||||
|
slots: string[];
|
||||||
|
events: string[];
|
||||||
|
}>;
|
||||||
|
}
|
||||||
|
|
||||||
|
const uiReferencePath = join(root, "node_modules", "@wrnexus", "ui", "component-reference.json");
|
||||||
|
const uiReference: UiComponentReference | undefined = existsSync(uiReferencePath)
|
||||||
|
? JSON.parse(readFileSync(uiReferencePath, "utf8"))
|
||||||
|
: undefined;
|
||||||
|
|
||||||
const catalog = [
|
const catalog = [
|
||||||
["ai", "AI", "Server-side Anthropic client with generation and streaming."],
|
["ai", "AI", "Server-side Anthropic client with generation and streaming."],
|
||||||
["authz", "Security", "Role, permission, policy, and authorization guards."],
|
["authz", "Security", "Role, permission, policy, and authorization guards."],
|
||||||
@@ -299,11 +317,30 @@ for (const [name, category, summary] of catalog) {
|
|||||||
.replace(/\bWrNexus\b/g, "WRNexusJS");
|
.replace(/\bWrNexus\b/g, "WRNexusJS");
|
||||||
const types = readFileSync(typesPath, "utf8");
|
const types = readFileSync(typesPath, "utf8");
|
||||||
const guide = markdown(readme);
|
const guide = markdown(readme);
|
||||||
|
const componentReference =
|
||||||
|
name === "ui" && uiReference
|
||||||
|
? `<section id="components" class="prose ui-component-reference"><h2>All ${uiReference.count} UI components and props</h2><p>This reference is generated from the exact installed <code>.wrn</code> sources. Required props have no default; optional props show their default value.</p>${[
|
||||||
|
...new Set(uiReference.components.map((component) => component.category)),
|
||||||
|
]
|
||||||
|
.sort()
|
||||||
|
.map(
|
||||||
|
(componentCategory) =>
|
||||||
|
`<h3>${escape(componentCategory[0]!.toUpperCase() + componentCategory.slice(1))}</h3><div class="table-wrap"><table><thead><tr><th>Component</th><th>Props</th><th>Slots</th><th>Events</th></tr></thead><tbody>${uiReference.components
|
||||||
|
.filter((component) => component.category === componentCategory)
|
||||||
|
.map(
|
||||||
|
(component) =>
|
||||||
|
`<tr><td><strong>${escape(component.name)}</strong><br><code>data-component="${escape(component.mount)}"</code><br><small>${escape(component.purpose)}</small></td><td>${component.props.length ? component.props.map((prop) => `<code>${escape(prop.name)}: ${escape(prop.type)}${prop.required ? " (required)" : ` = ${escape(prop.default ?? "")}`}</code>`).join("<br>") : "None"}</td><td>${component.slots.length ? component.slots.map((slot) => `<code>${escape(slot)}</code>`).join("<br>") : "None"}</td><td>${component.events.length ? component.events.map((event) => `<code>${escape(event)}</code>`).join("<br>") : "None"}</td></tr>`,
|
||||||
|
)
|
||||||
|
.join("")}</tbody></table></div>`,
|
||||||
|
)
|
||||||
|
.join("")}</section>`
|
||||||
|
: "";
|
||||||
const toc = [
|
const toc = [
|
||||||
{ id: "guide", title: "Guide", level: 2 },
|
{ id: "guide", title: "Guide", level: 2 },
|
||||||
...guide.headings,
|
...guide.headings,
|
||||||
{ id: "api", title: "Complete API", level: 2 },
|
{ id: "api", title: "Complete API", level: 2 },
|
||||||
{ id: "examples", title: "Examples", level: 2 },
|
{ id: "examples", title: "Examples", level: 2 },
|
||||||
|
...(componentReference ? [{ id: "components", title: "All UI components", level: 2 }] : []),
|
||||||
]
|
]
|
||||||
.map(
|
.map(
|
||||||
(heading) =>
|
(heading) =>
|
||||||
@@ -312,7 +349,7 @@ for (const [name, category, summary] of catalog) {
|
|||||||
.join("");
|
.join("");
|
||||||
const content = `<main class="page package-page">
|
const content = `<main class="page package-page">
|
||||||
<aside class="sidebar"><a href="/packages">← All packages</a><span class="category">${category}</span><h2>@wrnexus/${name}</h2><p>${summary}</p><span class="status status-beta">Private preview · ${frameworkVersion}</span><nav><a href="#access">Access</a><a href="#guide">Guide</a><a href="#api">Complete API</a></nav></aside>
|
<aside class="sidebar"><a href="/packages">← All packages</a><span class="category">${category}</span><h2>@wrnexus/${name}</h2><p>${summary}</p><span class="status status-beta">Private preview · ${frameworkVersion}</span><nav><a href="#access">Access</a><a href="#guide">Guide</a><a href="#api">Complete API</a></nav></aside>
|
||||||
<article id="main" class="documentation"><section class="doc-intro"><span class="eyebrow">${category} · Preview</span><h1>@wrnexus/${name}</h1><p>${summary}</p><section id="access" class="access-callout"><h2>Private registry access required</h2><p>This package is not available from the public npm registry. After WorkRoot approves access and supplies private registry instructions, install the release-aligned package:</p><pre><code>bun add @wrnexus/${name}@${frameworkVersion}</code><button type="button" class="copy-button" aria-label="Copy installation command">Copy</button></pre><p><a href="/access">Request preview access</a>. Never put registry tokens in source control.</p></section></section><section id="guide" class="prose">${guide.html}</section><section id="api" class="prose api"><h2>Complete TypeScript API</h2><p>This declaration comes from the exact installed package and lists its exported functions, classes, interfaces, and types.</p><pre data-language="typescript"><code>${escape(types)}</code></pre></section><section id="examples" class="prose examples"><h2>Examples</h2><p>Examples are taken from this package's installed documentation and must be evaluated with its requirements and stability notes.</p><div class="example-grid">${examplesFrom(readme, name)}</div></section></article>
|
<article id="main" class="documentation"><section class="doc-intro"><span class="eyebrow">${category} · Preview</span><h1>@wrnexus/${name}</h1><p>${summary}</p><section id="access" class="access-callout"><h2>Private registry access required</h2><p>This package is not available from the public npm registry. After WorkRoot approves access and supplies private registry instructions, install the release-aligned package:</p><pre><code>bun add @wrnexus/${name}@${frameworkVersion}</code><button type="button" class="copy-button" aria-label="Copy installation command">Copy</button></pre><p><a href="/access">Request preview access</a>. Never put registry tokens in source control.</p></section></section><section id="guide" class="prose">${guide.html}</section><section id="api" class="prose api"><h2>Complete TypeScript API</h2><p>This declaration comes from the exact installed package and lists its exported functions, classes, interfaces, and types.</p><pre data-language="typescript"><code>${escape(types)}</code></pre></section><section id="examples" class="prose examples"><h2>Examples</h2><p>Examples are taken from this package's installed documentation and must be evaluated with its requirements and stability notes.</p><div class="example-grid">${examplesFrom(readme, name)}</div></section>${componentReference}</article>
|
||||||
<aside class="on-this-page"><h2>On this page</h2><nav>${toc}</nav></aside>
|
<aside class="on-this-page"><h2>On this page</h2><nav>${toc}</nav></aside>
|
||||||
</main>`;
|
</main>`;
|
||||||
writeFileSync(join(packagePages, `${name}.wrn`), shell(`@wrnexus/${name}`, summary, content));
|
writeFileSync(join(packagePages, `${name}.wrn`), shell(`@wrnexus/${name}`, summary, content));
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
import { mkdirSync, readFileSync, writeFileSync } from "node:fs";
|
import { existsSync, mkdirSync, readFileSync, writeFileSync } from "node:fs";
|
||||||
import { join, resolve } from "node:path";
|
import { join, resolve } from "node:path";
|
||||||
import { format } from "prettier";
|
import { format } from "prettier";
|
||||||
|
|
||||||
@@ -15,6 +15,28 @@ const packageNames = [...Object.keys(pkg.dependencies), ...Object.keys(pkg.devDe
|
|||||||
.filter((name, index, all) => all.indexOf(name) === index)
|
.filter((name, index, all) => all.indexOf(name) === index)
|
||||||
.sort();
|
.sort();
|
||||||
const packageCount = packageNames.length;
|
const packageCount = packageNames.length;
|
||||||
|
const uiReferencePath = join(root, "node_modules", "@wrnexus", "ui", "component-reference.json");
|
||||||
|
const uiReference = existsSync(uiReferencePath)
|
||||||
|
? (JSON.parse(readFileSync(uiReferencePath, "utf8")) as {
|
||||||
|
count: number;
|
||||||
|
components: Array<{
|
||||||
|
name: string;
|
||||||
|
mount: string;
|
||||||
|
category: string;
|
||||||
|
props: Array<{ name: string; type: string; required: boolean; default: string | null }>;
|
||||||
|
slots: string[];
|
||||||
|
events: string[];
|
||||||
|
}>;
|
||||||
|
})
|
||||||
|
: undefined;
|
||||||
|
const uiReferenceText = uiReference
|
||||||
|
? uiReference.components
|
||||||
|
.map(
|
||||||
|
(component) =>
|
||||||
|
`### ${component.name}\nMount: data-component="${component.mount}"\nCategory: ${component.category}\nProps: ${component.props.length ? component.props.map((prop) => `${prop.name}: ${prop.type}${prop.required ? " (required)" : ` = ${prop.default}`}`).join(", ") : "none"}\nSlots: ${component.slots.join(", ") || "none"}\nEvents: ${component.events.join(", ") || "none"}`,
|
||||||
|
)
|
||||||
|
.join("\n\n")
|
||||||
|
: "UI component reference unavailable; install the release-aligned @wrnexus/ui package.";
|
||||||
|
|
||||||
async function writeFormatted(path: string, source: string) {
|
async function writeFormatted(path: string, source: string) {
|
||||||
writeFileSync(path, await format(source, { filepath: path }));
|
writeFileSync(path, await format(source, { filepath: path }));
|
||||||
@@ -487,7 +509,7 @@ await writeFormatted(
|
|||||||
);
|
);
|
||||||
writeFileSync(
|
writeFileSync(
|
||||||
join(pub, "llms-full.txt"),
|
join(pub, "llms-full.txt"),
|
||||||
`# WRNexusJS ${version} comprehensive documentation index\n\nStatus: Private Developer Preview. Runtime: Bun. UI language: .wrn.\nThis is the documentation application, not the framework monorepo.\n\n${urls.map((x) => `- https://wrnexusjs.dev${x}`).join("\n")}\n\nFor exact APIs, use installed package README files followed by exported declarations.\n`,
|
`# WRNexusJS ${version} comprehensive documentation index\n\nStatus: Private Developer Preview. Runtime: Bun. UI language: .wrn.\nThis is the documentation application, not the framework monorepo.\n\n${urls.map((x) => `- https://wrnexusjs.dev${x}`).join("\n")}\n\nFor exact APIs, use installed package README files followed by exported declarations.\n\n# Complete @wrnexus/ui component reference\n\n${uiReferenceText}\n`,
|
||||||
);
|
);
|
||||||
|
|
||||||
const packageMarker = "# Installed package documentation";
|
const packageMarker = "# Installed package documentation";
|
||||||
@@ -511,7 +533,7 @@ const installedPackageDocs = packageNames
|
|||||||
.join("\n\n---\n\n");
|
.join("\n\n---\n\n");
|
||||||
writeFileSync(
|
writeFileSync(
|
||||||
join(pub, "llms.txt"),
|
join(pub, "llms.txt"),
|
||||||
`${frameworkGuide}\n\n${packageMarker}\n\nThe following README files and declarations come from the installed private ${version} release.\n\n${installedPackageDocs}\n`,
|
`${frameworkGuide}\n\n# UI component catalog\n\nThe installed @wrnexus/ui release contains ${uiReference?.count ?? 0} documented components. Every mount name, prop type, required/default status, slot, and event is included below and in llms-full.txt.\n\n${uiReferenceText}\n\n${packageMarker}\n\nThe following README files and declarations come from the installed private ${version} release.\n\n${installedPackageDocs}\n`,
|
||||||
);
|
);
|
||||||
|
|
||||||
const auditDocs: Record<string, string> = {
|
const auditDocs: Record<string, string> = {
|
||||||
|
|||||||
Reference in New Issue
Block a user