@pagesmith/core 0.4.0 → 0.4.2
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/README.md +19 -0
- package/REFERENCE.md +160 -94
- package/dist/{content-config-DJXUOcNG.d.mts → content-config-Bu2HH0Yx.d.mts} +2 -2
- package/dist/{content-config-DJXUOcNG.d.mts.map → content-config-Bu2HH0Yx.d.mts.map} +1 -1
- package/dist/{content-layer-B5enqWeJ.mjs → content-layer-CJRrNpZ_.mjs} +71 -10
- package/dist/content-layer-CJRrNpZ_.mjs.map +1 -0
- package/dist/{content-layer-CpHYUYNN.d.mts → content-layer-Ckt08g2i.d.mts} +4 -3
- package/dist/content-layer-Ckt08g2i.d.mts.map +1 -0
- package/dist/create/index.d.mts.map +1 -1
- package/dist/create/index.mjs +5 -2
- package/dist/create/index.mjs.map +1 -1
- package/dist/css/index.mjs +1 -1
- package/dist/css-CO3CBqxx.mjs +24 -0
- package/dist/css-CO3CBqxx.mjs.map +1 -0
- package/dist/heading-D4X2L4vd.d.mts +12 -0
- package/dist/heading-D4X2L4vd.d.mts.map +1 -0
- package/dist/{index-C0QFHYwb.d.mts → index-B4YZRIzb.d.mts} +1 -1
- package/dist/{index-C0QFHYwb.d.mts.map → index-B4YZRIzb.d.mts.map} +1 -1
- package/dist/{index-DCznbvaV.d.mts → index-CryArLlX.d.mts} +1 -1
- package/dist/{index-DCznbvaV.d.mts.map → index-CryArLlX.d.mts.map} +1 -1
- package/dist/{index-CJkBs8YQ.d.mts → index-D44syBt-.d.mts} +3 -2
- package/dist/index-D44syBt-.d.mts.map +1 -0
- package/dist/index.d.mts +7 -6
- package/dist/index.d.mts.map +1 -1
- package/dist/index.mjs +4 -4
- package/dist/loaders/index.d.mts +1 -1
- package/dist/loaders/index.mjs +1 -1
- package/dist/{loaders-Cf-BXf2L.mjs → loaders-DnyWfANR.mjs} +3 -3
- package/dist/loaders-DnyWfANR.mjs.map +1 -0
- package/dist/markdown/index.d.mts +2 -2
- package/dist/markdown/index.mjs +1 -1
- package/dist/{markdown-BmDJgYeB.mjs → markdown-DMHd400a.mjs} +7 -2
- package/dist/{markdown-BmDJgYeB.mjs.map → markdown-DMHd400a.mjs.map} +1 -1
- package/dist/{heading-Dhvzlay-.d.mts → markdown-config-CDvh5aJ-.d.mts} +2 -10
- package/dist/markdown-config-CDvh5aJ-.d.mts.map +1 -0
- package/dist/mcp/index.d.mts.map +1 -1
- package/dist/mcp/index.mjs +1 -1
- package/dist/mcp/server.d.mts +1 -1
- package/dist/mcp/server.d.mts.map +1 -1
- package/dist/mcp/server.mjs +1 -1
- package/dist/runtime/index.d.mts.map +1 -1
- package/dist/runtime/index.mjs +4 -9
- package/dist/runtime/index.mjs.map +1 -1
- package/dist/schemas/index.d.mts +4 -3
- package/dist/{server-D3DHoh5f.mjs → server-BZA_iSen.mjs} +2 -1
- package/dist/server-BZA_iSen.mjs.map +1 -0
- package/dist/ssg-utils/index.d.mts +3 -13
- package/dist/ssg-utils/index.d.mts.map +1 -1
- package/dist/ssg-utils/index.mjs +2 -1
- package/dist/ssg-utils/index.mjs.map +1 -1
- package/dist/vite/index.d.mts +2 -2
- package/dist/vite/index.d.mts.map +1 -1
- package/dist/vite/index.mjs +5 -5
- package/dist/vite/index.mjs.map +1 -1
- package/docs/agents/AGENTS.md.template +24 -4
- package/docs/agents/changelog-notes.md +1 -1
- package/docs/agents/errors.md +61 -7
- package/docs/agents/migration.md +7 -7
- package/docs/agents/recipes.md +26 -2
- package/docs/agents/usage.md +66 -5
- package/docs/llms-full.txt +73 -15
- package/docs/llms.txt +46 -7
- package/package.json +2 -27
- package/dist/content-layer-B5enqWeJ.mjs.map +0 -1
- package/dist/content-layer-CpHYUYNN.d.mts.map +0 -1
- package/dist/css-BneO430t.mjs +0 -20
- package/dist/css-BneO430t.mjs.map +0 -1
- package/dist/heading-Dhvzlay-.d.mts.map +0 -1
- package/dist/index-CJkBs8YQ.d.mts.map +0 -1
- package/dist/loaders-Cf-BXf2L.mjs.map +0 -1
- package/dist/server-D3DHoh5f.mjs.map +0 -1
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"content-layer-CJRrNpZ_.mjs","names":["getTextContent","coreConvert","pathResolve","fsWatch"],"sources":["../src/convert.ts","../src/utils/read-time.ts","../src/entry.ts","../src/plugins/index.ts","../src/utils/glob.ts","../src/utils/slug.ts","../src/validation/schema-validator.ts","../src/validation/code-block-validator.ts","../src/validation/heading-validator.ts","../src/validation/link-validator.ts","../src/validation/runner.ts","../src/store.ts","../src/content-layer.ts"],"sourcesContent":["import { processMarkdown } from './markdown'\nimport type { Heading } from './schemas/heading'\nimport type { MarkdownConfig } from './schemas/markdown-config'\n\nexport type ConvertOptions = {\n markdown?: MarkdownConfig\n}\n\nexport type ConvertResult = {\n html: string\n toc: Heading[]\n frontmatter: Record<string, unknown>\n}\n\nexport async function convert(input: string, options: ConvertOptions = {}): Promise<ConvertResult> {\n const result = await processMarkdown(input, options.markdown || {})\n return { html: result.html, toc: result.headings, frontmatter: result.frontmatter }\n}\n","/**\n * Read time estimation.\n *\n * Computes estimated reading time from markdown source (~200 words per minute).\n */\n\n/** Compute read time in minutes from raw markdown. */\nexport function computeReadTime(rawMarkdown: string): number {\n const plainText = rawMarkdown\n .replace(/```[\\s\\S]*?```/g, ' ')\n .replace(/^( {4}|\\t).+$/gm, ' ')\n .replace(/^---[\\s\\S]*?---/m, ' ')\n .replace(/<[^>]+>/g, ' ')\n .replace(/!?\\[([^\\]]*)\\]\\([^)]*\\)/g, '$1')\n .replace(/[#*_~`>]/g, ' ')\n .replace(/\\s+/g, ' ')\n .trim()\n const wordCount = plainText.split(' ').filter(Boolean).length\n return Math.max(1, Math.ceil(wordCount / 200))\n}\n","/**\n * ContentEntry — represents a single content entry in a collection.\n *\n * Supports lazy rendering: data is available immediately after loading,\n * but HTML rendering is deferred until render() is called.\n */\n\nimport type { Heading } from './schemas/heading'\nimport type { MarkdownConfig } from './schemas/markdown-config'\nimport { processMarkdown } from './markdown'\nimport { computeReadTime } from './utils/read-time'\n\nexport type RenderedContent = {\n /** Processed HTML */\n html: string\n /** Extracted headings for TOC */\n headings: Heading[]\n /** Estimated read time in minutes */\n readTime: number\n}\n\nexport class ContentEntry<T = Record<string, any>> {\n /** URL-friendly identifier */\n readonly slug: string\n /** Collection this entry belongs to */\n readonly collection: string\n /** Absolute path to source file */\n readonly filePath: string\n /** Validated data (frontmatter or parsed data) */\n readonly data: T\n /** Raw body content (markdown only) */\n readonly rawContent?: string\n\n /** Cached render result */\n private _rendered?: RenderedContent\n /** Markdown config for rendering */\n private _markdownConfig: MarkdownConfig\n\n constructor(\n slug: string,\n collection: string,\n filePath: string,\n data: T,\n rawContent: string | undefined,\n markdownConfig: MarkdownConfig,\n ) {\n this.slug = slug\n this.collection = collection\n this.filePath = filePath\n this.data = data\n this.rawContent = rawContent\n this._markdownConfig = markdownConfig\n }\n\n /** Render the entry content to HTML. Cached after first call. */\n async render(options?: { force?: boolean }): Promise<RenderedContent> {\n if (this._rendered && !options?.force) {\n return this._rendered\n }\n\n if (!this.rawContent) {\n // Non-markdown entries have no renderable content\n this._rendered = { html: '', headings: [], readTime: 0 }\n return this._rendered\n }\n\n const result = await processMarkdown(this.rawContent, this._markdownConfig, {\n content: this.rawContent,\n frontmatter: this.data as Record<string, unknown>,\n })\n const readTime = computeReadTime(this.rawContent)\n\n this._rendered = {\n html: result.html,\n headings: result.headings,\n readTime,\n }\n\n return this._rendered\n }\n\n /** Clear cached render result. */\n clearRenderCache(): void {\n this._rendered = undefined\n }\n}\n","/**\n * Plugin registration and execution.\n */\n\nimport type { ContentPlugin } from '../schemas/content-config'\n\n/** Collect all remark plugins from content plugins. */\nexport function collectRemarkPlugins(plugins: ContentPlugin[]): any[] {\n return plugins.filter((p) => p.remarkPlugin).map((p) => p.remarkPlugin!)\n}\n\n/** Collect all rehype plugins from content plugins. */\nexport function collectRehypePlugins(plugins: ContentPlugin[]): any[] {\n return plugins.filter((p) => p.rehypePlugin).map((p) => p.rehypePlugin!)\n}\n\n/** Run all plugin validators against an entry. */\nexport function runPluginValidators(\n plugins: ContentPlugin[],\n entry: { data: Record<string, any>; content?: string },\n): string[] {\n const issues: string[] = []\n for (const plugin of plugins) {\n if (plugin.validate) {\n try {\n issues.push(...plugin.validate(entry))\n } catch (err) {\n issues.push(\n `[${plugin.name}] Validator threw: ${err instanceof Error ? err.message : String(err)}`,\n )\n }\n }\n }\n return issues\n}\n\nexport type { ContentPlugin } from '../schemas/content-config'\n","/**\n * File discovery via glob patterns.\n */\n\nimport fg from 'fast-glob'\nimport { resolve } from 'path'\n\nexport interface DiscoverOptions {\n /** Directory to search in (absolute path) */\n directory: string\n /** Glob patterns to include */\n include: string[]\n /** Glob patterns to exclude */\n exclude?: string[]\n}\n\n/** Discover files matching glob patterns in a directory. */\nexport async function discoverFiles(options: DiscoverOptions): Promise<string[]> {\n const { directory, include, exclude = [] } = options\n\n const files = await fg(include, {\n cwd: directory,\n absolute: true,\n ignore: ['**/node_modules/**', '**/dist/**', '**/dev/**', ...exclude],\n })\n\n return files.map((p) => resolve(p))\n}\n","/**\n * Path-to-slug conversion.\n *\n * Generalized from packages/core/src/content/collector.ts.\n */\n\nimport { extname, relative } from 'path'\n\n/**\n * Convert a content file path to a URL-friendly slug.\n *\n * Examples:\n * content/posts/hello-world/README.md -> 'hello-world'\n * content/posts/hello-world/index.md -> 'hello-world'\n * content/posts/hello-world.md -> 'hello-world'\n * content/authors/john.json -> 'john'\n * content/posts/nested/deep/post.md -> 'nested/deep/post'\n */\nexport function toSlug(filePath: string, directory: string): string {\n const ext = extname(filePath)\n let slug = relative(directory, filePath).replace(/\\\\/g, '/')\n\n // Remove file extension\n if (ext) {\n slug = slug.slice(0, -ext.length)\n }\n\n // Strip README / index suffixes\n if (slug === 'README' || slug === 'index') return '/'\n if (slug.endsWith('/README')) slug = slug.slice(0, -7)\n if (slug.endsWith('/index')) slug = slug.slice(0, -6)\n\n return slug\n}\n","/**\n * Schema validation with rich error reporting.\n *\n * Wraps Zod's safeParse to produce human-readable validation issues.\n */\n\nimport type { ZodError, ZodType } from 'zod'\n\nexport type ValidationIssue = {\n /** Field path (e.g. 'tags[0]') */\n field?: string\n /** Human-readable error message */\n message: string\n /** Error severity */\n severity: 'error' | 'warn'\n /** Origin of this issue — helps consumers distinguish validation phases. */\n source?: 'schema' | 'content' | 'plugin' | 'custom'\n}\n\nexport type ValidationEntryResult = {\n slug: string\n filePath: string\n issues: ValidationIssue[]\n}\n\nexport type ValidationResult = {\n collection: string\n entries: ValidationEntryResult[]\n errors: number\n warnings: number\n}\n\n/** Format a Zod error path into a human-readable field path. */\nexport function formatPath(path: PropertyKey[]): string {\n return path\n .map((segment, i) => {\n if (typeof segment === 'number') return `[${segment}]`\n if (typeof segment === 'symbol') return `[${String(segment)}]`\n if (i === 0) return segment\n return `.${segment}`\n })\n .join('')\n}\n\n/** Validate data against a Zod schema and return structured issues. */\nexport function validateSchema(\n data: Record<string, any>,\n schema: ZodType,\n): {\n issues: ValidationIssue[]\n validatedData: any\n} {\n const result = schema.safeParse(data)\n if (result.success) {\n return {\n issues: [],\n validatedData: result.data,\n }\n }\n\n const issues = (result.error as ZodError).issues.map((issue) => ({\n field: issue.path.length > 0 ? formatPath(issue.path) : undefined,\n message: issue.message,\n severity: 'error' as const,\n source: 'schema' as const,\n }))\n\n // On failure, return raw data so the pipeline can continue in non-strict mode.\n // The issues array signals that validation did not pass.\n return {\n issues,\n validatedData: data,\n }\n}\n","/**\n * Code block validator — checks fenced code block meta syntax.\n *\n * Walks the shared MDAST for `code` nodes. Validates known meta properties\n * and language identifiers. Meta syntax follows Expressive Code conventions.\n */\n\nimport type { ValidationIssue } from './schema-validator'\nimport type { ContentValidator, MdastNode, ResolvedValidatorContext } from './types'\n\n/** Known meta properties accepted by Expressive Code and its plugins. */\nconst KNOWN_META_PROPS = new Set([\n 'title',\n 'showLineNumbers',\n 'startLineNumber',\n 'wrap',\n 'frame',\n 'collapse',\n 'mark',\n 'ins',\n 'del',\n])\n\n/** Extract the property name portion of a meta token (before `=` or `{`). */\nfunction extractMetaPropNames(meta: string): string[] {\n const props: string[] = []\n\n // Match key=value, key={...}, or bare flags\n const tokenRegex = /(\\w+)(?:=(?:\\{[^}]*\\}|\"[^\"]*\"|'[^']*'|\\S+))?/g\n let match: RegExpExecArray | null\n while ((match = tokenRegex.exec(meta)) !== null) {\n props.push(match[1]!)\n }\n\n return props\n}\n\n/** Collect all `code` nodes from MDAST. */\nfunction collectCodeBlocks(node: MdastNode): MdastNode[] {\n const blocks: MdastNode[] = []\n\n if (node.type === 'code') {\n blocks.push(node)\n }\n\n if (node.children) {\n for (const child of node.children) {\n blocks.push(...collectCodeBlocks(child))\n }\n }\n\n return blocks\n}\n\nexport const codeBlockValidator: ContentValidator = {\n name: 'code-blocks',\n\n validate(ctx: ResolvedValidatorContext): ValidationIssue[] {\n if (!ctx.rawContent) return []\n\n const issues: ValidationIssue[] = []\n const tree = ctx.mdast as MdastNode\n\n const codeBlocks = collectCodeBlocks(tree)\n\n for (const block of codeBlocks) {\n const line = block.position?.start.line\n const lineInfo = line ? ` (line ${line})` : ''\n const meta = block.meta ?? ''\n const hasMeta = meta.trim().length > 0\n\n // Language required when using syntax features\n if (hasMeta && !block.lang) {\n issues.push({\n field: `code-block${lineInfo}`,\n message: 'Code block has meta properties but no language identifier',\n severity: 'warn',\n })\n }\n\n if (!hasMeta) continue\n\n // Check for unknown meta properties\n const propNames = extractMetaPropNames(meta)\n for (const prop of propNames) {\n if (!KNOWN_META_PROPS.has(prop)) {\n issues.push({\n field: `code-block${lineInfo}`,\n message: `Unknown code block meta property: \"${prop}\"`,\n severity: 'warn',\n })\n }\n }\n }\n\n return issues\n },\n}\n","/**\n * Heading validator — checks heading structure in markdown.\n *\n * Walks the shared MDAST for heading nodes. Validates level ordering and h1 uniqueness.\n */\n\nimport type { ValidationIssue } from './schema-validator'\nimport type { ContentValidator, MdastNode, ResolvedValidatorContext } from './types'\n\n/** Extract plain text from a heading node's children. */\nfunction getTextContent(node: MdastNode): string {\n if (node.type === 'text') return node.value ?? ''\n if (node.children) return node.children.map(getTextContent).join('')\n return ''\n}\n\n/** Collect all heading nodes from MDAST. */\nfunction collectHeadings(node: MdastNode): Array<{ depth: number; text: string; line?: number }> {\n const headings: Array<{ depth: number; text: string; line?: number }> = []\n\n if (node.type === 'heading' && node.depth) {\n headings.push({\n depth: node.depth,\n text: getTextContent(node),\n line: node.position?.start.line,\n })\n }\n\n if (node.children) {\n for (const child of node.children) {\n headings.push(...collectHeadings(child))\n }\n }\n\n return headings\n}\n\nexport const headingValidator: ContentValidator = {\n name: 'headings',\n\n validate(ctx: ResolvedValidatorContext): ValidationIssue[] {\n if (!ctx.rawContent) return []\n\n const issues: ValidationIssue[] = []\n const tree = ctx.mdast as MdastNode\n\n const headings = collectHeadings(tree)\n\n // No headings in a document with content is worth noting\n if (headings.length === 0) {\n const hasContent = ctx.rawContent.trim().length > 0\n if (hasContent) {\n issues.push({\n message: 'Document has content but no headings',\n severity: 'warn',\n })\n }\n return issues\n }\n\n // Empty heading text\n for (const h of headings) {\n if (!h.text.trim()) {\n const lineInfo = h.line ? ` (line ${h.line})` : ''\n issues.push({\n field: `headings${lineInfo}`,\n message: `Empty heading at level h${h.depth}`,\n severity: 'warn',\n })\n }\n }\n\n // At most one h1\n const h1s = headings.filter((h) => h.depth === 1)\n if (h1s.length > 1) {\n for (const h of h1s.slice(1)) {\n const lineInfo = h.line ? ` (line ${h.line})` : ''\n issues.push({\n field: `headings${lineInfo}`,\n message: `Multiple h1 headings found: \"${h.text}\"`,\n severity: 'warn',\n })\n }\n }\n\n // No skipped levels (only flag when going deeper)\n for (let i = 1; i < headings.length; i++) {\n const prev = headings[i - 1]!\n const curr = headings[i]!\n if (curr.depth > prev.depth + 1) {\n const lineInfo = curr.line ? ` (line ${curr.line})` : ''\n issues.push({\n field: `headings${lineInfo}`,\n message: `Heading level skip: h${prev.depth} -> h${curr.depth} (\"${curr.text}\")`,\n severity: 'warn',\n })\n }\n }\n\n return issues\n },\n}\n","/**\n * Link validator — checks links in markdown content.\n *\n * Walks the shared MDAST for link/image nodes. Internal links are checked for file existence;\n * external links are checked for well-formed URL format.\n */\n\nimport { existsSync } from 'fs'\nimport { dirname, resolve } from 'path'\nimport type { ValidationIssue } from './schema-validator'\nimport type { ContentValidator, MdastNode, ResolvedValidatorContext } from './types'\n\n/** Extract plain text from a node's children. */\nfunction getTextContent(node: MdastNode): string {\n if (node.type === 'text') return node.value ?? ''\n if (node.children) return node.children.map(getTextContent).join('')\n return ''\n}\n\n/** Walk MDAST tree, collecting link and image nodes. */\nfunction collectLinks(node: MdastNode): Array<{ url: string; text: string; line?: number }> {\n const links: Array<{ url: string; text: string; line?: number }> = []\n\n if ((node.type === 'link' || node.type === 'image') && node.url) {\n links.push({\n url: node.url,\n text: node.type === 'link' ? getTextContent(node) : '',\n line: node.position?.start.line,\n })\n }\n\n if (node.children) {\n for (const child of node.children) {\n links.push(...collectLinks(child))\n }\n }\n\n return links\n}\n\nfunction isInternalLink(url: string): boolean {\n if (url.startsWith('#')) return false\n if (url.startsWith('http://') || url.startsWith('https://')) return false\n if (url.startsWith('//')) return false\n if (url.startsWith('mailto:')) return false\n if (url.startsWith('tel:')) return false\n if (url.startsWith('data:')) return false\n return true\n}\n\nfunction isWellFormedUrl(url: string): boolean {\n try {\n new URL(url)\n return true\n } catch {\n return false\n }\n}\n\nexport type LinkValidatorOptions = {\n /** Glob patterns for internal links to skip file-existence checks on. */\n skipPatterns?: string[]\n}\n\nexport function createLinkValidator(options?: LinkValidatorOptions): ContentValidator {\n const skipPatterns = options?.skipPatterns ?? []\n\n function shouldSkip(url: string): boolean {\n return skipPatterns.some((pattern) => {\n if (pattern.includes('*')) {\n const regex = new RegExp('^' + pattern.replace(/\\*/g, '.*') + '$')\n return regex.test(url)\n }\n return url.startsWith(pattern)\n })\n }\n\n return {\n name: 'links',\n\n validate(ctx: ResolvedValidatorContext): ValidationIssue[] {\n if (!ctx.rawContent) return []\n\n const issues: ValidationIssue[] = []\n const tree = ctx.mdast as MdastNode\n\n const links = collectLinks(tree)\n const fileDir = dirname(ctx.filePath)\n\n for (const link of links) {\n const lineInfo = link.line ? ` (line ${link.line})` : ''\n\n // Empty link text — bad accessibility\n if (link.text !== undefined && !link.text.trim()) {\n issues.push({\n field: `links${lineInfo}`,\n message: `Link has no visible text: ${link.url}`,\n severity: 'warn',\n })\n }\n\n // External links — check URL format\n if (link.url.startsWith('http://') || link.url.startsWith('https://')) {\n if (!isWellFormedUrl(link.url)) {\n issues.push({\n field: `links${lineInfo}`,\n message: `Malformed external URL: ${link.url}`,\n severity: 'warn',\n })\n }\n continue\n }\n\n // Internal links — check file exists\n if (isInternalLink(link.url)) {\n if (shouldSkip(link.url)) continue\n\n // Strip fragment and query\n const urlPath = link.url.split('#')[0]!.split('?')[0]!\n if (!urlPath) continue // pure fragment link\n\n const resolved = resolve(fileDir, urlPath)\n if (!existsSync(resolved)) {\n issues.push({\n field: `links${lineInfo}`,\n message: `Broken internal link: ${link.url}`,\n severity: 'error',\n })\n }\n }\n }\n\n return issues\n },\n }\n}\n\nexport const linkValidator: ContentValidator = createLinkValidator()\n","/**\n * Validation runner — executes a list of content validators on an entry.\n *\n * Validators that throw are caught and converted to error-severity issues\n * so one failing validator does not block the rest.\n */\n\nimport type { Root } from 'mdast'\nimport remarkParse from 'remark-parse'\nimport { unified } from 'unified'\nimport type { ValidationIssue } from './schema-validator'\nimport type { ContentValidator, ResolvedValidatorContext, ValidatorContext } from './types'\n\nimport { codeBlockValidator } from './code-block-validator'\nimport { headingValidator } from './heading-validator'\nimport { linkValidator } from './link-validator'\n\n/** The built-in validators for markdown content. */\nexport const builtinMarkdownValidators: ContentValidator[] = [\n linkValidator,\n codeBlockValidator,\n headingValidator,\n]\n\n/** Parse raw markdown to MDAST once, reusing any pre-parsed tree. */\nfunction resolveContext(ctx: ValidatorContext): ResolvedValidatorContext {\n const mdast: Root =\n ctx.mdast ??\n unified()\n .use(remarkParse)\n .parse(ctx.rawContent ?? '')\n return { ...ctx, mdast }\n}\n\n/** Run all validators on a single content entry. */\nexport async function runValidators(\n ctx: ValidatorContext,\n validators: ContentValidator[],\n): Promise<ValidationIssue[]> {\n // Parse the MDAST once before the loop so all validators share the same tree.\n const resolved = resolveContext(ctx)\n\n const issues: ValidationIssue[] = []\n\n for (const validator of validators) {\n try {\n const result = await validator.validate(resolved)\n issues.push(...result.map((issue) => ({ ...issue, source: 'content' as const })))\n } catch (err) {\n // Convert thrown errors into issues so one bad validator doesn't abort all\n const message = err instanceof Error ? err.message : String(err)\n issues.push({\n message: `Validator \"${validator.name}\" threw: ${message}`,\n severity: 'error',\n source: 'content',\n })\n }\n }\n\n return issues\n}\n","/**\n * ContentStore — in-memory cache for loaded collections.\n *\n * Handles file discovery, loading, validation, and caching.\n * Not exported directly — used internally by ContentLayer.\n */\n\nimport { availableParallelism } from 'os'\nimport { resolve } from 'path'\nimport type { MarkdownConfig } from './schemas/markdown-config'\nimport type { ZodType } from 'zod'\nimport { ContentEntry } from './entry'\nimport { defaultIncludePatterns, resolveLoader } from './loaders'\nimport type { Loader } from './loaders/types'\nimport { collectRehypePlugins, collectRemarkPlugins, runPluginValidators } from './plugins'\nimport type { CollectionDef, RawEntry } from './schemas/collection'\nimport type { ContentLayerConfig } from './schemas/content-config'\nimport { discoverFiles } from './utils/glob'\nimport { toSlug } from './utils/slug'\nimport { validateSchema, type ValidationIssue } from './validation'\nimport { builtinMarkdownValidators, runValidators } from './validation/runner'\nimport type { ContentValidator } from './validation/types'\n\nconst MAX_CONCURRENCY = availableParallelism() * 2\n\nasync function mapWithConcurrency<T, R>(\n items: T[],\n concurrency: number,\n fn: (item: T) => Promise<R>,\n): Promise<R[]> {\n const results: R[] = Array.from({ length: items.length })\n let index = 0\n\n async function worker(): Promise<void> {\n while (index < items.length) {\n const i = index++\n results[i] = await fn(items[i])\n }\n }\n\n const workers = Array.from({ length: Math.min(concurrency, items.length) }, () => worker())\n await Promise.all(workers)\n return results\n}\n\ntype CacheEntry = {\n entry: ContentEntry\n issues: ValidationIssue[]\n}\n\nexport class ContentStore {\n private cache = new Map<string, Map<string, CacheEntry>>()\n private loaded = new Set<string>()\n private loading = new Map<string, Promise<ContentEntry[]>>()\n private config: ContentLayerConfig\n private rootDir: string\n private markdownConfig: MarkdownConfig\n\n constructor(config: ContentLayerConfig) {\n this.config = config\n this.rootDir = config.root ? resolve(config.root) : process.cwd()\n this.markdownConfig = this.createMarkdownConfig()\n }\n\n /** Load a collection (if not already loaded) and return entries. */\n async loadCollection<S extends ZodType>(\n name: string,\n def: CollectionDef<S>,\n ): Promise<ContentEntry[]> {\n if (this.loaded.has(name)) {\n const cached = this.cache.get(name)\n return cached ? Array.from(cached.values()).map((c) => c.entry) : []\n }\n\n const existing = this.loading.get(name)\n if (existing) return existing\n\n const promise = this._doLoadCollection(name, def)\n this.loading.set(name, promise)\n try {\n return await promise\n } finally {\n this.loading.delete(name)\n }\n }\n\n private async _doLoadCollection<S extends ZodType>(\n name: string,\n def: CollectionDef<S>,\n ): Promise<ContentEntry[]> {\n const loader = resolveLoader(def.loader)\n const directory = resolve(this.rootDir, def.directory)\n const include = def.include ?? defaultIncludePatterns(loader)\n\n const files = await discoverFiles({\n directory,\n include,\n exclude: def.exclude,\n })\n\n const entries = new Map<string, CacheEntry>()\n const strict = this.config.strict ?? false\n const results = await mapWithConcurrency(files, MAX_CONCURRENCY, async (filePath) => {\n try {\n return await this.loadEntry(name, filePath, directory, loader, def)\n } catch (err) {\n const message = err instanceof Error ? err.message : String(err)\n const loadError = new Error(`[${name}] Failed to load ${filePath}: ${message}`, {\n cause: err,\n })\n\n if (strict) {\n throw loadError\n }\n\n console.warn(`[pagesmith] ${loadError.message}`)\n const slug = def.slugify ? def.slugify(filePath, directory) : toSlug(filePath, directory)\n return {\n entry: new ContentEntry(slug, name, filePath, {}, undefined, this.markdownConfig),\n issues: [\n { message: loadError.message, severity: 'error' as const, source: 'schema' as const },\n ],\n }\n }\n })\n\n for (const result of results) {\n if (result) {\n entries.set(result.entry.slug, result)\n }\n }\n\n this.cache.set(name, entries)\n this.loaded.add(name)\n\n return Array.from(entries.values()).map((c) => c.entry)\n }\n\n /** Load a single entry from a file. */\n private async loadEntry(\n collectionName: string,\n filePath: string,\n directory: string,\n loader: Loader,\n def: CollectionDef<any>,\n ): Promise<CacheEntry | null> {\n const loaded = await loader.load(filePath)\n const slug = def.slugify ? def.slugify(filePath, directory) : toSlug(filePath, directory)\n\n let raw: RawEntry = {\n data: loaded.data,\n content: loaded.content,\n filePath,\n slug,\n }\n\n // Apply transform\n if (def.transform) {\n raw = await def.transform(raw)\n }\n\n // Apply computed fields (clone data to avoid mutating loader output)\n if (def.computed) {\n raw = { ...raw, data: { ...raw.data } }\n for (const [key, fn] of Object.entries(def.computed) as Array<\n [string, (entry: RawEntry) => any]\n >) {\n raw.data[key] = await fn(raw)\n }\n }\n\n // Apply filter\n if (def.filter && !def.filter(raw)) {\n return null\n }\n\n // Validate schema once to collect issues and transformed data.\n const { issues, validatedData } = validateSchema(raw.data, def.schema)\n\n // Custom validation\n if (def.validate) {\n const customError = def.validate(raw)\n if (customError) {\n issues.push({ message: customError, severity: 'error', source: 'custom' })\n }\n }\n\n // Run content validators on markdown entries\n const isMarkdownEntry = raw.content !== undefined\n if (isMarkdownEntry) {\n const validators = this.resolveValidators(def)\n if (validators.length > 0) {\n const contentIssues = await runValidators(\n {\n filePath,\n slug,\n collection: collectionName,\n rawContent: raw.content,\n data: raw.data,\n getEntry: (col, s) => {\n const cached = this.cache.get(col)?.get(s)\n if (!cached) return undefined\n return { slug: cached.entry.slug, data: cached.entry.data }\n },\n },\n validators,\n )\n issues.push(...contentIssues)\n }\n }\n\n if (this.config.plugins?.length) {\n const pluginIssues = runPluginValidators(this.config.plugins, {\n data: raw.data,\n content: raw.content,\n })\n for (const message of pluginIssues) {\n issues.push({ message, severity: 'error', source: 'plugin' })\n }\n }\n\n const entry = new ContentEntry(\n slug,\n collectionName,\n filePath,\n validatedData,\n raw.content,\n this.markdownConfig,\n )\n\n return { entry, issues }\n }\n\n /** Get a single entry by slug. */\n getEntry(collection: string, slug: string): ContentEntry | undefined {\n return this.cache.get(collection)?.get(slug)?.entry\n }\n\n isCollectionLoaded(collection: string): boolean {\n return this.loaded.has(collection)\n }\n\n /** Get validation issues for a collection. */\n getIssues(collection: string): Map<string, ValidationIssue[]> {\n const result = new Map<string, ValidationIssue[]>()\n const entries = this.cache.get(collection)\n if (!entries) return result\n for (const [slug, cached] of entries) {\n if (cached.issues.length > 0) {\n result.set(slug, cached.issues)\n }\n }\n return result\n }\n\n /** Invalidate a single entry and reload it without reloading the entire collection. */\n async invalidate(collection: string, slug: string): Promise<void> {\n const def = this.config.collections[collection]\n if (!def) return\n\n const collectionCache = this.cache.get(collection)\n if (!collectionCache) return\n\n const existing = collectionCache.get(slug)\n if (!existing) return\n\n const loader = resolveLoader(def.loader)\n const directory = resolve(this.rootDir, def.directory)\n\n try {\n const result = await this.loadEntry(\n collection,\n existing.entry.filePath,\n directory,\n loader,\n def,\n )\n if (result) {\n collectionCache.set(slug, result)\n } else {\n // Entry was filtered out after reload\n collectionCache.delete(slug)\n }\n } catch {\n // File may have been deleted; remove from cache\n collectionCache.delete(slug)\n }\n }\n\n /** Invalidate an entire collection. */\n async invalidateCollection(collection: string): Promise<void> {\n this.cache.delete(collection)\n this.loaded.delete(collection)\n }\n\n /** Invalidate all collections. */\n invalidateAll(): void {\n this.cache.clear()\n this.loaded.clear()\n }\n\n /** Get cache statistics for debugging and monitoring. */\n getCacheStats(): { collections: number; entries: Record<string, number>; totalEntries: number } {\n const entries: Record<string, number> = {}\n let totalEntries = 0\n for (const [name, cache] of this.cache) {\n entries[name] = cache.size\n totalEntries += cache.size\n }\n return { collections: this.loaded.size, entries, totalEntries }\n }\n\n /** Invalidate entries matching a predicate without reloading the entire collection. */\n async invalidateWhere(\n collection: string,\n predicate: (entry: ContentEntry) => boolean,\n ): Promise<number> {\n const collectionCache = this.cache.get(collection)\n if (!collectionCache) return 0\n\n const def = this.config.collections[collection]\n if (!def) return 0\n\n const loader = resolveLoader(def.loader)\n const directory = resolve(this.rootDir, def.directory)\n let count = 0\n\n for (const [slug, cached] of collectionCache) {\n if (!predicate(cached.entry)) continue\n count++\n try {\n const result = await this.loadEntry(\n collection,\n cached.entry.filePath,\n directory,\n loader,\n def,\n )\n if (result) {\n collectionCache.set(slug, result)\n } else {\n collectionCache.delete(slug)\n }\n } catch {\n collectionCache.delete(slug)\n }\n }\n\n return count\n }\n\n /** Resolve the list of content validators for a collection. */\n private resolveValidators(def: CollectionDef<any>): ContentValidator[] {\n const builtin = def.disableBuiltinValidators ? [] : builtinMarkdownValidators\n const custom = def.validators ?? []\n return [...builtin, ...custom]\n }\n\n private createMarkdownConfig(): MarkdownConfig {\n const base = this.config.markdown ?? {}\n const remarkPlugins = [...(base.remarkPlugins ?? [])]\n const rehypePlugins = [...(base.rehypePlugins ?? [])]\n const plugins = this.config.plugins ?? []\n\n if (plugins.length > 0) {\n remarkPlugins.push(...collectRemarkPlugins(plugins))\n rehypePlugins.push(...collectRehypePlugins(plugins))\n }\n\n return {\n ...base,\n ...(remarkPlugins.length > 0 ? { remarkPlugins } : {}),\n ...(rehypePlugins.length > 0 ? { rehypePlugins } : {}),\n }\n }\n}\n","/**\n * ContentLayer — the main API for working with content collections.\n *\n * Created via createContentLayer(config). Provides methods to:\n * - Load and query collections (getCollection, getEntry)\n * - Convert markdown directly (convert)\n * - Invalidate cache (invalidate, invalidateCollection, invalidateAll)\n * - Validate all entries (validate)\n */\n\nimport { watch as fsWatch, type FSWatcher } from 'fs'\nimport { resolve as pathResolve } from 'path'\n\nimport { convert as coreConvert } from './convert'\nimport type { ConvertResult } from './convert'\nimport type { MarkdownConfig } from './schemas/markdown-config'\nimport type { ContentEntry } from './entry'\nimport type { CollectionDef, InferCollectionData } from './schemas/collection'\nimport type { ContentLayerConfig } from './schemas/content-config'\nimport { ContentStore } from './store'\nimport type { ValidationResult } from './validation'\n\nexport type WatchEvent = {\n collection: string\n event: string\n filename: string | null\n}\n\nexport type WatchHandle = {\n close(): void\n}\n\nexport type WatchCallback = (event: WatchEvent) => void\n\n/** Typed content layer that preserves collection schema types. */\nexport type TypedContentLayer<T extends Record<string, CollectionDef>> = ContentLayer & {\n getCollection<K extends keyof T & string>(\n name: K,\n ): Promise<ContentEntry<InferCollectionData<T[K]>>[]>\n getEntry<K extends keyof T & string>(\n collection: K,\n slug: string,\n ): Promise<ContentEntry<InferCollectionData<T[K]>> | undefined>\n}\n\nexport interface ContentLayer {\n /** Get all entries in a collection. */\n getCollection(name: string): Promise<ContentEntry[]>\n\n /** Get a single entry by collection name and slug. */\n getEntry(collection: string, slug: string): Promise<ContentEntry | undefined>\n\n /** Convert raw markdown to HTML (no collection, no validation). */\n convert(markdown: string, options?: LayerConvertOptions): Promise<ConvertResult>\n\n /** Invalidate a single entry's cache. */\n invalidate(collection: string, slug: string): Promise<void>\n\n /** Invalidate an entire collection's cache. */\n invalidateCollection(collection: string): Promise<void>\n\n /** Invalidate all cached data. */\n invalidateAll(): void\n\n /** Validate all entries in a collection (or all collections). */\n validate(collection?: string): Promise<ValidationResult[]>\n\n /** Get the names of all configured collections. */\n getCollectionNames(): string[]\n\n /** Get the definition of a collection. */\n getCollectionDef(name: string): CollectionDef | undefined\n\n /** Get all collection definitions. */\n getCollections(): Record<string, CollectionDef>\n\n /** Invalidate entries in a collection that match a predicate. Returns count of invalidated entries. */\n invalidateWhere(collection: string, predicate: (entry: ContentEntry) => boolean): Promise<number>\n\n /** Watch collection directories for changes. Returns a handle to stop watching. */\n watch(callback: WatchCallback): WatchHandle\n\n /** Get cache statistics for debugging and monitoring. */\n getCacheStats(): { collections: number; entries: Record<string, number>; totalEntries: number }\n}\n\nexport type LayerConvertOptions = {\n markdown?: MarkdownConfig\n}\n\nclass ContentLayerImpl implements ContentLayer {\n private store: ContentStore\n private config: ContentLayerConfig\n\n constructor(config: ContentLayerConfig) {\n this.config = config\n this.store = new ContentStore(config)\n }\n\n async getCollection(name: string): Promise<ContentEntry[]> {\n const def = this.config.collections[name]\n if (!def) {\n throw new Error(\n `Collection \"${name}\" not found. Available: ${Object.keys(this.config.collections).join(\n ', ',\n )}`,\n )\n }\n return this.store.loadCollection(name, def)\n }\n\n async getEntry(collection: string, slug: string): Promise<ContentEntry | undefined> {\n const cached = this.store.getEntry(collection, slug)\n if (cached) return cached\n\n // If the collection was already loaded and this slug wasn't found, short-circuit.\n if (this.store.isCollectionLoaded(collection)) return undefined\n\n // The first getEntry call loads the full collection and then serves from cache.\n // Single-entry loading would skip collection-level transforms and validation context.\n await this.getCollection(collection)\n return this.store.getEntry(collection, slug)\n }\n\n async convert(markdown: string, options?: LayerConvertOptions): Promise<ConvertResult> {\n return coreConvert(markdown, {\n markdown: options?.markdown ?? this.config.markdown,\n })\n }\n\n async invalidate(collection: string, slug: string): Promise<void> {\n await this.store.invalidate(collection, slug)\n }\n\n async invalidateCollection(collection: string): Promise<void> {\n await this.store.invalidateCollection(collection)\n }\n\n invalidateAll(): void {\n this.store.invalidateAll()\n }\n\n async invalidateWhere(\n collection: string,\n predicate: (entry: ContentEntry) => boolean,\n ): Promise<number> {\n return this.store.invalidateWhere(collection, predicate)\n }\n\n async validate(collection?: string): Promise<ValidationResult[]> {\n const names = collection ? [collection] : Object.keys(this.config.collections)\n const results: ValidationResult[] = []\n\n for (const name of names) {\n // Ensure loaded\n await this.getCollection(name)\n\n const issues = this.store.getIssues(name)\n const entries = Array.from(issues.entries()).map(([slug, entryIssues]) => {\n const entry = this.store.getEntry(name, slug)\n return {\n slug,\n filePath: entry?.filePath ?? '',\n issues: entryIssues,\n }\n })\n\n let errors = 0\n let warnings = 0\n for (const entry of entries) {\n for (const issue of entry.issues) {\n if (issue.severity === 'error') errors++\n else warnings++\n }\n }\n\n results.push({ collection: name, entries, errors, warnings })\n }\n\n return results\n }\n\n getCollectionNames(): string[] {\n return Object.keys(this.config.collections)\n }\n\n getCollectionDef(name: string): CollectionDef | undefined {\n return this.config.collections[name]\n }\n\n getCollections(): Record<string, CollectionDef> {\n return { ...this.config.collections }\n }\n\n watch(callback: WatchCallback): WatchHandle {\n const watchers: FSWatcher[] = []\n const root = this.config.root ?? process.cwd()\n const timers = new Map<string, ReturnType<typeof setTimeout>>()\n\n for (const [name, def] of Object.entries(this.config.collections)) {\n const dir = pathResolve(root, def.directory)\n try {\n const watcher = fsWatch(dir, { recursive: true }, (event, filename) => {\n // Debounce: coalesce rapid changes per collection within 100ms\n const existing = timers.get(name)\n if (existing) clearTimeout(existing)\n timers.set(\n name,\n setTimeout(() => {\n timers.delete(name)\n void this.store.invalidateCollection(name)\n callback({ collection: name, event, filename })\n }, 100),\n )\n })\n watcher.on('error', (err) => {\n console.warn(`Content watcher error for \"${name}\":`, err.message)\n })\n watchers.push(watcher)\n } catch {\n // Directory may not exist yet — skip silently\n }\n }\n\n return {\n close() {\n for (const w of watchers) w.close()\n for (const t of timers.values()) clearTimeout(t)\n timers.clear()\n },\n }\n }\n\n getCacheStats() {\n return this.store.getCacheStats()\n }\n}\n\n/** Create a new content layer from a configuration. */\nexport function createContentLayer<T extends Record<string, CollectionDef>>(\n config: ContentLayerConfig & { collections: T },\n): TypedContentLayer<T>\nexport function createContentLayer(config: ContentLayerConfig): ContentLayer\nexport function createContentLayer(config: ContentLayerConfig): ContentLayer {\n return new ContentLayerImpl(config)\n}\n"],"mappings":"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"}
|
|
@@ -1,5 +1,6 @@
|
|
|
1
|
-
import { d as ValidatorContext, i as CollectionDef, l as ContentValidator, m as ValidationResult, o as InferCollectionData, p as ValidationIssue, t as ContentLayerConfig } from "./content-config-
|
|
2
|
-
import {
|
|
1
|
+
import { d as ValidatorContext, i as CollectionDef, l as ContentValidator, m as ValidationResult, o as InferCollectionData, p as ValidationIssue, t as ContentLayerConfig } from "./content-config-Bu2HH0Yx.mjs";
|
|
2
|
+
import { t as MarkdownConfig } from "./markdown-config-CDvh5aJ-.mjs";
|
|
3
|
+
import { t as Heading } from "./heading-D4X2L4vd.mjs";
|
|
3
4
|
|
|
4
5
|
//#region src/convert.d.ts
|
|
5
6
|
type ConvertOptions = {
|
|
@@ -118,4 +119,4 @@ declare function createContentLayer<T extends Record<string, CollectionDef>>(con
|
|
|
118
119
|
declare function createContentLayer(config: ContentLayerConfig): ContentLayer;
|
|
119
120
|
//#endregion
|
|
120
121
|
export { ConvertResult as _, WatchEvent as a, builtinMarkdownValidators as c, linkValidator as d, headingValidator as f, ConvertOptions as g, RenderedContent as h, WatchCallback as i, runValidators as l, ContentEntry as m, LayerConvertOptions as n, WatchHandle as o, codeBlockValidator as p, TypedContentLayer as r, createContentLayer as s, ContentLayer as t, createLinkValidator as u, convert as v };
|
|
121
|
-
//# sourceMappingURL=content-layer-
|
|
122
|
+
//# sourceMappingURL=content-layer-Ckt08g2i.d.mts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"content-layer-Ckt08g2i.d.mts","names":[],"sources":["../src/convert.ts","../src/entry.ts","../src/validation/code-block-validator.ts","../src/validation/heading-validator.ts","../src/validation/link-validator.ts","../src/validation/runner.ts","../src/content-layer.ts"],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.mts","names":[],"sources":["../../src/create/index.ts"],"mappings":";;AAiCA;;;;KAAY,QAAA;EACV,IAAA;EACA,WAAA;EACA,MAAA;EACA,IAAA;EACA,UAAA;EACA,OAAA,EAAS,MAAA;AAAA;AAAA,cAGE,SAAA,EAAW,QAAA;AAAA,iBAkFR,aAAA,CAAA;AAAA,
|
|
1
|
+
{"version":3,"file":"index.d.mts","names":[],"sources":["../../src/create/index.ts"],"mappings":";;AAiCA;;;;KAAY,QAAA;EACV,IAAA;EACA,WAAA;EACA,MAAA;EACA,IAAA;EACA,UAAA;EACA,OAAA,EAAS,MAAA;AAAA;AAAA,cAGE,SAAA,EAAW,QAAA;AAAA,iBAkFR,aAAA,CAAA;AAAA,iBAmJM,aAAA,CAAc,WAAA,UAAqB,YAAA,WAAuB,OAAA"}
|
package/dist/create/index.mjs
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { cpSync, existsSync, mkdirSync, mkdtempSync, readFileSync, readdirSync, rmSync, unlinkSync, writeFileSync } from "fs";
|
|
2
2
|
import { join, resolve } from "path";
|
|
3
3
|
import { tmpdir } from "os";
|
|
4
|
-
import { execSync } from "child_process";
|
|
4
|
+
import { execFileSync, execSync } from "child_process";
|
|
5
5
|
//#region src/create/index.ts
|
|
6
6
|
/**
|
|
7
7
|
* Project scaffolding for `pagesmith create`.
|
|
@@ -182,7 +182,10 @@ function writePackageJson(destination, projectName, template) {
|
|
|
182
182
|
pkg.dependencies = pkg.dependencies ?? {};
|
|
183
183
|
pkg.dependencies[template.dependency] = getPackageVersion();
|
|
184
184
|
if (pkg.devDependencies?.vite && !pkg.devDependencies["vite-plus"]) pkg.devDependencies["vite-plus"] = "^0.1.13";
|
|
185
|
-
|
|
185
|
+
try {
|
|
186
|
+
const npmVersion = execFileSync("npm", ["--version"], { encoding: "utf-8" }).trim();
|
|
187
|
+
pkg.packageManager = `npm@${npmVersion}`;
|
|
188
|
+
} catch {}
|
|
186
189
|
writeFileSync(existingPkg, JSON.stringify(pkg, null, 2) + "\n");
|
|
187
190
|
}
|
|
188
191
|
async function createProject(projectName, templateName) {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.mjs","names":[],"sources":["../../src/create/index.ts"],"sourcesContent":["/**\n * Project scaffolding for `pagesmith create`.\n *\n * Supports local templates (bundled) and remote templates (GitHub examples).\n */\n\nimport {\n cpSync,\n existsSync,\n mkdirSync,\n mkdtempSync,\n readdirSync,\n readFileSync,\n rmSync,\n unlinkSync,\n writeFileSync,\n} from 'fs'\nimport { join, resolve } from 'path'\nimport { execSync } from 'child_process'\nimport { tmpdir } from 'os'\n\nconst GITHUB_REPO = 'sujeet-pro/pagesmith'\n\nfunction getPackageVersion(): string {\n try {\n const pkgPath = resolve(import.meta.dirname, '..', '..', 'package.json')\n const pkg = JSON.parse(readFileSync(pkgPath, 'utf-8')) as { version?: string }\n return `^${pkg.version ?? '0.1.0'}`\n } catch {\n return '^0.1.0'\n }\n}\n\nexport type Template = {\n name: string\n description: string\n source: 'local' | 'github'\n path: string\n dependency: '@pagesmith/core' | '@pagesmith/docs'\n scripts: Record<string, string>\n}\n\nexport const templates: Template[] = [\n {\n name: 'docs',\n description: 'Documentation site with @pagesmith/docs',\n source: 'local',\n path: 'templates/docs',\n dependency: '@pagesmith/docs',\n scripts: { dev: 'pagesmith dev', build: 'pagesmith build', preview: 'pagesmith preview' },\n },\n {\n name: 'blog',\n description: 'Blog with custom layouts using @pagesmith/core',\n source: 'github',\n path: 'examples/blog-site',\n dependency: '@pagesmith/core',\n scripts: { dev: 'vp dev', build: 'vp build', check: 'vp check' },\n },\n {\n name: 'react',\n description: 'React SSG site with react-router',\n source: 'github',\n path: 'examples/with-react',\n dependency: '@pagesmith/core',\n scripts: {\n dev: 'vp dev',\n build: 'vp build',\n check: 'vp check',\n preview: 'vp preview',\n },\n },\n {\n name: 'solid',\n description: 'SolidJS SSG site',\n source: 'github',\n path: 'examples/with-solid',\n dependency: '@pagesmith/core',\n scripts: {\n dev: 'vp dev',\n build: 'vp build',\n check: 'vp check',\n preview: 'vp preview',\n },\n },\n {\n name: 'svelte',\n description: 'Svelte SSG site',\n source: 'github',\n path: 'examples/with-svelte',\n dependency: '@pagesmith/core',\n scripts: {\n dev: 'vp dev',\n build: 'vp build',\n check: 'vp check',\n preview: 'vp preview',\n },\n },\n {\n name: 'ejs',\n description: 'Vanilla Node.js + EJS templates',\n source: 'github',\n path: 'examples/with-vanilla-ejs',\n dependency: '@pagesmith/core',\n scripts: {\n dev: 'vp dev',\n build: 'vp build',\n check: 'vp check',\n },\n },\n {\n name: 'hbs',\n description: 'Vanilla Node.js + Handlebars templates',\n source: 'github',\n path: 'examples/with-vanilla-hbs',\n dependency: '@pagesmith/core',\n scripts: {\n dev: 'vp dev',\n build: 'vp build',\n check: 'vp check',\n },\n },\n]\n\nexport function listTemplates(): string {\n const maxName = Math.max(...templates.map((t) => t.name.length))\n return templates.map((t) => ` ${t.name.padEnd(maxName + 2)} ${t.description}`).join('\\n')\n}\n\nasync function downloadFromGithub(templatePath: string, destination: string): Promise<void> {\n const tarballUrl = `https://github.com/${GITHUB_REPO}/archive/refs/heads/main.tar.gz`\n console.log('Downloading template from GitHub...')\n\n const response = await fetch(tarballUrl, { redirect: 'follow' })\n if (!response.ok) {\n throw new Error(`Failed to download: ${response.status} ${response.statusText}`)\n }\n\n const tmpFile = join(tmpdir(), `pagesmith-${Date.now()}.tar.gz`)\n const tmpExtract = mkdtempSync(join(tmpdir(), 'pagesmith-'))\n\n try {\n writeFileSync(tmpFile, Buffer.from(await response.arrayBuffer()))\n\n // Extract full tarball\n execSync(`tar xzf ${tmpFile} -C ${tmpExtract}`, { stdio: 'pipe' })\n\n // Find the extracted top-level directory\n const dirs = readdirSync(tmpExtract)\n const topDir = dirs[0]\n if (!topDir) throw new Error('Empty tarball')\n\n const sourcePath = join(tmpExtract, topDir, templatePath)\n if (!existsSync(sourcePath)) {\n throw new Error(`Template path not found in repo: ${templatePath}`)\n }\n\n mkdirSync(destination, { recursive: true })\n cpSync(sourcePath, destination, { recursive: true })\n } finally {\n unlinkSync(tmpFile)\n rmSync(tmpExtract, { recursive: true, force: true })\n }\n}\n\nfunction adaptForStandalone(destination: string, template: Template): void {\n // Update content.config.mjs paths (from ./posts to ./content/posts)\n const configPath = join(destination, 'content.config.mjs')\n if (existsSync(configPath)) {\n let config = readFileSync(configPath, 'utf-8')\n config = config.replace(/directory: '\\.\\/posts'/g, \"directory: './content/posts'\")\n config = config.replace(/directory: '\\.\\/pages'/g, \"directory: './content/pages'\")\n config = config.replace(/directory: '\\.\\/authors'/g, \"directory: './content/authors'\")\n config = config.replace(/directory: '\\.\\/config'/g, \"directory: './content/config'\")\n writeFileSync(configPath, config)\n }\n\n // Update vite.config.ts shared-content references\n const viteConfigPath = join(destination, 'vite.config.ts')\n if (existsSync(viteConfigPath)) {\n let config = readFileSync(viteConfigPath, 'utf-8')\n config = config.replace(\n /import content from '\\.\\.\\/shared-content\\/content\\.config'/g,\n \"import content from './content.config.mjs'\",\n )\n config = config.replace(\n /configPath:\\s*'\\.\\.\\/shared-content\\/content\\.config\\.ts'/g,\n \"configPath: './content.config.mjs'\",\n )\n config = config.replace(\n /root:\\s*resolve\\(import\\.meta\\.dirname,\\s*'\\.\\.\\/shared-content'\\)/g,\n 'root: import.meta.dirname',\n )\n writeFileSync(viteConfigPath, config)\n }\n\n // Update build.mjs (remove shared-content references)\n const buildPath = join(destination, 'build.mjs')\n if (existsSync(buildPath)) {\n let script = readFileSync(buildPath, 'utf-8')\n // Replace shared-content imports\n script = script.replace(\n /import .* from '\\.\\.\\/shared-content\\/content\\.config\\.mjs'/g,\n \"import content from './content.config.mjs'\",\n )\n // Simplify content layer setup\n script = script.replace(\n /const contentRoot = resolve\\(root, '\\.\\.\\/shared-content'\\)/g,\n 'const contentRoot = root',\n )\n // Fix named imports\n script = script.replace(\n /import \\{ pages, posts \\} from '\\.\\.\\/shared-content\\/content\\.config\\.mjs'/g,\n \"import content from './content.config.mjs'\\nconst { pages, posts } = content\",\n )\n writeFileSync(buildPath, script)\n }\n\n // Remove workspace-specific tsconfig paths\n const tsconfigPath = join(destination, 'tsconfig.json')\n if (existsSync(tsconfigPath)) {\n const tsconfig = JSON.parse(readFileSync(tsconfigPath, 'utf-8'))\n if (tsconfig.compilerOptions?.paths) {\n delete tsconfig.compilerOptions.paths\n }\n writeFileSync(tsconfigPath, JSON.stringify(tsconfig, null, 2) + '\\n')\n }\n}\n\nfunction writePackageJson(destination: string, projectName: string, template: Template): void {\n const existingPkg = join(destination, 'package.json')\n let pkg: Record<string, any> = {}\n\n if (existsSync(existingPkg)) {\n pkg = JSON.parse(readFileSync(existingPkg, 'utf-8'))\n }\n\n pkg.name = projectName\n pkg.private = true\n pkg.type = 'module'\n pkg.version = '0.0.0'\n pkg.scripts = template.scripts\n\n // Replace workspace \"*\" deps with actual versions\n if (pkg.dependencies) {\n for (const [name, version] of Object.entries(pkg.dependencies)) {\n if (version === '*' && name.startsWith('@pagesmith/')) {\n pkg.dependencies[name] = getPackageVersion()\n }\n }\n }\n\n // Ensure the primary dependency is present\n pkg.dependencies = pkg.dependencies ?? {}\n pkg.dependencies[template.dependency] = getPackageVersion()\n\n // Keep Vite+ in standalone examples that already use it\n if (pkg.devDependencies?.vite && !pkg.devDependencies['vite-plus']) {\n pkg.devDependencies['vite-plus'] = '^0.1.13'\n }\n\n pkg.packageManager = 'npm@11.12.0'\n\n writeFileSync(existingPkg, JSON.stringify(pkg, null, 2) + '\\n')\n}\n\nexport async function createProject(projectName: string, templateName: string): Promise<void> {\n const template = templates.find((t) => t.name === templateName)\n if (!template) {\n throw new Error(`Unknown template \"${templateName}\". Available templates:\\n${listTemplates()}`)\n }\n\n const destination = resolve(projectName)\n if (existsSync(destination) && readdirSync(destination).length > 0) {\n throw new Error(`Directory \"${projectName}\" already exists and is not empty.`)\n }\n\n if (template.source === 'local') {\n const templateDir = resolve(\n import.meta.dirname,\n '../../templates',\n template.path.split('/').pop()!,\n )\n mkdirSync(destination, { recursive: true })\n cpSync(templateDir, destination, { recursive: true })\n } else {\n await downloadFromGithub(template.path, destination)\n adaptForStandalone(destination, template)\n }\n\n writePackageJson(destination, projectName, template)\n\n console.log(`\\nCreated \"${projectName}\" from the \"${template.name}\" template.\\n`)\n console.log('Next steps:')\n console.log(` cd ${projectName}`)\n console.log(' vp install')\n if (template.scripts.dev) {\n console.log(` vp run dev`)\n } else {\n console.log(` vp run build`)\n }\n console.log()\n}\n"],"mappings":";;;;;;;;;;AAqBA,MAAM,cAAc;AAEpB,SAAS,oBAA4B;AACnC,KAAI;EACF,MAAM,UAAU,QAAQ,OAAO,KAAK,SAAS,MAAM,MAAM,eAAe;AAExE,SAAO,IADK,KAAK,MAAM,aAAa,SAAS,QAAQ,CAAC,CACvC,WAAW;SACpB;AACN,SAAO;;;AAaX,MAAa,YAAwB;CACnC;EACE,MAAM;EACN,aAAa;EACb,QAAQ;EACR,MAAM;EACN,YAAY;EACZ,SAAS;GAAE,KAAK;GAAiB,OAAO;GAAmB,SAAS;GAAqB;EAC1F;CACD;EACE,MAAM;EACN,aAAa;EACb,QAAQ;EACR,MAAM;EACN,YAAY;EACZ,SAAS;GAAE,KAAK;GAAU,OAAO;GAAY,OAAO;GAAY;EACjE;CACD;EACE,MAAM;EACN,aAAa;EACb,QAAQ;EACR,MAAM;EACN,YAAY;EACZ,SAAS;GACP,KAAK;GACL,OAAO;GACP,OAAO;GACP,SAAS;GACV;EACF;CACD;EACE,MAAM;EACN,aAAa;EACb,QAAQ;EACR,MAAM;EACN,YAAY;EACZ,SAAS;GACP,KAAK;GACL,OAAO;GACP,OAAO;GACP,SAAS;GACV;EACF;CACD;EACE,MAAM;EACN,aAAa;EACb,QAAQ;EACR,MAAM;EACN,YAAY;EACZ,SAAS;GACP,KAAK;GACL,OAAO;GACP,OAAO;GACP,SAAS;GACV;EACF;CACD;EACE,MAAM;EACN,aAAa;EACb,QAAQ;EACR,MAAM;EACN,YAAY;EACZ,SAAS;GACP,KAAK;GACL,OAAO;GACP,OAAO;GACR;EACF;CACD;EACE,MAAM;EACN,aAAa;EACb,QAAQ;EACR,MAAM;EACN,YAAY;EACZ,SAAS;GACP,KAAK;GACL,OAAO;GACP,OAAO;GACR;EACF;CACF;AAED,SAAgB,gBAAwB;CACtC,MAAM,UAAU,KAAK,IAAI,GAAG,UAAU,KAAK,MAAM,EAAE,KAAK,OAAO,CAAC;AAChE,QAAO,UAAU,KAAK,MAAM,KAAK,EAAE,KAAK,OAAO,UAAU,EAAE,CAAC,GAAG,EAAE,cAAc,CAAC,KAAK,KAAK;;AAG5F,eAAe,mBAAmB,cAAsB,aAAoC;CAC1F,MAAM,aAAa,sBAAsB,YAAY;AACrD,SAAQ,IAAI,sCAAsC;CAElD,MAAM,WAAW,MAAM,MAAM,YAAY,EAAE,UAAU,UAAU,CAAC;AAChE,KAAI,CAAC,SAAS,GACZ,OAAM,IAAI,MAAM,uBAAuB,SAAS,OAAO,GAAG,SAAS,aAAa;CAGlF,MAAM,UAAU,KAAK,QAAQ,EAAE,aAAa,KAAK,KAAK,CAAC,SAAS;CAChE,MAAM,aAAa,YAAY,KAAK,QAAQ,EAAE,aAAa,CAAC;AAE5D,KAAI;AACF,gBAAc,SAAS,OAAO,KAAK,MAAM,SAAS,aAAa,CAAC,CAAC;AAGjE,WAAS,WAAW,QAAQ,MAAM,cAAc,EAAE,OAAO,QAAQ,CAAC;EAIlE,MAAM,SADO,YAAY,WAAW,CAChB;AACpB,MAAI,CAAC,OAAQ,OAAM,IAAI,MAAM,gBAAgB;EAE7C,MAAM,aAAa,KAAK,YAAY,QAAQ,aAAa;AACzD,MAAI,CAAC,WAAW,WAAW,CACzB,OAAM,IAAI,MAAM,oCAAoC,eAAe;AAGrE,YAAU,aAAa,EAAE,WAAW,MAAM,CAAC;AAC3C,SAAO,YAAY,aAAa,EAAE,WAAW,MAAM,CAAC;WAC5C;AACR,aAAW,QAAQ;AACnB,SAAO,YAAY;GAAE,WAAW;GAAM,OAAO;GAAM,CAAC;;;AAIxD,SAAS,mBAAmB,aAAqB,UAA0B;CAEzE,MAAM,aAAa,KAAK,aAAa,qBAAqB;AAC1D,KAAI,WAAW,WAAW,EAAE;EAC1B,IAAI,SAAS,aAAa,YAAY,QAAQ;AAC9C,WAAS,OAAO,QAAQ,2BAA2B,+BAA+B;AAClF,WAAS,OAAO,QAAQ,2BAA2B,+BAA+B;AAClF,WAAS,OAAO,QAAQ,6BAA6B,iCAAiC;AACtF,WAAS,OAAO,QAAQ,4BAA4B,gCAAgC;AACpF,gBAAc,YAAY,OAAO;;CAInC,MAAM,iBAAiB,KAAK,aAAa,iBAAiB;AAC1D,KAAI,WAAW,eAAe,EAAE;EAC9B,IAAI,SAAS,aAAa,gBAAgB,QAAQ;AAClD,WAAS,OAAO,QACd,gEACA,6CACD;AACD,WAAS,OAAO,QACd,8DACA,qCACD;AACD,WAAS,OAAO,QACd,uEACA,4BACD;AACD,gBAAc,gBAAgB,OAAO;;CAIvC,MAAM,YAAY,KAAK,aAAa,YAAY;AAChD,KAAI,WAAW,UAAU,EAAE;EACzB,IAAI,SAAS,aAAa,WAAW,QAAQ;AAE7C,WAAS,OAAO,QACd,gEACA,6CACD;AAED,WAAS,OAAO,QACd,gEACA,2BACD;AAED,WAAS,OAAO,QACd,gFACA,+EACD;AACD,gBAAc,WAAW,OAAO;;CAIlC,MAAM,eAAe,KAAK,aAAa,gBAAgB;AACvD,KAAI,WAAW,aAAa,EAAE;EAC5B,MAAM,WAAW,KAAK,MAAM,aAAa,cAAc,QAAQ,CAAC;AAChE,MAAI,SAAS,iBAAiB,MAC5B,QAAO,SAAS,gBAAgB;AAElC,gBAAc,cAAc,KAAK,UAAU,UAAU,MAAM,EAAE,GAAG,KAAK;;;AAIzE,SAAS,iBAAiB,aAAqB,aAAqB,UAA0B;CAC5F,MAAM,cAAc,KAAK,aAAa,eAAe;CACrD,IAAI,MAA2B,EAAE;AAEjC,KAAI,WAAW,YAAY,CACzB,OAAM,KAAK,MAAM,aAAa,aAAa,QAAQ,CAAC;AAGtD,KAAI,OAAO;AACX,KAAI,UAAU;AACd,KAAI,OAAO;AACX,KAAI,UAAU;AACd,KAAI,UAAU,SAAS;AAGvB,KAAI,IAAI;OACD,MAAM,CAAC,MAAM,YAAY,OAAO,QAAQ,IAAI,aAAa,CAC5D,KAAI,YAAY,OAAO,KAAK,WAAW,cAAc,CACnD,KAAI,aAAa,QAAQ,mBAAmB;;AAMlD,KAAI,eAAe,IAAI,gBAAgB,EAAE;AACzC,KAAI,aAAa,SAAS,cAAc,mBAAmB;AAG3D,KAAI,IAAI,iBAAiB,QAAQ,CAAC,IAAI,gBAAgB,aACpD,KAAI,gBAAgB,eAAe;AAGrC,KAAI,iBAAiB;AAErB,eAAc,aAAa,KAAK,UAAU,KAAK,MAAM,EAAE,GAAG,KAAK;;AAGjE,eAAsB,cAAc,aAAqB,cAAqC;CAC5F,MAAM,WAAW,UAAU,MAAM,MAAM,EAAE,SAAS,aAAa;AAC/D,KAAI,CAAC,SACH,OAAM,IAAI,MAAM,qBAAqB,aAAa,2BAA2B,eAAe,GAAG;CAGjG,MAAM,cAAc,QAAQ,YAAY;AACxC,KAAI,WAAW,YAAY,IAAI,YAAY,YAAY,CAAC,SAAS,EAC/D,OAAM,IAAI,MAAM,cAAc,YAAY,oCAAoC;AAGhF,KAAI,SAAS,WAAW,SAAS;EAC/B,MAAM,cAAc,QAClB,OAAO,KAAK,SACZ,mBACA,SAAS,KAAK,MAAM,IAAI,CAAC,KAAK,CAC/B;AACD,YAAU,aAAa,EAAE,WAAW,MAAM,CAAC;AAC3C,SAAO,aAAa,aAAa,EAAE,WAAW,MAAM,CAAC;QAChD;AACL,QAAM,mBAAmB,SAAS,MAAM,YAAY;AACpD,qBAAmB,aAAa,SAAS;;AAG3C,kBAAiB,aAAa,aAAa,SAAS;AAEpD,SAAQ,IAAI,cAAc,YAAY,cAAc,SAAS,KAAK,eAAe;AACjF,SAAQ,IAAI,cAAc;AAC1B,SAAQ,IAAI,QAAQ,cAAc;AAClC,SAAQ,IAAI,eAAe;AAC3B,KAAI,SAAS,QAAQ,IACnB,SAAQ,IAAI,eAAe;KAE3B,SAAQ,IAAI,iBAAiB;AAE/B,SAAQ,KAAK"}
|
|
1
|
+
{"version":3,"file":"index.mjs","names":[],"sources":["../../src/create/index.ts"],"sourcesContent":["/**\n * Project scaffolding for `pagesmith create`.\n *\n * Supports local templates (bundled) and remote templates (GitHub examples).\n */\n\nimport {\n cpSync,\n existsSync,\n mkdirSync,\n mkdtempSync,\n readdirSync,\n readFileSync,\n rmSync,\n unlinkSync,\n writeFileSync,\n} from 'fs'\nimport { join, resolve } from 'path'\nimport { execFileSync, execSync } from 'child_process'\nimport { tmpdir } from 'os'\n\nconst GITHUB_REPO = 'sujeet-pro/pagesmith'\n\nfunction getPackageVersion(): string {\n try {\n const pkgPath = resolve(import.meta.dirname, '..', '..', 'package.json')\n const pkg = JSON.parse(readFileSync(pkgPath, 'utf-8')) as { version?: string }\n return `^${pkg.version ?? '0.1.0'}`\n } catch {\n return '^0.1.0'\n }\n}\n\nexport type Template = {\n name: string\n description: string\n source: 'local' | 'github'\n path: string\n dependency: '@pagesmith/core' | '@pagesmith/docs'\n scripts: Record<string, string>\n}\n\nexport const templates: Template[] = [\n {\n name: 'docs',\n description: 'Documentation site with @pagesmith/docs',\n source: 'local',\n path: 'templates/docs',\n dependency: '@pagesmith/docs',\n scripts: { dev: 'pagesmith dev', build: 'pagesmith build', preview: 'pagesmith preview' },\n },\n {\n name: 'blog',\n description: 'Blog with custom layouts using @pagesmith/core',\n source: 'github',\n path: 'examples/blog-site',\n dependency: '@pagesmith/core',\n scripts: { dev: 'vp dev', build: 'vp build', check: 'vp check' },\n },\n {\n name: 'react',\n description: 'React SSG site with react-router',\n source: 'github',\n path: 'examples/with-react',\n dependency: '@pagesmith/core',\n scripts: {\n dev: 'vp dev',\n build: 'vp build',\n check: 'vp check',\n preview: 'vp preview',\n },\n },\n {\n name: 'solid',\n description: 'SolidJS SSG site',\n source: 'github',\n path: 'examples/with-solid',\n dependency: '@pagesmith/core',\n scripts: {\n dev: 'vp dev',\n build: 'vp build',\n check: 'vp check',\n preview: 'vp preview',\n },\n },\n {\n name: 'svelte',\n description: 'Svelte SSG site',\n source: 'github',\n path: 'examples/with-svelte',\n dependency: '@pagesmith/core',\n scripts: {\n dev: 'vp dev',\n build: 'vp build',\n check: 'vp check',\n preview: 'vp preview',\n },\n },\n {\n name: 'ejs',\n description: 'Vanilla Node.js + EJS templates',\n source: 'github',\n path: 'examples/with-vanilla-ejs',\n dependency: '@pagesmith/core',\n scripts: {\n dev: 'vp dev',\n build: 'vp build',\n check: 'vp check',\n },\n },\n {\n name: 'hbs',\n description: 'Vanilla Node.js + Handlebars templates',\n source: 'github',\n path: 'examples/with-vanilla-hbs',\n dependency: '@pagesmith/core',\n scripts: {\n dev: 'vp dev',\n build: 'vp build',\n check: 'vp check',\n },\n },\n]\n\nexport function listTemplates(): string {\n const maxName = Math.max(...templates.map((t) => t.name.length))\n return templates.map((t) => ` ${t.name.padEnd(maxName + 2)} ${t.description}`).join('\\n')\n}\n\nasync function downloadFromGithub(templatePath: string, destination: string): Promise<void> {\n const tarballUrl = `https://github.com/${GITHUB_REPO}/archive/refs/heads/main.tar.gz`\n console.log('Downloading template from GitHub...')\n\n const response = await fetch(tarballUrl, { redirect: 'follow' })\n if (!response.ok) {\n throw new Error(`Failed to download: ${response.status} ${response.statusText}`)\n }\n\n const tmpFile = join(tmpdir(), `pagesmith-${Date.now()}.tar.gz`)\n const tmpExtract = mkdtempSync(join(tmpdir(), 'pagesmith-'))\n\n try {\n writeFileSync(tmpFile, Buffer.from(await response.arrayBuffer()))\n\n // Extract full tarball\n execSync(`tar xzf ${tmpFile} -C ${tmpExtract}`, { stdio: 'pipe' })\n\n // Find the extracted top-level directory\n const dirs = readdirSync(tmpExtract)\n const topDir = dirs[0]\n if (!topDir) throw new Error('Empty tarball')\n\n const sourcePath = join(tmpExtract, topDir, templatePath)\n if (!existsSync(sourcePath)) {\n throw new Error(`Template path not found in repo: ${templatePath}`)\n }\n\n mkdirSync(destination, { recursive: true })\n cpSync(sourcePath, destination, { recursive: true })\n } finally {\n unlinkSync(tmpFile)\n rmSync(tmpExtract, { recursive: true, force: true })\n }\n}\n\nfunction adaptForStandalone(destination: string, template: Template): void {\n // Update content.config.mjs paths (from ./posts to ./content/posts)\n const configPath = join(destination, 'content.config.mjs')\n if (existsSync(configPath)) {\n let config = readFileSync(configPath, 'utf-8')\n config = config.replace(/directory: '\\.\\/posts'/g, \"directory: './content/posts'\")\n config = config.replace(/directory: '\\.\\/pages'/g, \"directory: './content/pages'\")\n config = config.replace(/directory: '\\.\\/authors'/g, \"directory: './content/authors'\")\n config = config.replace(/directory: '\\.\\/config'/g, \"directory: './content/config'\")\n writeFileSync(configPath, config)\n }\n\n // Update vite.config.ts shared-content references\n const viteConfigPath = join(destination, 'vite.config.ts')\n if (existsSync(viteConfigPath)) {\n let config = readFileSync(viteConfigPath, 'utf-8')\n config = config.replace(\n /import content from '\\.\\.\\/shared-content\\/content\\.config'/g,\n \"import content from './content.config.mjs'\",\n )\n config = config.replace(\n /configPath:\\s*'\\.\\.\\/shared-content\\/content\\.config\\.ts'/g,\n \"configPath: './content.config.mjs'\",\n )\n config = config.replace(\n /root:\\s*resolve\\(import\\.meta\\.dirname,\\s*'\\.\\.\\/shared-content'\\)/g,\n 'root: import.meta.dirname',\n )\n writeFileSync(viteConfigPath, config)\n }\n\n // Update build.mjs (remove shared-content references)\n const buildPath = join(destination, 'build.mjs')\n if (existsSync(buildPath)) {\n let script = readFileSync(buildPath, 'utf-8')\n // Replace shared-content imports\n script = script.replace(\n /import .* from '\\.\\.\\/shared-content\\/content\\.config\\.mjs'/g,\n \"import content from './content.config.mjs'\",\n )\n // Simplify content layer setup\n script = script.replace(\n /const contentRoot = resolve\\(root, '\\.\\.\\/shared-content'\\)/g,\n 'const contentRoot = root',\n )\n // Fix named imports\n script = script.replace(\n /import \\{ pages, posts \\} from '\\.\\.\\/shared-content\\/content\\.config\\.mjs'/g,\n \"import content from './content.config.mjs'\\nconst { pages, posts } = content\",\n )\n writeFileSync(buildPath, script)\n }\n\n // Remove workspace-specific tsconfig paths\n const tsconfigPath = join(destination, 'tsconfig.json')\n if (existsSync(tsconfigPath)) {\n const tsconfig = JSON.parse(readFileSync(tsconfigPath, 'utf-8'))\n if (tsconfig.compilerOptions?.paths) {\n delete tsconfig.compilerOptions.paths\n }\n writeFileSync(tsconfigPath, JSON.stringify(tsconfig, null, 2) + '\\n')\n }\n}\n\nfunction writePackageJson(destination: string, projectName: string, template: Template): void {\n const existingPkg = join(destination, 'package.json')\n let pkg: Record<string, any> = {}\n\n if (existsSync(existingPkg)) {\n pkg = JSON.parse(readFileSync(existingPkg, 'utf-8'))\n }\n\n pkg.name = projectName\n pkg.private = true\n pkg.type = 'module'\n pkg.version = '0.0.0'\n pkg.scripts = template.scripts\n\n // Replace workspace \"*\" deps with actual versions\n if (pkg.dependencies) {\n for (const [name, version] of Object.entries(pkg.dependencies)) {\n if (version === '*' && name.startsWith('@pagesmith/')) {\n pkg.dependencies[name] = getPackageVersion()\n }\n }\n }\n\n // Ensure the primary dependency is present\n pkg.dependencies = pkg.dependencies ?? {}\n pkg.dependencies[template.dependency] = getPackageVersion()\n\n // Keep Vite+ in standalone examples that already use it\n if (pkg.devDependencies?.vite && !pkg.devDependencies['vite-plus']) {\n pkg.devDependencies['vite-plus'] = '^0.1.13'\n }\n\n try {\n const npmVersion = execFileSync('npm', ['--version'], { encoding: 'utf-8' }).trim()\n pkg.packageManager = `npm@${npmVersion}`\n } catch {\n // Omit packageManager if npm version cannot be detected\n }\n\n writeFileSync(existingPkg, JSON.stringify(pkg, null, 2) + '\\n')\n}\n\nexport async function createProject(projectName: string, templateName: string): Promise<void> {\n const template = templates.find((t) => t.name === templateName)\n if (!template) {\n throw new Error(`Unknown template \"${templateName}\". Available templates:\\n${listTemplates()}`)\n }\n\n const destination = resolve(projectName)\n if (existsSync(destination) && readdirSync(destination).length > 0) {\n throw new Error(`Directory \"${projectName}\" already exists and is not empty.`)\n }\n\n if (template.source === 'local') {\n const templateDir = resolve(\n import.meta.dirname,\n '../../templates',\n template.path.split('/').pop()!,\n )\n mkdirSync(destination, { recursive: true })\n cpSync(templateDir, destination, { recursive: true })\n } else {\n await downloadFromGithub(template.path, destination)\n adaptForStandalone(destination, template)\n }\n\n writePackageJson(destination, projectName, template)\n\n console.log(`\\nCreated \"${projectName}\" from the \"${template.name}\" template.\\n`)\n console.log('Next steps:')\n console.log(` cd ${projectName}`)\n console.log(' vp install')\n if (template.scripts.dev) {\n console.log(` vp run dev`)\n } else {\n console.log(` vp run build`)\n }\n console.log()\n}\n"],"mappings":"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"}
|
package/dist/css/index.mjs
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import { t as buildCss } from "../css-
|
|
1
|
+
import { t as buildCss } from "../css-CO3CBqxx.mjs";
|
|
2
2
|
export { buildCss };
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
import { resolve } from "path";
|
|
2
|
+
import { bundle } from "lightningcss";
|
|
3
|
+
//#region src/css/builder.ts
|
|
4
|
+
function buildCss(entryPath, config) {
|
|
5
|
+
const targets = config?.targets ?? {};
|
|
6
|
+
try {
|
|
7
|
+
const { code } = bundle({
|
|
8
|
+
filename: resolve(entryPath),
|
|
9
|
+
minify: config?.minify ?? true,
|
|
10
|
+
targets: {
|
|
11
|
+
chrome: (targets.chrome ?? 123) << 16,
|
|
12
|
+
firefox: (targets.firefox ?? 120) << 16,
|
|
13
|
+
safari: (targets.safari ?? 18) << 16
|
|
14
|
+
}
|
|
15
|
+
});
|
|
16
|
+
return new TextDecoder().decode(code);
|
|
17
|
+
} catch (err) {
|
|
18
|
+
throw new Error(`CSS build failed for ${entryPath}: ${err instanceof Error ? err.message : String(err)}`, { cause: err });
|
|
19
|
+
}
|
|
20
|
+
}
|
|
21
|
+
//#endregion
|
|
22
|
+
export { buildCss as t };
|
|
23
|
+
|
|
24
|
+
//# sourceMappingURL=css-CO3CBqxx.mjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"css-CO3CBqxx.mjs","names":[],"sources":["../src/css/builder.ts"],"sourcesContent":["import { bundle } from 'lightningcss'\nimport { resolve } from 'path'\n\nexport type CssBuildOptions = {\n minify?: boolean\n targets?: {\n chrome?: number\n firefox?: number\n safari?: number\n }\n}\n\nexport function buildCss(entryPath: string, config?: CssBuildOptions): string {\n const targets = config?.targets ?? {}\n try {\n const { code } = bundle({\n filename: resolve(entryPath),\n minify: config?.minify ?? true,\n targets: {\n chrome: (targets.chrome ?? 123) << 16,\n firefox: (targets.firefox ?? 120) << 16,\n safari: (targets.safari ?? 18) << 16,\n },\n })\n return new TextDecoder().decode(code)\n } catch (err) {\n throw new Error(\n `CSS build failed for ${entryPath}: ${err instanceof Error ? err.message : String(err)}`,\n { cause: err },\n )\n }\n}\n"],"mappings":";;;AAYA,SAAgB,SAAS,WAAmB,QAAkC;CAC5E,MAAM,UAAU,QAAQ,WAAW,EAAE;AACrC,KAAI;EACF,MAAM,EAAE,SAAS,OAAO;GACtB,UAAU,QAAQ,UAAU;GAC5B,QAAQ,QAAQ,UAAU;GAC1B,SAAS;IACP,SAAS,QAAQ,UAAU,QAAQ;IACnC,UAAU,QAAQ,WAAW,QAAQ;IACrC,SAAS,QAAQ,UAAU,OAAO;IACnC;GACF,CAAC;AACF,SAAO,IAAI,aAAa,CAAC,OAAO,KAAK;UAC9B,KAAK;AACZ,QAAM,IAAI,MACR,wBAAwB,UAAU,IAAI,eAAe,QAAQ,IAAI,UAAU,OAAO,IAAI,IACtF,EAAE,OAAO,KAAK,CACf"}
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import { z } from "zod";
|
|
2
|
+
|
|
3
|
+
//#region src/schemas/heading.d.ts
|
|
4
|
+
declare const HeadingSchema: z.ZodObject<{
|
|
5
|
+
depth: z.ZodNumber;
|
|
6
|
+
text: z.ZodString;
|
|
7
|
+
slug: z.ZodString;
|
|
8
|
+
}, z.core.$strip>;
|
|
9
|
+
type Heading = z.infer<typeof HeadingSchema>;
|
|
10
|
+
//#endregion
|
|
11
|
+
export { HeadingSchema as n, Heading as t };
|
|
12
|
+
//# sourceMappingURL=heading-D4X2L4vd.d.mts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"heading-D4X2L4vd.d.mts","names":[],"sources":["../src/schemas/heading.ts"],"mappings":";;;cAIa,aAAA,EAAa,CAAA,CAAA,SAAA;;;;;KAMd,OAAA,GAAU,CAAA,CAAE,KAAA,QAAa,aAAA"}
|
|
@@ -38,4 +38,4 @@ declare const BlogFrontmatterSchema: z.ZodObject<{
|
|
|
38
38
|
type BlogFrontmatter = z.infer<typeof BlogFrontmatterSchema>;
|
|
39
39
|
//#endregion
|
|
40
40
|
export { ProjectFrontmatter as a, BlogFrontmatterSchema as i, BaseFrontmatterSchema as n, ProjectFrontmatterSchema as o, BlogFrontmatter as r, BaseFrontmatter as t };
|
|
41
|
-
//# sourceMappingURL=index-
|
|
41
|
+
//# sourceMappingURL=index-B4YZRIzb.d.mts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index-
|
|
1
|
+
{"version":3,"file":"index-B4YZRIzb.d.mts","names":[],"sources":["../src/schemas/frontmatter.ts"],"mappings":";;;cAIa,qBAAA,EAAqB,CAAA,CAAA,SAAA;;;;;;;;KAWtB,eAAA,GAAkB,CAAA,CAAE,KAAA,QAAa,qBAAA;AAAA,cAIhC,wBAAA,EAAwB,CAAA,CAAA,SAAA;;;;;;;;;;;;;KAYzB,kBAAA,GAAqB,CAAA,CAAE,KAAA,QAAa,wBAAA;AAAA,cAInC,qBAAA,EAAqB,CAAA,CAAA,SAAA;;;;;;;;;;;KAMtB,eAAA,GAAkB,CAAA,CAAE,KAAA,QAAa,qBAAA"}
|
|
@@ -58,4 +58,4 @@ declare function resolveLoader(loaderOrType: LoaderType | Loader): Loader;
|
|
|
58
58
|
declare function defaultIncludePatterns(loader: Loader): string[];
|
|
59
59
|
//#endregion
|
|
60
60
|
export { TomlLoader as a, JsoncLoader as c, YamlLoader as i, JsonLoader as l, registerLoader as n, MarkdownLoader as o, resolveLoader as r, LoaderError as s, defaultIncludePatterns as t };
|
|
61
|
-
//# sourceMappingURL=index-
|
|
61
|
+
//# sourceMappingURL=index-CryArLlX.d.mts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index-
|
|
1
|
+
{"version":3,"file":"index-CryArLlX.d.mts","names":[],"sources":["../src/loaders/json.ts","../src/loaders/jsonc.ts","../src/loaders/errors.ts","../src/loaders/markdown.ts","../src/loaders/toml.ts","../src/loaders/yaml.ts","../src/loaders/index.ts"],"mappings":";;;cAWa,UAAA,YAAsB,MAAA;EACjC,IAAA;EACA,IAAA;EACA,UAAA;EAEM,IAAA,CAAK,QAAA,WAAmB,OAAA,CAAQ,YAAA;AAAA;;;cCoC3B,WAAA,YAAuB,MAAA;EAClC,IAAA;EACA,IAAA;EACA,UAAA;EAEM,IAAA,CAAK,QAAA,WAAmB,OAAA,CAAQ,YAAA;AAAA;;;cCzD3B,WAAA,SAAoB,KAAA;EAAA,SACtB,QAAA;EAAA,SACA,MAAA;EAAA,SACA,IAAA;EAAA,SACA,MAAA;cAEG,OAAA,UAAiB,QAAA,UAAkB,MAAA,UAAgB,IAAA,WAAe,MAAA;AAAA;;;cCOnE,cAAA,YAA0B,MAAA;EACrC,IAAA;EACA,IAAA;EACA,UAAA;EAEM,IAAA,CAAK,QAAA,WAAmB,OAAA,CAAQ,YAAA;AAAA;;;cCT3B,UAAA,YAAsB,MAAA;EACjC,IAAA;EACA,IAAA;EACA,UAAA;EAEM,IAAA,CAAK,QAAA,WAAmB,OAAA,CAAQ,YAAA;AAAA;;;cCL3B,UAAA,YAAsB,MAAA;EACjC,IAAA;EACA,IAAA;EACA,UAAA;EAEM,IAAA,CAAK,QAAA,WAAmB,OAAA,CAAQ,YAAA;AAAA;;;;iBCgBxB,cAAA,CAAe,IAAA,UAAc,MAAA,EAAQ,MAAA;;iBAKrC,aAAA,CAAc,YAAA,EAAc,UAAA,GAAa,MAAA,GAAS,MAAA;;iBAwBlD,sBAAA,CAAuB,MAAA,EAAQ,MAAA"}
|
|
@@ -1,4 +1,5 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { t as MarkdownConfig } from "./markdown-config-CDvh5aJ-.mjs";
|
|
2
|
+
import { t as Heading } from "./heading-D4X2L4vd.mjs";
|
|
2
3
|
|
|
3
4
|
//#region src/markdown/pipeline.d.ts
|
|
4
5
|
type MarkdownResult = {
|
|
@@ -12,4 +13,4 @@ declare function processMarkdown(raw: string, config?: MarkdownConfig, preExtrac
|
|
|
12
13
|
}): Promise<MarkdownResult>;
|
|
13
14
|
//#endregion
|
|
14
15
|
export { processMarkdown as n, MarkdownResult as t };
|
|
15
|
-
//# sourceMappingURL=index-
|
|
16
|
+
//# sourceMappingURL=index-D44syBt-.d.mts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index-D44syBt-.d.mts","names":[],"sources":["../src/markdown/pipeline.ts"],"mappings":";;;;KAuBY,cAAA;EACV,IAAA;EACA,QAAA,EAAU,OAAA;EACV,WAAA,EAAa,MAAA;AAAA;AAAA,iBA8JO,eAAA,CACpB,GAAA,UACA,MAAA,GAAS,cAAA,EACT,YAAA;EAAiB,OAAA;EAAiB,WAAA,EAAa,MAAA;AAAA,IAC9C,OAAA,CAAQ,cAAA"}
|
package/dist/index.d.mts
CHANGED
|
@@ -1,12 +1,13 @@
|
|
|
1
1
|
import { n as buildCss, t as CssBuildOptions } from "./index-B7NRZAxd.mjs";
|
|
2
2
|
import { n as LoaderResult, r as LoaderType, t as Loader } from "./types-B-V5qemH.mjs";
|
|
3
|
-
import { a as CollectionMap, c as RawEntry, d as ValidatorContext, f as ValidationEntryResult, i as CollectionDef, l as ContentValidator, m as ValidationResult, n as ContentPlugin, o as InferCollectionData, p as ValidationIssue, r as CollectionComputed, s as InferCollectionLoaderKind, t as ContentLayerConfig, u as ResolvedValidatorContext } from "./content-config-
|
|
4
|
-
import {
|
|
5
|
-
import {
|
|
3
|
+
import { a as CollectionMap, c as RawEntry, d as ValidatorContext, f as ValidationEntryResult, i as CollectionDef, l as ContentValidator, m as ValidationResult, n as ContentPlugin, o as InferCollectionData, p as ValidationIssue, r as CollectionComputed, s as InferCollectionLoaderKind, t as ContentLayerConfig, u as ResolvedValidatorContext } from "./content-config-Bu2HH0Yx.mjs";
|
|
4
|
+
import { n as MarkdownConfigSchema, t as MarkdownConfig } from "./markdown-config-CDvh5aJ-.mjs";
|
|
5
|
+
import { n as HeadingSchema, t as Heading } from "./heading-D4X2L4vd.mjs";
|
|
6
|
+
import { _ as ConvertResult, a as WatchEvent, c as builtinMarkdownValidators, d as linkValidator, f as headingValidator, g as ConvertOptions, h as RenderedContent, i as WatchCallback, l as runValidators, m as ContentEntry, n as LayerConvertOptions, o as WatchHandle, p as codeBlockValidator, r as TypedContentLayer, s as createContentLayer, t as ContentLayer, u as createLinkValidator, v as convert } from "./content-layer-Ckt08g2i.mjs";
|
|
6
7
|
import { Fragment, HtmlString, h } from "./jsx-runtime/index.mjs";
|
|
7
|
-
import { n as processMarkdown, t as MarkdownResult } from "./index-
|
|
8
|
-
import { a as ProjectFrontmatter, i as BlogFrontmatterSchema, n as BaseFrontmatterSchema, o as ProjectFrontmatterSchema, r as BlogFrontmatter, t as BaseFrontmatter } from "./index-
|
|
9
|
-
import { a as TomlLoader, c as JsoncLoader, i as YamlLoader, l as JsonLoader, n as registerLoader, o as MarkdownLoader } from "./index-
|
|
8
|
+
import { n as processMarkdown, t as MarkdownResult } from "./index-D44syBt-.mjs";
|
|
9
|
+
import { a as ProjectFrontmatter, i as BlogFrontmatterSchema, n as BaseFrontmatterSchema, o as ProjectFrontmatterSchema, r as BlogFrontmatter, t as BaseFrontmatter } from "./index-B4YZRIzb.mjs";
|
|
10
|
+
import { a as TomlLoader, c as JsoncLoader, i as YamlLoader, l as JsonLoader, n as registerLoader, o as MarkdownLoader } from "./index-CryArLlX.mjs";
|
|
10
11
|
import { ZodSchema, z, z as z$1 } from "zod";
|
|
11
12
|
|
|
12
13
|
//#region src/config.d.ts
|
package/dist/index.d.mts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.mts","names":[],"sources":["../src/config.ts","../src/frontmatter.ts","../src/toc.ts"],"mappings":"
|
|
1
|
+
{"version":3,"file":"index.d.mts","names":[],"sources":["../src/config.ts","../src/frontmatter.ts","../src/toc.ts"],"mappings":";;;;;;;;;;;;;;iBAagB,YAAA,CAAa,MAAA,EAAQ,kBAAA,GAAqB,kBAAA;;iBAK1C,gBAAA,iBACE,GAAA,CAAE,OAAA,0BACM,kBAAA,6BACF,UAAA,GAAa,MAAA,GAAS,UAAA,GAAa,MAAA,CAAA,CAEzD,GAAA,EAAK,IAAA,CAAK,aAAA,CAAc,CAAA,EAAG,SAAA,EAAW,OAAA;EACpC,QAAA,GAAW,SAAA,GAAY,kBAAA;AAAA,IAExB,aAAA,CAAc,CAAA,EAAG,SAAA,EAAW,OAAA;;iBAKf,iBAAA,4BAA6C,aAAA,CAAA,CAC3D,WAAA,EAAa,YAAA,GACZ,YAAA;;;KCrBS,iBAAA;EACV,WAAA,EAAa,MAAA;EACb,OAAA;AAAA;;iBAIc,kBAAA,CAAmB,GAAA,WAAc,iBAAA;ADLjD;;;;;;AAAA,iBCgBgB,mBAAA,GAAA,CACd,WAAA,EAAa,MAAA,eACb,MAAA,EAAQ,SAAA,CAAU,CAAA;EACf,OAAA;EAAe,IAAA,EAAM,CAAA;AAAA;EAAQ,OAAA;EAAgB,MAAA;AAAA;;;;;;;;;iBCxBlC,UAAA,CAAW,IAAA,WAAe,OAAA"}
|
package/dist/index.mjs
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
|
-
import { t as processMarkdown } from "./markdown-
|
|
2
|
-
import { a as linkValidator, c as validateSchema, d as convert, i as createLinkValidator, n as builtinMarkdownValidators, o as headingValidator, r as runValidators, s as codeBlockValidator, t as createContentLayer, u as ContentEntry } from "./content-layer-
|
|
3
|
-
import { a as TomlLoader, c as JsonLoader, i as YamlLoader, n as registerLoader, o as MarkdownLoader, s as JsoncLoader } from "./loaders-
|
|
1
|
+
import { t as processMarkdown } from "./markdown-DMHd400a.mjs";
|
|
2
|
+
import { a as linkValidator, c as validateSchema, d as convert, i as createLinkValidator, n as builtinMarkdownValidators, o as headingValidator, r as runValidators, s as codeBlockValidator, t as createContentLayer, u as ContentEntry } from "./content-layer-CJRrNpZ_.mjs";
|
|
3
|
+
import { a as TomlLoader, c as JsonLoader, i as YamlLoader, n as registerLoader, o as MarkdownLoader, s as JsoncLoader } from "./loaders-DnyWfANR.mjs";
|
|
4
4
|
import { Fragment, HtmlString, h } from "./jsx-runtime/index.mjs";
|
|
5
|
-
import { t as buildCss } from "./css-
|
|
5
|
+
import { t as buildCss } from "./css-CO3CBqxx.mjs";
|
|
6
6
|
import { a as ProjectFrontmatterSchema, i as BlogFrontmatterSchema, n as HeadingSchema, r as BaseFrontmatterSchema, t as MarkdownConfigSchema } from "./schemas-UL4ynWsA.mjs";
|
|
7
7
|
import matter from "gray-matter";
|
|
8
8
|
import { parse } from "yaml";
|
package/dist/loaders/index.d.mts
CHANGED
|
@@ -1,3 +1,3 @@
|
|
|
1
1
|
import { n as LoaderResult, r as LoaderType, t as Loader } from "../types-B-V5qemH.mjs";
|
|
2
|
-
import { a as TomlLoader, c as JsoncLoader, i as YamlLoader, l as JsonLoader, n as registerLoader, o as MarkdownLoader, r as resolveLoader, s as LoaderError, t as defaultIncludePatterns } from "../index-
|
|
2
|
+
import { a as TomlLoader, c as JsoncLoader, i as YamlLoader, l as JsonLoader, n as registerLoader, o as MarkdownLoader, r as resolveLoader, s as LoaderError, t as defaultIncludePatterns } from "../index-CryArLlX.mjs";
|
|
3
3
|
export { JsonLoader, JsoncLoader, Loader, LoaderError, LoaderResult, LoaderType, MarkdownLoader, TomlLoader, YamlLoader, defaultIncludePatterns, registerLoader, resolveLoader };
|
package/dist/loaders/index.mjs
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import { a as TomlLoader, c as JsonLoader, i as YamlLoader, l as LoaderError, n as registerLoader, o as MarkdownLoader, r as resolveLoader, s as JsoncLoader, t as defaultIncludePatterns } from "../loaders-
|
|
1
|
+
import { a as TomlLoader, c as JsonLoader, i as YamlLoader, l as LoaderError, n as registerLoader, o as MarkdownLoader, r as resolveLoader, s as JsoncLoader, t as defaultIncludePatterns } from "../loaders-DnyWfANR.mjs";
|
|
2
2
|
export { JsonLoader, JsoncLoader, LoaderError, MarkdownLoader, TomlLoader, YamlLoader, defaultIncludePatterns, registerLoader, resolveLoader };
|
|
@@ -86,8 +86,8 @@ var JsoncLoader = class {
|
|
|
86
86
|
async load(filePath) {
|
|
87
87
|
const raw = await readFile(filePath, "utf-8");
|
|
88
88
|
try {
|
|
89
|
-
const
|
|
90
|
-
return { data: JSON.parse(
|
|
89
|
+
const withoutTrailingCommas = stripComments(raw).replace(/,\s*([}\]])/g, "$1");
|
|
90
|
+
return { data: JSON.parse(withoutTrailingCommas) };
|
|
91
91
|
} catch (err) {
|
|
92
92
|
throw new LoaderError(err instanceof Error ? err.message : String(err), filePath, "JSONC");
|
|
93
93
|
}
|
|
@@ -190,4 +190,4 @@ function defaultIncludePatterns(loader) {
|
|
|
190
190
|
//#endregion
|
|
191
191
|
export { TomlLoader as a, JsonLoader as c, YamlLoader as i, LoaderError as l, registerLoader as n, MarkdownLoader as o, resolveLoader as r, JsoncLoader as s, defaultIncludePatterns as t };
|
|
192
192
|
|
|
193
|
-
//# sourceMappingURL=loaders-
|
|
193
|
+
//# sourceMappingURL=loaders-DnyWfANR.mjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"loaders-DnyWfANR.mjs","names":["parseYaml","parse"],"sources":["../src/loaders/errors.ts","../src/loaders/json.ts","../src/loaders/jsonc.ts","../src/loaders/markdown.ts","../src/loaders/toml.ts","../src/loaders/yaml.ts","../src/loaders/index.ts"],"sourcesContent":["export class LoaderError extends Error {\n readonly filePath: string\n readonly format: string\n readonly line?: number\n readonly column?: number\n\n constructor(message: string, filePath: string, format: string, line?: number, column?: number) {\n super(`${format} parse error in ${filePath}${line ? `:${line}` : ''}: ${message}`)\n this.name = 'LoaderError'\n this.filePath = filePath\n this.format = format\n this.line = line\n this.column = column\n }\n}\n","/**\n * JSON / JSON5 / JSONC loader.\n *\n * Detects format from file extension and parses accordingly.\n */\n\nimport { readFile } from 'fs/promises'\nimport JSON5 from 'json5'\nimport { LoaderError } from './errors'\nimport type { Loader, LoaderResult } from './types'\n\nexport class JsonLoader implements Loader {\n name = 'json'\n kind = 'data' as const\n extensions = ['.json', '.json5']\n\n async load(filePath: string): Promise<LoaderResult> {\n const raw = await readFile(filePath, 'utf-8')\n const isJson = filePath.endsWith('.json')\n\n try {\n const data = isJson ? JSON.parse(raw) : JSON5.parse(raw)\n return { data }\n } catch (err) {\n const message = err instanceof Error ? err.message : String(err)\n throw new LoaderError(message, filePath, isJson ? 'JSON' : 'JSON5')\n }\n }\n}\n","/**\n * JSONC loader — JSON with Comments.\n *\n * Strips single-line (//) and multi-line comments before parsing.\n * Delegates to JSON.parse after stripping (no JSON5 superset features).\n */\n\nimport { readFile } from 'fs/promises'\nimport { LoaderError } from './errors'\nimport type { Loader, LoaderResult } from './types'\n\n/** Strip // and block comments, preserving strings. */\nfunction stripComments(raw: string): string {\n let result = ''\n let i = 0\n const len = raw.length\n\n while (i < len) {\n // String literal — copy verbatim to preserve contents\n if (raw[i] === '\"') {\n let end = i + 1\n while (end < len && raw[end] !== '\"') {\n if (raw[end] === '\\\\') end++ // skip escaped char\n end++\n }\n result += raw.slice(i, end + 1)\n i = end + 1\n continue\n }\n\n // Single-line comment\n if (raw[i] === '/' && raw[i + 1] === '/') {\n i += 2\n while (i < len && raw[i] !== '\\n') i++\n continue\n }\n\n // Block comment\n if (raw[i] === '/' && raw[i + 1] === '*') {\n i += 2\n while (i < len && !(raw[i] === '*' && raw[i + 1] === '/')) i++\n i += 2 // skip closing */\n continue\n }\n\n result += raw[i]\n i++\n }\n\n return result\n}\n\nexport class JsoncLoader implements Loader {\n name = 'jsonc'\n kind = 'data' as const\n extensions = ['.jsonc']\n\n async load(filePath: string): Promise<LoaderResult> {\n const raw = await readFile(filePath, 'utf-8')\n try {\n const stripped = stripComments(raw)\n const withoutTrailingCommas = stripped.replace(/,\\s*([}\\]])/g, '$1')\n const data = JSON.parse(withoutTrailingCommas)\n return { data }\n } catch (err) {\n const message = err instanceof Error ? err.message : String(err)\n throw new LoaderError(message, filePath, 'JSONC')\n }\n }\n}\n","/**\n * Markdown loader.\n *\n * Uses gray-matter to extract YAML frontmatter and body content.\n * Rendering is NOT done here — it's deferred to ContentEntry.render().\n */\n\nimport { readFile } from 'fs/promises'\nimport matter from 'gray-matter'\nimport { parse as parseYaml } from 'yaml'\nimport { LoaderError } from './errors'\nimport type { Loader, LoaderResult } from './types'\n\nexport class MarkdownLoader implements Loader {\n name = 'markdown'\n kind = 'markdown' as const\n extensions = ['.md']\n\n async load(filePath: string): Promise<LoaderResult> {\n const raw = await readFile(filePath, 'utf-8')\n try {\n const { data, content } = matter(raw, { engines: { yaml: parseYaml } })\n return { data, content }\n } catch (err) {\n const message = err instanceof Error ? err.message : String(err)\n throw new LoaderError(message, filePath, 'Markdown')\n }\n }\n}\n","/**\n * TOML loader.\n */\n\nimport { readFile } from 'fs/promises'\nimport { parse } from 'smol-toml'\nimport { LoaderError } from './errors'\nimport type { Loader, LoaderResult } from './types'\n\nexport class TomlLoader implements Loader {\n name = 'toml'\n kind = 'data' as const\n extensions = ['.toml']\n\n async load(filePath: string): Promise<LoaderResult> {\n const raw = await readFile(filePath, 'utf-8')\n try {\n const data = parse(raw)\n return { data }\n } catch (err) {\n const message = err instanceof Error ? err.message : String(err)\n throw new LoaderError(message, filePath, 'TOML')\n }\n }\n}\n","/**\n * YAML loader.\n */\n\nimport { readFile } from 'fs/promises'\nimport { parse } from 'yaml'\nimport { LoaderError } from './errors'\nimport type { Loader, LoaderResult } from './types'\n\nexport class YamlLoader implements Loader {\n name = 'yaml'\n kind = 'data' as const\n extensions = ['.yaml', '.yml']\n\n async load(filePath: string): Promise<LoaderResult> {\n const raw = await readFile(filePath, 'utf-8')\n try {\n const data = parse(raw) ?? {}\n return { data }\n } catch (err) {\n const message = err instanceof Error ? err.message : String(err)\n const line =\n err != null && typeof err === 'object' && 'linePos' in err\n ? (err as any).linePos?.[0]?.line\n : undefined\n throw new LoaderError(message, filePath, 'YAML', line)\n }\n }\n}\n","/**\n * Loader registry — resolves loader type strings to Loader instances.\n */\n\nexport { JsonLoader } from './json'\nexport { JsoncLoader } from './jsonc'\nexport { LoaderError } from './errors'\nexport { MarkdownLoader } from './markdown'\nexport { TomlLoader } from './toml'\nexport type { Loader, LoaderResult, LoaderType } from './types'\nexport { YamlLoader } from './yaml'\n\nimport { JsonLoader } from './json'\nimport { JsoncLoader } from './jsonc'\nimport { MarkdownLoader } from './markdown'\nimport { TomlLoader } from './toml'\nimport type { Loader, LoaderType } from './types'\nimport { YamlLoader } from './yaml'\n\n/** Singleton loader instances (loaders are stateless). */\nconst markdownLoader = new MarkdownLoader()\nconst jsonLoader = new JsonLoader()\nconst jsoncLoader = new JsoncLoader()\nconst yamlLoader = new YamlLoader()\nconst tomlLoader = new TomlLoader()\n\n/** Custom loader registry for user-registered loaders. */\nconst customLoaders = new Map<string, Loader>()\n\n/** Register a custom loader by name. */\nexport function registerLoader(name: string, loader: Loader): void {\n customLoaders.set(name, loader)\n}\n\n/** Resolve a loader type string or custom Loader instance. */\nexport function resolveLoader(loaderOrType: LoaderType | Loader): Loader {\n if (typeof loaderOrType === 'object') return loaderOrType\n\n const custom = customLoaders.get(loaderOrType)\n if (custom) return custom\n\n switch (loaderOrType) {\n case 'markdown':\n return markdownLoader\n case 'json':\n case 'json5':\n return jsonLoader\n case 'jsonc':\n return jsoncLoader\n case 'yaml':\n return yamlLoader\n case 'toml':\n return tomlLoader\n default:\n throw new Error(`Unknown loader type: ${loaderOrType as string}`)\n }\n}\n\n/** Get default include glob patterns for a loader. */\nexport function defaultIncludePatterns(loader: Loader): string[] {\n return loader.extensions.map((ext) => `**/*${ext}`)\n}\n"],"mappings":"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"}
|
|
@@ -1,3 +1,3 @@
|
|
|
1
|
-
import {
|
|
2
|
-
import { n as processMarkdown, t as MarkdownResult } from "../index-
|
|
1
|
+
import { t as MarkdownConfig } from "../markdown-config-CDvh5aJ-.mjs";
|
|
2
|
+
import { n as processMarkdown, t as MarkdownResult } from "../index-D44syBt-.mjs";
|
|
3
3
|
export { MarkdownConfig, MarkdownResult, processMarkdown };
|
package/dist/markdown/index.mjs
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import { t as processMarkdown } from "../markdown-
|
|
1
|
+
import { t as processMarkdown } from "../markdown-DMHd400a.mjs";
|
|
2
2
|
export { processMarkdown };
|
|
@@ -108,6 +108,11 @@ function createProcessor(config) {
|
|
|
108
108
|
* Pass a new config object — a fresh reference gets its own cache entry.
|
|
109
109
|
* For example: `processMarkdown(md, { ...existingConfig, remarkPlugins: [...] })`.
|
|
110
110
|
*/
|
|
111
|
+
function deepFreeze(obj) {
|
|
112
|
+
Object.freeze(obj);
|
|
113
|
+
for (const value of Object.values(obj)) if (value && typeof value === "object" && !Object.isFrozen(value)) deepFreeze(value);
|
|
114
|
+
return obj;
|
|
115
|
+
}
|
|
111
116
|
const processorCache = /* @__PURE__ */ new WeakMap();
|
|
112
117
|
async function processMarkdown(raw, config, preExtracted) {
|
|
113
118
|
let frontmatter;
|
|
@@ -121,7 +126,7 @@ async function processMarkdown(raw, config, preExtracted) {
|
|
|
121
126
|
content = parsed.content;
|
|
122
127
|
}
|
|
123
128
|
const resolvedConfig = config && Object.keys(config).length > 0 ? config : DEFAULT_MARKDOWN_CONFIG;
|
|
124
|
-
if (Object.isFrozen(resolvedConfig) === false)
|
|
129
|
+
if (Object.isFrozen(resolvedConfig) === false) deepFreeze(resolvedConfig);
|
|
125
130
|
let processor = processorCache.get(resolvedConfig);
|
|
126
131
|
if (!processor) {
|
|
127
132
|
processor = createProcessor(resolvedConfig);
|
|
@@ -142,4 +147,4 @@ async function processMarkdown(raw, config, preExtracted) {
|
|
|
142
147
|
//#endregion
|
|
143
148
|
export { processMarkdown as t };
|
|
144
149
|
|
|
145
|
-
//# sourceMappingURL=markdown-
|
|
150
|
+
//# sourceMappingURL=markdown-DMHd400a.mjs.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"markdown-BmDJgYeB.mjs","names":["parseYaml"],"sources":["../src/markdown/pipeline.ts"],"sourcesContent":["import matter from 'gray-matter'\nimport { parse as parseYaml } from 'yaml'\nimport { rehypeAccessibleEmojis } from 'rehype-accessible-emojis'\nimport rehypeAutolinkHeadings from 'rehype-autolink-headings'\nimport rehypeExpressiveCode, {\n type BundledShikiTheme,\n type RehypeExpressiveCodeOptions,\n} from 'rehype-expressive-code'\nimport rehypeExternalLinks from 'rehype-external-links'\nimport rehypeMathjax from 'rehype-mathjax/svg'\nimport rehypeSlug from 'rehype-slug'\nimport rehypeStringify from 'rehype-stringify'\nimport remarkFrontmatter from 'remark-frontmatter'\nimport remarkGfm from 'remark-gfm'\nimport remarkGithubAlerts from 'remark-github-alerts'\nimport remarkMath from 'remark-math'\nimport remarkParse from 'remark-parse'\nimport remarkRehype from 'remark-rehype'\nimport remarkSmartypants from 'remark-smartypants'\nimport { unified } from 'unified'\nimport type { Heading } from '../schemas/heading'\nimport type { MarkdownConfig } from '../schemas/markdown-config'\n\nexport type MarkdownResult = {\n html: string\n headings: Heading[]\n frontmatter: Record<string, unknown>\n}\n\nexport type { MarkdownConfig }\n\nconst DEFAULT_MARKDOWN_CONFIG: MarkdownConfig = {}\n\n/** Default language aliases for fenced code blocks that Shiki doesn't recognize natively. */\nconst DEFAULT_LANG_ALIASES: Record<string, string> = {\n dot: 'text',\n mermaid: 'text',\n plantuml: 'text',\n excalidraw: 'json',\n drawio: 'xml',\n proto: 'protobuf',\n ejs: 'html',\n hbs: 'handlebars',\n}\n\nfunction getTextContent(node: any): string {\n if (node.type === 'text') return node.value || ''\n if (node.children) return node.children.map(getTextContent).join('')\n return ''\n}\n\nfunction extractHeadings(tree: any, headings: Heading[]): void {\n if (tree.type === 'element' && /^h[1-6]$/.test(tree.tagName)) {\n headings.push({\n depth: parseInt(tree.tagName[1]),\n text: getTextContent(tree),\n slug: tree.properties?.id || '',\n })\n }\n if (tree.children) {\n for (const child of tree.children) {\n extractHeadings(child, headings)\n }\n }\n}\n\nfunction createProcessor(config: MarkdownConfig) {\n const processor = unified()\n .use(remarkParse)\n .use(remarkGfm)\n .use(remarkMath)\n .use(remarkFrontmatter, ['yaml'])\n // GitHub-flavored alerts: > [!NOTE], > [!TIP], > [!IMPORTANT], > [!WARNING], > [!CAUTION]\n .use(remarkGithubAlerts)\n // Smart typography: \"smart quotes\", em—dashes, el…lipses\n .use(remarkSmartypants)\n\n if (config.remarkPlugins) {\n for (const plugin of config.remarkPlugins) {\n if (Array.isArray(plugin)) processor.use(plugin[0], plugin[1])\n else processor.use(plugin)\n }\n }\n\n // Apply language aliases to fenced code blocks before Expressive Code processes them.\n // Merge defaults with user-provided aliases (user overrides take precedence).\n const langAlias = { ...DEFAULT_LANG_ALIASES, ...config.shiki?.langAlias }\n processor.use(() => (tree: any) => {\n const visit = (node: any): void => {\n if (node?.type === 'code' && typeof node.lang === 'string' && langAlias[node.lang]) {\n node.lang = langAlias[node.lang]\n }\n if (Array.isArray(node?.children)) {\n for (const child of node.children) visit(child)\n }\n }\n visit(tree)\n })\n\n processor.use(remarkRehype, { allowDangerousHtml: true })\n\n // MathJax must run before Expressive Code so that math elements (from remark-math)\n // are rendered to SVG before Expressive Code tries to highlight them as code blocks.\n processor.use(rehypeMathjax)\n\n // Expressive Code — syntax highlighting, code frames, tabs, copy button\n const lightTheme = (config.shiki?.themes?.light || 'github-light') as BundledShikiTheme\n const darkTheme = (config.shiki?.themes?.dark || 'github-dark') as BundledShikiTheme\n\n processor.use(rehypeExpressiveCode, {\n themes: [darkTheme, lightTheme],\n useDarkModeMediaQuery: true,\n styleOverrides: {\n uiFontFamily: 'var(--ps-font-sans, var(--font-family, system-ui, sans-serif))',\n codeFontFamily: 'var(--ps-font-mono, var(--font-mono, ui-monospace, monospace))',\n codeFontSize: 'var(--ps-font-size-sm, 0.875rem)',\n codeLineHeight: '1.7',\n borderRadius: 'var(--ps-radius-lg, 0.5rem)',\n borderColor: 'var(--ps-color-border-subtle, var(--color-border-subtle, #e5e7eb))',\n },\n } satisfies RehypeExpressiveCodeOptions)\n\n processor\n .use(rehypeSlug)\n .use(rehypeAutolinkHeadings, { behavior: 'wrap' })\n // External links: add target=\"_blank\" rel=\"noopener noreferrer\" to absolute URLs\n .use(rehypeExternalLinks, {\n target: '_blank',\n rel: ['noopener', 'noreferrer'],\n })\n // Accessible emojis: wrap emoji characters in <span role=\"img\" aria-label=\"...\">\n .use(rehypeAccessibleEmojis)\n\n processor.use(() => (tree: any, file: any) => {\n const headings: Heading[] = []\n extractHeadings(tree, headings)\n file.data.headings = headings\n })\n\n if (config.rehypePlugins) {\n for (const plugin of config.rehypePlugins) {\n if (Array.isArray(plugin)) processor.use(plugin[0], plugin[1])\n else processor.use(plugin)\n }\n }\n\n processor.use(rehypeStringify, { allowDangerousHtml: true })\n return processor\n}\n\n/**\n * Processor cache keyed by MarkdownConfig object reference.\n *\n * **Why a WeakMap keyed by object reference?**\n * Building a unified processor chain is expensive — it loads Shiki grammars,\n * theme JSON, and instantiates every remark/rehype plugin. Caching the\n * processor by config reference lets callers that reuse the same config object\n * (the common case) skip all of that setup on subsequent calls. The WeakMap\n * also ensures that if a config object is garbage-collected, its processor is\n * too, so long-running processes don't leak memory.\n *\n * **Why is the config frozen?**\n * The cache assumes the config does not change after the processor is built.\n * If a caller mutated a config object after the processor was created, later\n * calls would still receive the stale processor (keyed by the same reference),\n * producing silently wrong output. Freezing the config at first use turns that\n * silent bug into a loud TypeError on any attempted mutation.\n *\n * **What if a consumer needs different settings?**\n * Pass a new config object — a fresh reference gets its own cache entry.\n * For example: `processMarkdown(md, { ...existingConfig, remarkPlugins: [...] })`.\n */\nconst processorCache = new WeakMap<MarkdownConfig, ReturnType<typeof createProcessor>>()\n\nexport async function processMarkdown(\n raw: string,\n config?: MarkdownConfig,\n preExtracted?: { content: string; frontmatter: Record<string, unknown> },\n): Promise<MarkdownResult> {\n let frontmatter: Record<string, unknown>\n let content: string\n if (preExtracted) {\n frontmatter = preExtracted.frontmatter\n content = preExtracted.content\n } else {\n const parsed = matter(raw, { engines: { yaml: parseYaml } })\n frontmatter = parsed.data\n content = parsed.content\n }\n const resolvedConfig = config && Object.keys(config).length > 0 ? config : DEFAULT_MARKDOWN_CONFIG\n // Freeze to prevent mutation after caching — see processorCache JSDoc above.\n if (Object.isFrozen(resolvedConfig) === false) Object.freeze(resolvedConfig)\n let processor = processorCache.get(resolvedConfig)\n if (!processor) {\n processor = createProcessor(resolvedConfig)\n processorCache.set(resolvedConfig, processor)\n }\n try {\n const result = await processor.process(content)\n const headings = Array.isArray(result.data.headings) ? (result.data.headings as Heading[]) : []\n return { html: String(result), headings, frontmatter }\n } catch (err) {\n throw new Error(\n `Markdown processing failed: ${err instanceof Error ? err.message : String(err)}`,\n { cause: err },\n )\n }\n}\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"markdown-DMHd400a.mjs","names":["parseYaml"],"sources":["../src/markdown/pipeline.ts"],"sourcesContent":["import matter from 'gray-matter'\nimport { parse as parseYaml } from 'yaml'\nimport { rehypeAccessibleEmojis } from 'rehype-accessible-emojis'\nimport rehypeAutolinkHeadings from 'rehype-autolink-headings'\nimport rehypeExpressiveCode, {\n type BundledShikiTheme,\n type RehypeExpressiveCodeOptions,\n} from 'rehype-expressive-code'\nimport rehypeExternalLinks from 'rehype-external-links'\nimport rehypeMathjax from 'rehype-mathjax/svg'\nimport rehypeSlug from 'rehype-slug'\nimport rehypeStringify from 'rehype-stringify'\nimport remarkFrontmatter from 'remark-frontmatter'\nimport remarkGfm from 'remark-gfm'\nimport remarkGithubAlerts from 'remark-github-alerts'\nimport remarkMath from 'remark-math'\nimport remarkParse from 'remark-parse'\nimport remarkRehype from 'remark-rehype'\nimport remarkSmartypants from 'remark-smartypants'\nimport { unified } from 'unified'\nimport type { Heading } from '../schemas/heading'\nimport type { MarkdownConfig } from '../schemas/markdown-config'\n\nexport type MarkdownResult = {\n html: string\n headings: Heading[]\n frontmatter: Record<string, unknown>\n}\n\nexport type { MarkdownConfig }\n\nconst DEFAULT_MARKDOWN_CONFIG: MarkdownConfig = {}\n\n/** Default language aliases for fenced code blocks that Shiki doesn't recognize natively. */\nconst DEFAULT_LANG_ALIASES: Record<string, string> = {\n dot: 'text',\n mermaid: 'text',\n plantuml: 'text',\n excalidraw: 'json',\n drawio: 'xml',\n proto: 'protobuf',\n ejs: 'html',\n hbs: 'handlebars',\n}\n\nfunction getTextContent(node: any): string {\n if (node.type === 'text') return node.value || ''\n if (node.children) return node.children.map(getTextContent).join('')\n return ''\n}\n\nfunction extractHeadings(tree: any, headings: Heading[]): void {\n if (tree.type === 'element' && /^h[1-6]$/.test(tree.tagName)) {\n headings.push({\n depth: parseInt(tree.tagName[1]),\n text: getTextContent(tree),\n slug: tree.properties?.id || '',\n })\n }\n if (tree.children) {\n for (const child of tree.children) {\n extractHeadings(child, headings)\n }\n }\n}\n\nfunction createProcessor(config: MarkdownConfig) {\n const processor = unified()\n .use(remarkParse)\n .use(remarkGfm)\n .use(remarkMath)\n .use(remarkFrontmatter, ['yaml'])\n // GitHub-flavored alerts: > [!NOTE], > [!TIP], > [!IMPORTANT], > [!WARNING], > [!CAUTION]\n .use(remarkGithubAlerts)\n // Smart typography: \"smart quotes\", em—dashes, el…lipses\n .use(remarkSmartypants)\n\n if (config.remarkPlugins) {\n for (const plugin of config.remarkPlugins) {\n if (Array.isArray(plugin)) processor.use(plugin[0], plugin[1])\n else processor.use(plugin)\n }\n }\n\n // Apply language aliases to fenced code blocks before Expressive Code processes them.\n // Merge defaults with user-provided aliases (user overrides take precedence).\n const langAlias = { ...DEFAULT_LANG_ALIASES, ...config.shiki?.langAlias }\n processor.use(() => (tree: any) => {\n const visit = (node: any): void => {\n if (node?.type === 'code' && typeof node.lang === 'string' && langAlias[node.lang]) {\n node.lang = langAlias[node.lang]\n }\n if (Array.isArray(node?.children)) {\n for (const child of node.children) visit(child)\n }\n }\n visit(tree)\n })\n\n processor.use(remarkRehype, { allowDangerousHtml: true })\n\n // MathJax must run before Expressive Code so that math elements (from remark-math)\n // are rendered to SVG before Expressive Code tries to highlight them as code blocks.\n processor.use(rehypeMathjax)\n\n // Expressive Code — syntax highlighting, code frames, tabs, copy button\n const lightTheme = (config.shiki?.themes?.light || 'github-light') as BundledShikiTheme\n const darkTheme = (config.shiki?.themes?.dark || 'github-dark') as BundledShikiTheme\n\n processor.use(rehypeExpressiveCode, {\n themes: [darkTheme, lightTheme],\n useDarkModeMediaQuery: true,\n styleOverrides: {\n uiFontFamily: 'var(--ps-font-sans, var(--font-family, system-ui, sans-serif))',\n codeFontFamily: 'var(--ps-font-mono, var(--font-mono, ui-monospace, monospace))',\n codeFontSize: 'var(--ps-font-size-sm, 0.875rem)',\n codeLineHeight: '1.7',\n borderRadius: 'var(--ps-radius-lg, 0.5rem)',\n borderColor: 'var(--ps-color-border-subtle, var(--color-border-subtle, #e5e7eb))',\n },\n } satisfies RehypeExpressiveCodeOptions)\n\n processor\n .use(rehypeSlug)\n .use(rehypeAutolinkHeadings, { behavior: 'wrap' })\n // External links: add target=\"_blank\" rel=\"noopener noreferrer\" to absolute URLs\n .use(rehypeExternalLinks, {\n target: '_blank',\n rel: ['noopener', 'noreferrer'],\n })\n // Accessible emojis: wrap emoji characters in <span role=\"img\" aria-label=\"...\">\n .use(rehypeAccessibleEmojis)\n\n processor.use(() => (tree: any, file: any) => {\n const headings: Heading[] = []\n extractHeadings(tree, headings)\n file.data.headings = headings\n })\n\n if (config.rehypePlugins) {\n for (const plugin of config.rehypePlugins) {\n if (Array.isArray(plugin)) processor.use(plugin[0], plugin[1])\n else processor.use(plugin)\n }\n }\n\n processor.use(rehypeStringify, { allowDangerousHtml: true })\n return processor\n}\n\n/**\n * Processor cache keyed by MarkdownConfig object reference.\n *\n * **Why a WeakMap keyed by object reference?**\n * Building a unified processor chain is expensive — it loads Shiki grammars,\n * theme JSON, and instantiates every remark/rehype plugin. Caching the\n * processor by config reference lets callers that reuse the same config object\n * (the common case) skip all of that setup on subsequent calls. The WeakMap\n * also ensures that if a config object is garbage-collected, its processor is\n * too, so long-running processes don't leak memory.\n *\n * **Why is the config frozen?**\n * The cache assumes the config does not change after the processor is built.\n * If a caller mutated a config object after the processor was created, later\n * calls would still receive the stale processor (keyed by the same reference),\n * producing silently wrong output. Freezing the config at first use turns that\n * silent bug into a loud TypeError on any attempted mutation.\n *\n * **What if a consumer needs different settings?**\n * Pass a new config object — a fresh reference gets its own cache entry.\n * For example: `processMarkdown(md, { ...existingConfig, remarkPlugins: [...] })`.\n */\nfunction deepFreeze<T extends object>(obj: T): T {\n Object.freeze(obj)\n for (const value of Object.values(obj)) {\n if (value && typeof value === 'object' && !Object.isFrozen(value)) {\n deepFreeze(value)\n }\n }\n return obj\n}\n\nconst processorCache = new WeakMap<MarkdownConfig, ReturnType<typeof createProcessor>>()\n\nexport async function processMarkdown(\n raw: string,\n config?: MarkdownConfig,\n preExtracted?: { content: string; frontmatter: Record<string, unknown> },\n): Promise<MarkdownResult> {\n let frontmatter: Record<string, unknown>\n let content: string\n if (preExtracted) {\n frontmatter = preExtracted.frontmatter\n content = preExtracted.content\n } else {\n const parsed = matter(raw, { engines: { yaml: parseYaml } })\n frontmatter = parsed.data\n content = parsed.content\n }\n const resolvedConfig = config && Object.keys(config).length > 0 ? config : DEFAULT_MARKDOWN_CONFIG\n // Freeze to prevent mutation after caching — see processorCache JSDoc above.\n if (Object.isFrozen(resolvedConfig) === false) deepFreeze(resolvedConfig)\n let processor = processorCache.get(resolvedConfig)\n if (!processor) {\n processor = createProcessor(resolvedConfig)\n processorCache.set(resolvedConfig, processor)\n }\n try {\n const result = await processor.process(content)\n const headings = Array.isArray(result.data.headings) ? (result.data.headings as Heading[]) : []\n return { html: String(result), headings, frontmatter }\n } catch (err) {\n throw new Error(\n `Markdown processing failed: ${err instanceof Error ? err.message : String(err)}`,\n { cause: err },\n )\n }\n}\n"],"mappings":"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"}
|
|
@@ -15,13 +15,5 @@ declare const MarkdownConfigSchema: z.ZodObject<{
|
|
|
15
15
|
}, z.core.$strip>;
|
|
16
16
|
type MarkdownConfig = z.infer<typeof MarkdownConfigSchema>;
|
|
17
17
|
//#endregion
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
depth: z.ZodNumber;
|
|
21
|
-
text: z.ZodString;
|
|
22
|
-
slug: z.ZodString;
|
|
23
|
-
}, z.core.$strip>;
|
|
24
|
-
type Heading = z.infer<typeof HeadingSchema>;
|
|
25
|
-
//#endregion
|
|
26
|
-
export { MarkdownConfigSchema as i, HeadingSchema as n, MarkdownConfig as r, Heading as t };
|
|
27
|
-
//# sourceMappingURL=heading-Dhvzlay-.d.mts.map
|
|
18
|
+
export { MarkdownConfigSchema as n, MarkdownConfig as t };
|
|
19
|
+
//# sourceMappingURL=markdown-config-CDvh5aJ-.d.mts.map
|