@nuasite/cms-marker 0.0.64 → 0.0.66
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/types/build-processor.d.ts +2 -1
- package/dist/types/build-processor.d.ts.map +1 -1
- package/dist/types/component-registry.d.ts.map +1 -1
- package/dist/types/config.d.ts +19 -0
- package/dist/types/config.d.ts.map +1 -0
- package/dist/types/dev-middleware.d.ts +10 -2
- package/dist/types/dev-middleware.d.ts.map +1 -1
- package/dist/types/error-collector.d.ts +56 -0
- package/dist/types/error-collector.d.ts.map +1 -0
- package/dist/types/html-processor.d.ts.map +1 -1
- package/dist/types/index.d.ts +2 -1
- package/dist/types/index.d.ts.map +1 -1
- package/dist/types/manifest-writer.d.ts +11 -2
- package/dist/types/manifest-writer.d.ts.map +1 -1
- package/dist/types/source-finder.d.ts +18 -3
- package/dist/types/source-finder.d.ts.map +1 -1
- package/dist/types/tailwind-colors.d.ts +6 -30
- package/dist/types/tailwind-colors.d.ts.map +1 -1
- package/dist/types/tsconfig.tsbuildinfo +1 -1
- package/dist/types/types.d.ts +25 -9
- package/dist/types/types.d.ts.map +1 -1
- package/dist/types/vite-plugin.d.ts.map +1 -1
- package/package.json +2 -1
- package/src/build-processor.ts +73 -19
- package/src/component-registry.ts +2 -0
- package/src/config.ts +29 -0
- package/src/dev-middleware.ts +12 -4
- package/src/error-collector.ts +106 -0
- package/src/html-processor.ts +55 -37
- package/src/index.ts +20 -4
- package/src/manifest-writer.ts +38 -7
- package/src/source-finder.ts +1003 -295
- package/src/tailwind-colors.ts +511 -121
- package/src/types.ts +27 -9
- package/src/vite-plugin.ts +4 -12
- package/dist/types/astro-transform.d.ts +0 -21
- package/dist/types/astro-transform.d.ts.map +0 -1
- package/src/astro-transform.ts +0 -205
package/src/html-processor.ts
CHANGED
|
@@ -1,9 +1,12 @@
|
|
|
1
|
-
import { parse } from 'node-html-parser'
|
|
1
|
+
import { type HTMLElement as ParsedHTMLElement, parse } from 'node-html-parser'
|
|
2
2
|
import { enhanceManifestWithSourceSnippets } from './source-finder'
|
|
3
3
|
import { extractColorClasses } from './tailwind-colors'
|
|
4
|
-
import type { ComponentInstance, ManifestEntry, SourceContext } from './types'
|
|
4
|
+
import type { ComponentInstance, ImageMetadata, ManifestEntry, SourceContext } from './types'
|
|
5
5
|
import { generateStableId } from './utils'
|
|
6
6
|
|
|
7
|
+
/** Type for parsed HTML element nodes from node-html-parser */
|
|
8
|
+
type HTMLNode = ParsedHTMLElement
|
|
9
|
+
|
|
7
10
|
/**
|
|
8
11
|
* Inline text styling elements that should NOT be marked with CMS IDs.
|
|
9
12
|
* These elements are text formatting and should be part of their parent's content.
|
|
@@ -187,7 +190,7 @@ export async function processHtml(
|
|
|
187
190
|
const entries: Record<string, ManifestEntry> = {}
|
|
188
191
|
const components: Record<string, ComponentInstance> = {}
|
|
189
192
|
const sourceLocationMap = new Map<string, { file: string; line: number }>()
|
|
190
|
-
const markedComponentRoots = new Set<
|
|
193
|
+
const markedComponentRoots = new Set<HTMLNode>()
|
|
191
194
|
let collectionWrapperId: string | undefined
|
|
192
195
|
|
|
193
196
|
// First pass: detect and mark component root elements
|
|
@@ -222,15 +225,15 @@ export async function processHtml(
|
|
|
222
225
|
|
|
223
226
|
// Check if any ancestor is already marked as a component root from the same file
|
|
224
227
|
// (we only want to mark the outermost element from each component)
|
|
225
|
-
let parent = node.parentNode
|
|
228
|
+
let parent = node.parentNode as HTMLNode | null
|
|
226
229
|
let ancestorFromSameComponent = false
|
|
227
230
|
while (parent) {
|
|
228
|
-
const parentSource =
|
|
231
|
+
const parentSource = parent.getAttribute?.('data-astro-source-file')
|
|
229
232
|
if (parentSource === sourceFile) {
|
|
230
233
|
ancestorFromSameComponent = true
|
|
231
234
|
break
|
|
232
235
|
}
|
|
233
|
-
parent = parent.parentNode
|
|
236
|
+
parent = parent.parentNode as HTMLNode | null
|
|
234
237
|
}
|
|
235
238
|
|
|
236
239
|
if (ancestorFromSameComponent) return
|
|
@@ -279,7 +282,12 @@ export async function processHtml(
|
|
|
279
282
|
|
|
280
283
|
// Image detection pass: mark img elements for CMS image replacement
|
|
281
284
|
// Store image entries separately to add to manifest later
|
|
282
|
-
|
|
285
|
+
interface ImageEntry {
|
|
286
|
+
metadata: ImageMetadata
|
|
287
|
+
sourceFile?: string
|
|
288
|
+
sourceLine?: number
|
|
289
|
+
}
|
|
290
|
+
const imageEntries = new Map<string, ImageEntry>()
|
|
283
291
|
root.querySelectorAll('img').forEach((node) => {
|
|
284
292
|
// Skip if already marked
|
|
285
293
|
if (node.getAttribute(attributeName)) return
|
|
@@ -294,7 +302,7 @@ export async function processHtml(
|
|
|
294
302
|
// Try to get source location from the image itself or ancestors
|
|
295
303
|
let sourceFile: string | undefined
|
|
296
304
|
let sourceLine: number | undefined
|
|
297
|
-
let current:
|
|
305
|
+
let current: HTMLNode | null = node
|
|
298
306
|
while (current && !sourceFile) {
|
|
299
307
|
const file = current.getAttribute?.('data-astro-source-file')
|
|
300
308
|
const line = current.getAttribute?.('data-astro-source-loc') || current.getAttribute?.('data-astro-source-line')
|
|
@@ -307,13 +315,20 @@ export async function processHtml(
|
|
|
307
315
|
}
|
|
308
316
|
}
|
|
309
317
|
}
|
|
310
|
-
current = current.parentNode
|
|
318
|
+
current = current.parentNode as HTMLNode | null
|
|
311
319
|
}
|
|
312
320
|
|
|
313
|
-
//
|
|
314
|
-
|
|
321
|
+
// Build image metadata
|
|
322
|
+
const metadata: ImageMetadata = {
|
|
315
323
|
src,
|
|
316
324
|
alt: node.getAttribute('alt') || '',
|
|
325
|
+
srcSet: node.getAttribute('srcset') || undefined,
|
|
326
|
+
sizes: node.getAttribute('sizes') || undefined,
|
|
327
|
+
}
|
|
328
|
+
|
|
329
|
+
// Store image info for manifest
|
|
330
|
+
imageEntries.set(id, {
|
|
331
|
+
metadata,
|
|
317
332
|
sourceFile,
|
|
318
333
|
sourceLine,
|
|
319
334
|
})
|
|
@@ -335,23 +350,23 @@ export async function processHtml(
|
|
|
335
350
|
// Check if this element has any direct child elements without source file attribute
|
|
336
351
|
// These would be markdown-rendered elements
|
|
337
352
|
const childElements = node.childNodes.filter(
|
|
338
|
-
(child:
|
|
353
|
+
(child): child is HTMLNode => child.nodeType === 1 && 'tagName' in child,
|
|
339
354
|
)
|
|
340
355
|
const hasMarkdownChildren = childElements.some(
|
|
341
|
-
(child
|
|
356
|
+
(child) => !child.getAttribute?.('data-astro-source-file'),
|
|
342
357
|
)
|
|
343
358
|
|
|
344
359
|
if (hasMarkdownChildren) {
|
|
345
360
|
// Check if any ancestor already has been marked as a collection wrapper
|
|
346
361
|
// We want the innermost wrapper
|
|
347
|
-
let parent = node.parentNode
|
|
362
|
+
let parent = node.parentNode as HTMLNode | null
|
|
348
363
|
let hasAncestorWrapper = false
|
|
349
364
|
while (parent) {
|
|
350
|
-
if (
|
|
365
|
+
if (parent.getAttribute?.(attributeName)?.startsWith('cms-collection-')) {
|
|
351
366
|
hasAncestorWrapper = true
|
|
352
367
|
break
|
|
353
368
|
}
|
|
354
|
-
parent = parent.parentNode
|
|
369
|
+
parent = parent.parentNode as HTMLNode | null
|
|
355
370
|
}
|
|
356
371
|
|
|
357
372
|
if (!hasAncestorWrapper) {
|
|
@@ -382,7 +397,7 @@ export async function processHtml(
|
|
|
382
397
|
|
|
383
398
|
if (bodyStart.length > 10) {
|
|
384
399
|
// Store all candidates that match the body start
|
|
385
|
-
const candidates: Array<{ node:
|
|
400
|
+
const candidates: Array<{ node: HTMLNode; blockChildCount: number }> = []
|
|
386
401
|
|
|
387
402
|
for (const node of allElements) {
|
|
388
403
|
const tag = node.tagName?.toLowerCase?.() ?? ''
|
|
@@ -391,8 +406,8 @@ export async function processHtml(
|
|
|
391
406
|
|
|
392
407
|
// Check if this element's first text content starts with the markdown body
|
|
393
408
|
const firstChild = node.childNodes.find(
|
|
394
|
-
(child:
|
|
395
|
-
)
|
|
409
|
+
(child): child is HTMLNode => child.nodeType === 1 && 'tagName' in child,
|
|
410
|
+
)
|
|
396
411
|
|
|
397
412
|
if (firstChild) {
|
|
398
413
|
const firstChildText = (firstChild.innerText || '').trim().substring(0, 80)
|
|
@@ -401,7 +416,8 @@ export async function processHtml(
|
|
|
401
416
|
// Markdown typically renders to multiple block elements (p, h2, h3, ul, ol, etc.)
|
|
402
417
|
const blockTags = ['p', 'h1', 'h2', 'h3', 'h4', 'h5', 'h6', 'ul', 'ol', 'blockquote', 'pre', 'table', 'hr']
|
|
403
418
|
const blockChildCount = node.childNodes.filter(
|
|
404
|
-
(child:
|
|
419
|
+
(child): child is HTMLNode =>
|
|
420
|
+
child.nodeType === 1 && 'tagName' in child && blockTags.includes((child as HTMLNode).tagName?.toLowerCase?.() ?? ''),
|
|
405
421
|
).length
|
|
406
422
|
|
|
407
423
|
candidates.push({ node, blockChildCount })
|
|
@@ -495,11 +511,14 @@ export async function processHtml(
|
|
|
495
511
|
|
|
496
512
|
// Get child CMS elements
|
|
497
513
|
const childCmsElements = node.querySelectorAll(`[${attributeName}]`)
|
|
498
|
-
const childCmsIds = Array.from(childCmsElements)
|
|
514
|
+
const childCmsIds = Array.from(childCmsElements)
|
|
515
|
+
.map((child) => child.getAttribute(attributeName))
|
|
516
|
+
.filter((id): id is string => id !== null)
|
|
499
517
|
|
|
500
518
|
// Build text with placeholders for child CMS elements
|
|
501
519
|
// Recursively process child nodes to handle nested CMS elements correctly
|
|
502
|
-
|
|
520
|
+
type ChildNode = { nodeType: number; text?: string; childNodes?: ChildNode[]; getAttribute?: (name: string) => string | null }
|
|
521
|
+
const buildTextWithPlaceholders = (nodes: ChildNode[]): string => {
|
|
503
522
|
let text = ''
|
|
504
523
|
for (const child of nodes) {
|
|
505
524
|
if (child.nodeType === 3) {
|
|
@@ -507,21 +526,21 @@ export async function processHtml(
|
|
|
507
526
|
text += child.text || ''
|
|
508
527
|
} else if (child.nodeType === 1) {
|
|
509
528
|
// Element node
|
|
510
|
-
const directCmsId =
|
|
529
|
+
const directCmsId = child.getAttribute?.(attributeName)
|
|
511
530
|
|
|
512
531
|
if (directCmsId) {
|
|
513
532
|
// Child has a direct CMS ID - use placeholder
|
|
514
533
|
text += `{{cms:${directCmsId}}}`
|
|
515
534
|
} else {
|
|
516
535
|
// Child doesn't have a CMS ID - recursively process its children
|
|
517
|
-
text += buildTextWithPlaceholders(child.childNodes || [])
|
|
536
|
+
text += buildTextWithPlaceholders((child.childNodes || []) as ChildNode[])
|
|
518
537
|
}
|
|
519
538
|
}
|
|
520
539
|
}
|
|
521
540
|
return text
|
|
522
541
|
}
|
|
523
542
|
|
|
524
|
-
const textWithPlaceholders = buildTextWithPlaceholders(node.childNodes || [])
|
|
543
|
+
const textWithPlaceholders = buildTextWithPlaceholders((node.childNodes || []) as ChildNode[])
|
|
525
544
|
|
|
526
545
|
// Get direct text content (without placeholders)
|
|
527
546
|
const directText = textWithPlaceholders.replace(/\{\{cms:[^}]+\}\}/g, '').trim()
|
|
@@ -540,14 +559,14 @@ export async function processHtml(
|
|
|
540
559
|
|
|
541
560
|
// Find parent component if any
|
|
542
561
|
let parentComponentId: string | undefined
|
|
543
|
-
let parent = node.parentNode
|
|
562
|
+
let parent = node.parentNode as HTMLNode | null
|
|
544
563
|
while (parent) {
|
|
545
|
-
const parentCompId =
|
|
564
|
+
const parentCompId = parent.getAttribute?.('data-cms-component-id')
|
|
546
565
|
if (parentCompId) {
|
|
547
566
|
parentComponentId = parentCompId
|
|
548
567
|
break
|
|
549
568
|
}
|
|
550
|
-
parent = parent.parentNode
|
|
569
|
+
parent = parent.parentNode as HTMLNode | null
|
|
551
570
|
}
|
|
552
571
|
|
|
553
572
|
// Extract source context for resilient matching
|
|
@@ -564,7 +583,7 @@ export async function processHtml(
|
|
|
564
583
|
const imageInfo = imageEntries.get(id)
|
|
565
584
|
const isImage = !!imageInfo
|
|
566
585
|
|
|
567
|
-
const entryText = isImage ? (imageInfo.alt || imageInfo.src) : textWithPlaceholders.trim()
|
|
586
|
+
const entryText = isImage ? (imageInfo.metadata.alt || imageInfo.metadata.src) : textWithPlaceholders.trim()
|
|
568
587
|
// For images, use the source file we captured from ancestors if not in sourceLocationMap
|
|
569
588
|
const entrySourcePath = sourceLocation?.file || imageInfo?.sourceFile || sourcePath
|
|
570
589
|
|
|
@@ -591,12 +610,11 @@ export async function processHtml(
|
|
|
591
610
|
collectionName: isCollectionWrapper ? collectionInfo?.name : undefined,
|
|
592
611
|
collectionSlug: isCollectionWrapper ? collectionInfo?.slug : undefined,
|
|
593
612
|
contentPath: isCollectionWrapper ? collectionInfo?.contentPath : undefined,
|
|
594
|
-
// Add image info for image entries
|
|
595
|
-
imageSrc: imageInfo?.src,
|
|
596
|
-
imageAlt: imageInfo?.alt,
|
|
597
613
|
// Robustness fields
|
|
598
614
|
stableId,
|
|
599
615
|
sourceContext,
|
|
616
|
+
// Image metadata for image entries
|
|
617
|
+
imageMetadata: imageInfo?.metadata,
|
|
600
618
|
// Color classes for buttons/styled elements
|
|
601
619
|
colorClasses,
|
|
602
620
|
}
|
|
@@ -604,7 +622,7 @@ export async function processHtml(
|
|
|
604
622
|
}
|
|
605
623
|
|
|
606
624
|
// Clean up any remaining source attributes from component-marked elements
|
|
607
|
-
markedComponentRoots.forEach((node
|
|
625
|
+
markedComponentRoots.forEach((node) => {
|
|
608
626
|
node.removeAttribute('data-astro-source-file')
|
|
609
627
|
node.removeAttribute('data-astro-source-loc')
|
|
610
628
|
node.removeAttribute('data-astro-source-line')
|
|
@@ -645,13 +663,13 @@ export function cleanText(text: string): string {
|
|
|
645
663
|
* This captures information about the element's position in the DOM
|
|
646
664
|
* that can be used as fallback when exact matching fails.
|
|
647
665
|
*/
|
|
648
|
-
function extractSourceContext(node:
|
|
649
|
-
const parent = node.parentNode
|
|
666
|
+
function extractSourceContext(node: HTMLNode, attributeName: string): SourceContext | undefined {
|
|
667
|
+
const parent = node.parentNode as HTMLNode | null
|
|
650
668
|
if (!parent) return undefined
|
|
651
669
|
|
|
652
|
-
const siblings = parent.childNodes?.filter((child:
|
|
670
|
+
const siblings = parent.childNodes?.filter((child): child is HTMLNode => {
|
|
653
671
|
// Only consider element nodes, not text nodes
|
|
654
|
-
return child.nodeType === 1 && child
|
|
672
|
+
return child.nodeType === 1 && 'tagName' in child
|
|
655
673
|
}) || []
|
|
656
674
|
|
|
657
675
|
const siblingIndex = siblings.indexOf(node)
|
package/src/index.ts
CHANGED
|
@@ -1,7 +1,9 @@
|
|
|
1
1
|
import type { AstroIntegration } from 'astro'
|
|
2
2
|
import { processBuildOutput } from './build-processor'
|
|
3
3
|
import { ComponentRegistry } from './component-registry'
|
|
4
|
+
import { resetProjectRoot } from './config'
|
|
4
5
|
import { createDevMiddleware } from './dev-middleware'
|
|
6
|
+
import { getErrorCollector, resetErrorCollector } from './error-collector'
|
|
5
7
|
import { ManifestWriter } from './manifest-writer'
|
|
6
8
|
import type { CmsMarkerOptions, ComponentDefinition } from './types'
|
|
7
9
|
import { createVitePlugin } from './vite-plugin'
|
|
@@ -46,6 +48,8 @@ export default function cmsMarker(options: CmsMarkerOptions = {}): AstroIntegrat
|
|
|
46
48
|
// Reset state for new build/dev session
|
|
47
49
|
idCounter.value = 0
|
|
48
50
|
manifestWriter.reset()
|
|
51
|
+
resetErrorCollector()
|
|
52
|
+
resetProjectRoot()
|
|
49
53
|
|
|
50
54
|
// Load available colors from Tailwind config
|
|
51
55
|
await manifestWriter.loadAvailableColors()
|
|
@@ -72,15 +76,16 @@ export default function cmsMarker(options: CmsMarkerOptions = {}): AstroIntegrat
|
|
|
72
76
|
command,
|
|
73
77
|
}
|
|
74
78
|
|
|
79
|
+
// VitePluginLike is compatible with both Astro's bundled Vite and root Vite
|
|
75
80
|
updateConfig({
|
|
76
81
|
vite: {
|
|
77
|
-
plugins:
|
|
82
|
+
plugins: createVitePlugin(pluginContext) as any,
|
|
78
83
|
},
|
|
79
84
|
})
|
|
80
85
|
},
|
|
81
86
|
|
|
82
87
|
'astro:server:setup': ({ server, logger }) => {
|
|
83
|
-
createDevMiddleware(server
|
|
88
|
+
createDevMiddleware(server, config, manifestWriter, componentDefinitions, idCounter)
|
|
84
89
|
logger.info('Dev middleware initialized')
|
|
85
90
|
},
|
|
86
91
|
|
|
@@ -88,13 +93,24 @@ export default function cmsMarker(options: CmsMarkerOptions = {}): AstroIntegrat
|
|
|
88
93
|
if (generateManifest) {
|
|
89
94
|
await processBuildOutput(dir, config, manifestWriter, idCounter, logger)
|
|
90
95
|
}
|
|
96
|
+
|
|
97
|
+
// Report any warnings collected during processing
|
|
98
|
+
const errorCollector = getErrorCollector()
|
|
99
|
+
if (errorCollector.hasWarnings()) {
|
|
100
|
+
const warnings = errorCollector.getWarnings()
|
|
101
|
+
logger.warn(`${warnings.length} warning(s) during processing:`)
|
|
102
|
+
for (const { context, message } of warnings) {
|
|
103
|
+
logger.warn(` - ${context}: ${message}`)
|
|
104
|
+
}
|
|
105
|
+
}
|
|
91
106
|
},
|
|
92
107
|
},
|
|
93
108
|
}
|
|
94
109
|
}
|
|
95
110
|
|
|
96
|
-
export
|
|
97
|
-
|
|
111
|
+
// Re-export config functions for testing
|
|
112
|
+
export { getProjectRoot, resetProjectRoot, setProjectRoot } from './config'
|
|
98
113
|
// Re-export types for consumers
|
|
99
114
|
export type { CollectionInfo, MarkdownContent, SourceLocation, VariableReference } from './source-finder'
|
|
115
|
+
export { findCollectionSource, parseMarkdownContent } from './source-finder'
|
|
100
116
|
export type * from './types'
|
package/src/manifest-writer.ts
CHANGED
|
@@ -1,7 +1,17 @@
|
|
|
1
1
|
import fs from 'node:fs/promises'
|
|
2
2
|
import path from 'node:path'
|
|
3
|
-
import {
|
|
4
|
-
import
|
|
3
|
+
import { getProjectRoot } from './config'
|
|
4
|
+
import { parseTailwindConfig, parseTextStyles } from './tailwind-colors'
|
|
5
|
+
import type {
|
|
6
|
+
AvailableColors,
|
|
7
|
+
AvailableTextStyles,
|
|
8
|
+
CmsManifest,
|
|
9
|
+
CollectionEntry,
|
|
10
|
+
ComponentDefinition,
|
|
11
|
+
ComponentInstance,
|
|
12
|
+
ManifestEntry,
|
|
13
|
+
ManifestMetadata,
|
|
14
|
+
} from './types'
|
|
5
15
|
import { generateManifestContentHash, generateSourceFileHashes } from './utils'
|
|
6
16
|
|
|
7
17
|
/** Current manifest schema version */
|
|
@@ -22,6 +32,7 @@ export class ManifestWriter {
|
|
|
22
32
|
private manifestFile: string
|
|
23
33
|
private componentDefinitions: Record<string, ComponentDefinition>
|
|
24
34
|
private availableColors: AvailableColors | undefined
|
|
35
|
+
private availableTextStyles: AvailableTextStyles | undefined
|
|
25
36
|
private writeQueue: Promise<void> = Promise.resolve()
|
|
26
37
|
|
|
27
38
|
constructor(manifestFile: string, componentDefinitions: Record<string, ComponentDefinition> = {}) {
|
|
@@ -51,13 +62,13 @@ export class ManifestWriter {
|
|
|
51
62
|
}
|
|
52
63
|
|
|
53
64
|
/**
|
|
54
|
-
* Load available Tailwind colors from the project's CSS config
|
|
65
|
+
* Load available Tailwind colors and text styles from the project's CSS config
|
|
55
66
|
*/
|
|
56
|
-
async loadAvailableColors(projectRoot: string =
|
|
67
|
+
async loadAvailableColors(projectRoot: string = getProjectRoot()): Promise<void> {
|
|
57
68
|
this.availableColors = await parseTailwindConfig(projectRoot)
|
|
58
|
-
|
|
59
|
-
this.availableColors.colorSafelistHtml = generateColorSafelistHtml(this.availableColors)
|
|
69
|
+
this.availableTextStyles = await parseTextStyles(projectRoot)
|
|
60
70
|
this.globalManifest.availableColors = this.availableColors
|
|
71
|
+
this.globalManifest.availableTextStyles = this.availableTextStyles
|
|
61
72
|
}
|
|
62
73
|
|
|
63
74
|
/**
|
|
@@ -68,6 +79,14 @@ export class ManifestWriter {
|
|
|
68
79
|
this.globalManifest.availableColors = colors
|
|
69
80
|
}
|
|
70
81
|
|
|
82
|
+
/**
|
|
83
|
+
* Set available text styles directly (for testing or custom styles)
|
|
84
|
+
*/
|
|
85
|
+
setAvailableTextStyles(textStyles: AvailableTextStyles): void {
|
|
86
|
+
this.availableTextStyles = textStyles
|
|
87
|
+
this.globalManifest.availableTextStyles = textStyles
|
|
88
|
+
}
|
|
89
|
+
|
|
71
90
|
/**
|
|
72
91
|
* Get the manifest path for a given page
|
|
73
92
|
* Places manifest next to the page: /about -> /about.json, / -> /index.json
|
|
@@ -163,18 +182,22 @@ export class ManifestWriter {
|
|
|
163
182
|
// Wait for all queued writes to complete
|
|
164
183
|
await this.writeQueue
|
|
165
184
|
|
|
166
|
-
// Write global manifest with settings (component definitions and
|
|
185
|
+
// Write global manifest with settings (component definitions, colors, and text styles)
|
|
167
186
|
if (this.outDir) {
|
|
168
187
|
const globalManifestPath = path.join(this.outDir, this.manifestFile)
|
|
169
188
|
const globalSettings: {
|
|
170
189
|
componentDefinitions: Record<string, ComponentDefinition>
|
|
171
190
|
availableColors?: AvailableColors
|
|
191
|
+
availableTextStyles?: AvailableTextStyles
|
|
172
192
|
} = {
|
|
173
193
|
componentDefinitions: this.componentDefinitions,
|
|
174
194
|
}
|
|
175
195
|
if (this.availableColors) {
|
|
176
196
|
globalSettings.availableColors = this.availableColors
|
|
177
197
|
}
|
|
198
|
+
if (this.availableTextStyles) {
|
|
199
|
+
globalSettings.availableTextStyles = this.availableTextStyles
|
|
200
|
+
}
|
|
178
201
|
await fs.writeFile(
|
|
179
202
|
globalManifestPath,
|
|
180
203
|
JSON.stringify(globalSettings, null, 2),
|
|
@@ -218,6 +241,7 @@ export class ManifestWriter {
|
|
|
218
241
|
componentDefinitions: this.componentDefinitions,
|
|
219
242
|
collections: {},
|
|
220
243
|
availableColors: this.availableColors,
|
|
244
|
+
availableTextStyles: this.availableTextStyles,
|
|
221
245
|
}
|
|
222
246
|
this.writeQueue = Promise.resolve()
|
|
223
247
|
}
|
|
@@ -228,4 +252,11 @@ export class ManifestWriter {
|
|
|
228
252
|
getAvailableColors(): AvailableColors | undefined {
|
|
229
253
|
return this.availableColors
|
|
230
254
|
}
|
|
255
|
+
|
|
256
|
+
/**
|
|
257
|
+
* Get available text styles (for use in dev middleware)
|
|
258
|
+
*/
|
|
259
|
+
getAvailableTextStyles(): AvailableTextStyles | undefined {
|
|
260
|
+
return this.availableTextStyles
|
|
261
|
+
}
|
|
231
262
|
}
|