@oktis-works/theme-runtime 0.0.0-stage → 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,13 @@
1
+ export { ThemeRenderer } from './renderer.js';
2
+ export { ThemeResolver } from './resolver.js';
3
+ export type { ResolvedComponent } from './resolver.js';
4
+ export { TemplateHierarchyResolver, buildTemplateChain, } from './template-resolver.js';
5
+ export type { TemplateContext, ResolvedTemplate, TemplateFileChecker } from './template-resolver.js';
6
+ export { ThemeLoader } from './loader.js';
7
+ export { prerenderStatic, routeToOutputFile, type PrerenderRoute, type PrerenderResult } from './prerender.js';
8
+ export type { DiscoveredTheme } from './loader.js';
9
+ export { RuntimeRouter, targetedRevalidate, } from './routing.js';
10
+ export type { RouteResolution, ContentLookup, EventEmitLike, } from './routing.js';
11
+ export { buildThemeStyles, compileScss, compileTailwind, resolveStyleEngine, scopeCss, validateStyleManifest, getThemeScopeAttribute, } from './style-engine.js';
12
+ export type { ThemeStyleReport, StyleEngineOptions } from './style-engine.js';
13
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,aAAa,EAAE,MAAM,eAAe,CAAC;AAC9C,OAAO,EAAE,aAAa,EAAE,MAAM,eAAe,CAAC;AAC9C,YAAY,EAAE,iBAAiB,EAAE,MAAM,eAAe,CAAC;AACvD,OAAO,EACL,yBAAyB,EACzB,kBAAkB,GACnB,MAAM,wBAAwB,CAAC;AAChC,YAAY,EAAE,eAAe,EAAE,gBAAgB,EAAE,mBAAmB,EAAE,MAAM,wBAAwB,CAAC;AACrG,OAAO,EAAE,WAAW,EAAE,MAAM,aAAa,CAAC;AAC1C,OAAO,EAAE,eAAe,EAAE,iBAAiB,EAAE,KAAK,cAAc,EAAE,KAAK,eAAe,EAAE,MAAM,gBAAgB,CAAC;AAC/G,YAAY,EAAE,eAAe,EAAE,MAAM,aAAa,CAAC;AACnD,OAAO,EACL,aAAa,EACb,kBAAkB,GACnB,MAAM,cAAc,CAAC;AACtB,YAAY,EACV,eAAe,EACf,aAAa,EACb,aAAa,GACd,MAAM,cAAc,CAAC;AACtB,OAAO,EACL,gBAAgB,EAChB,WAAW,EACX,eAAe,EACf,kBAAkB,EAClB,QAAQ,EACR,qBAAqB,EACrB,sBAAsB,GACvB,MAAM,mBAAmB,CAAC;AAC3B,YAAY,EAAE,gBAAgB,EAAE,kBAAkB,EAAE,MAAM,mBAAmB,CAAC"}
package/dist/index.js ADDED
@@ -0,0 +1,9 @@
1
+ // @oktis-works/theme-runtime - Main Entry Point
2
+ export { ThemeRenderer } from './renderer.js';
3
+ export { ThemeResolver } from './resolver.js';
4
+ export { TemplateHierarchyResolver, buildTemplateChain, } from './template-resolver.js';
5
+ export { ThemeLoader } from './loader.js';
6
+ export { prerenderStatic, routeToOutputFile } from './prerender.js';
7
+ export { RuntimeRouter, targetedRevalidate, } from './routing.js';
8
+ export { buildThemeStyles, compileScss, compileTailwind, resolveStyleEngine, scopeCss, validateStyleManifest, getThemeScopeAttribute, } from './style-engine.js';
9
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,gDAAgD;AAEhD,OAAO,EAAE,aAAa,EAAE,MAAM,eAAe,CAAC;AAC9C,OAAO,EAAE,aAAa,EAAE,MAAM,eAAe,CAAC;AAE9C,OAAO,EACL,yBAAyB,EACzB,kBAAkB,GACnB,MAAM,wBAAwB,CAAC;AAEhC,OAAO,EAAE,WAAW,EAAE,MAAM,aAAa,CAAC;AAC1C,OAAO,EAAE,eAAe,EAAE,iBAAiB,EAA6C,MAAM,gBAAgB,CAAC;AAE/G,OAAO,EACL,aAAa,EACb,kBAAkB,GACnB,MAAM,cAAc,CAAC;AAMtB,OAAO,EACL,gBAAgB,EAChB,WAAW,EACX,eAAe,EACf,kBAAkB,EAClB,QAAQ,EACR,qBAAqB,EACrB,sBAAsB,GACvB,MAAM,mBAAmB,CAAC"}
@@ -0,0 +1,20 @@
1
+ import type { ThemeManifest } from '@oktis-works/theme-sdk';
2
+ export interface DiscoveredTheme {
3
+ manifest: ThemeManifest;
4
+ path: string;
5
+ }
6
+ export declare class ThemeLoader {
7
+ private themesDir;
8
+ constructor(themesDir: string);
9
+ /** Varre o diretório e retorna temas com theme.json válido. */
10
+ discoverThemes(): Promise<DiscoveredTheme[]>;
11
+ /** Carrega um único tema a partir do caminho contendo theme.json. */
12
+ loadTheme(themeName: string): Promise<DiscoveredTheme | null>;
13
+ /**
14
+ * Ordena temas respeitando a cadeia de herança (`parent`):
15
+ * pais antes dos filhos — mesmo contrato do PluginLoader.resolveDependencies.
16
+ */
17
+ orderInheritanceChain(themes: DiscoveredTheme[]): DiscoveredTheme[];
18
+ private loadManifest;
19
+ }
20
+ //# sourceMappingURL=loader.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"loader.d.ts","sourceRoot":"","sources":["../src/loader.ts"],"names":[],"mappings":"AAIA,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,wBAAwB,CAAC;AAG5D,MAAM,WAAW,eAAe;IAC9B,QAAQ,EAAE,aAAa,CAAC;IACxB,IAAI,EAAE,MAAM,CAAC;CACd;AAED,qBAAa,WAAW;IACtB,OAAO,CAAC,SAAS,CAAS;gBAEd,SAAS,EAAE,MAAM;IAI7B,+DAA+D;IACzD,cAAc,IAAI,OAAO,CAAC,eAAe,EAAE,CAAC;IAclD,qEAAqE;IAC/D,SAAS,CAAC,SAAS,EAAE,MAAM,GAAG,OAAO,CAAC,eAAe,GAAG,IAAI,CAAC;IAMnE;;;OAGG;IACH,qBAAqB,CAAC,MAAM,EAAE,eAAe,EAAE,GAAG,eAAe,EAAE;YAyBrD,YAAY;CAkB3B"}
package/dist/loader.js ADDED
@@ -0,0 +1,75 @@
1
+ // @oktis-works/theme-runtime - Theme Loader (descoberta via node_modules / diretório)
2
+ import { readdir, readFile } from 'node:fs/promises';
3
+ import { join, resolve } from 'node:path';
4
+ import { validateStyleManifest } from './style-engine.js';
5
+ export class ThemeLoader {
6
+ themesDir;
7
+ constructor(themesDir) {
8
+ this.themesDir = resolve(themesDir);
9
+ }
10
+ /** Varre o diretório e retorna temas com theme.json válido. */
11
+ async discoverThemes() {
12
+ const entries = await readdir(this.themesDir, { withFileTypes: true });
13
+ const themes = [];
14
+ for (const entry of entries) {
15
+ if (!entry.isDirectory())
16
+ continue;
17
+ const themePath = join(this.themesDir, entry.name);
18
+ const manifest = await this.loadManifest(themePath);
19
+ if (manifest)
20
+ themes.push({ manifest, path: themePath });
21
+ }
22
+ return themes;
23
+ }
24
+ /** Carrega um único tema a partir do caminho contendo theme.json. */
25
+ async loadTheme(themeName) {
26
+ const themePath = join(this.themesDir, themeName);
27
+ const manifest = await this.loadManifest(themePath);
28
+ return manifest ? { manifest, path: themePath } : null;
29
+ }
30
+ /**
31
+ * Ordena temas respeitando a cadeia de herança (`parent`):
32
+ * pais antes dos filhos — mesmo contrato do PluginLoader.resolveDependencies.
33
+ */
34
+ orderInheritanceChain(themes) {
35
+ const byName = new Map(themes.map((theme) => [theme.manifest.name, theme]));
36
+ const visited = new Set();
37
+ const visiting = new Set();
38
+ const ordered = [];
39
+ const visit = (theme) => {
40
+ const name = theme.manifest.name;
41
+ if (visited.has(name))
42
+ return;
43
+ if (visiting.has(name))
44
+ return; // ciclo: ignora
45
+ visiting.add(name);
46
+ const parent = theme.manifest.parent ? byName.get(theme.manifest.parent) : undefined;
47
+ if (parent)
48
+ visit(parent);
49
+ visiting.delete(name);
50
+ visited.add(name);
51
+ ordered.push(theme);
52
+ };
53
+ for (const theme of themes)
54
+ visit(theme);
55
+ return ordered;
56
+ }
57
+ async loadManifest(themePath) {
58
+ try {
59
+ const raw = await readFile(join(themePath, 'theme.json'), 'utf-8');
60
+ const manifest = JSON.parse(raw);
61
+ if (!manifest.name || !manifest.version)
62
+ return null;
63
+ // validação de estilo exclusiva (avisa em erro, mas não bloqueia descoberta)
64
+ const errors = validateStyleManifest(manifest, themePath);
65
+ if (errors.length) {
66
+ console.warn(`[ThemeLoader] ${manifest.name}: ${errors.join('; ')}`);
67
+ }
68
+ return manifest;
69
+ }
70
+ catch {
71
+ return null;
72
+ }
73
+ }
74
+ }
75
+ //# sourceMappingURL=loader.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"loader.js","sourceRoot":"","sources":["../src/loader.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,24 @@
1
+ export interface PrerenderRoute {
2
+ /** Caminho público da rota, ex.: '/', '/meu-post' */
3
+ path: string;
4
+ /** Produz o HTML final da rota. */
5
+ render: () => Promise<string> | string;
6
+ }
7
+ export interface PrerenderResult {
8
+ pages: number;
9
+ failed: Array<{
10
+ path: string;
11
+ error: string;
12
+ }>;
13
+ outputDir: string;
14
+ durationMs: number;
15
+ }
16
+ /** Converte um caminho de rota no arquivo de saída hierárquico (dir/index.html). */
17
+ export declare function routeToOutputFile(routePath: string): string;
18
+ /**
19
+ * Gera HTML estático para as rotas informadas, escrevendo <outDir>/<rota>/index.html.
20
+ * Falhas por rota não abortam o lote — são reportadas em `failed`.
21
+ */
22
+ export declare function prerenderStatic(routes: PrerenderRoute[], outDir: string): Promise<PrerenderResult>;
23
+ export declare function assertSafeOutDir(outDir: string, root: string): boolean;
24
+ //# sourceMappingURL=prerender.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"prerender.d.ts","sourceRoot":"","sources":["../src/prerender.ts"],"names":[],"mappings":"AAKA,MAAM,WAAW,cAAc;IAC7B,qDAAqD;IACrD,IAAI,EAAE,MAAM,CAAC;IACb,mCAAmC;IACnC,MAAM,EAAE,MAAM,OAAO,CAAC,MAAM,CAAC,GAAG,MAAM,CAAC;CACxC;AAED,MAAM,WAAW,eAAe;IAC9B,KAAK,EAAE,MAAM,CAAC;IACd,MAAM,EAAE,KAAK,CAAC;QAAE,IAAI,EAAE,MAAM,CAAC;QAAC,KAAK,EAAE,MAAM,CAAA;KAAE,CAAC,CAAC;IAC/C,SAAS,EAAE,MAAM,CAAC;IAClB,UAAU,EAAE,MAAM,CAAC;CACpB;AAED,oFAAoF;AACpF,wBAAgB,iBAAiB,CAAC,SAAS,EAAE,MAAM,GAAG,MAAM,CAK3D;AAED;;;GAGG;AACH,wBAAsB,eAAe,CAAC,MAAM,EAAE,cAAc,EAAE,EAAE,MAAM,EAAE,MAAM,GAAG,OAAO,CAAC,eAAe,CAAC,CAqBxG;AAED,wBAAgB,gBAAgB,CAAC,MAAM,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,GAAG,OAAO,CAEtE"}
@@ -0,0 +1,39 @@
1
+ // @oktis-works/theme-runtime - Prerender estático (SSG) — theme-rendering-002
2
+ import { mkdir, writeFile } from 'node:fs/promises';
3
+ import { join, resolve, sep } from 'node:path';
4
+ /** Converte um caminho de rota no arquivo de saída hierárquico (dir/index.html). */
5
+ export function routeToOutputFile(routePath) {
6
+ const normalized = routePath.split('?')[0].replace(/\/+/g, '/').replace(/\/$/, '');
7
+ const safe = normalized === '' ? 'index' : normalized.replace(/^\//, '');
8
+ if (safe.includes('..'))
9
+ throw new Error(`Caminho inseguro para prerender: ${routePath}`);
10
+ return join(safe, 'index.html');
11
+ }
12
+ /**
13
+ * Gera HTML estático para as rotas informadas, escrevendo <outDir>/<rota>/index.html.
14
+ * Falhas por rota não abortam o lote — são reportadas em `failed`.
15
+ */
16
+ export async function prerenderStatic(routes, outDir) {
17
+ const started = Date.now();
18
+ const outputDir = resolve(outDir);
19
+ await mkdir(outputDir, { recursive: true });
20
+ const failed = [];
21
+ let pages = 0;
22
+ for (const route of routes) {
23
+ try {
24
+ const html = await route.render();
25
+ const file = join(outputDir, routeToOutputFile(route.path));
26
+ await mkdir(join(file, '..'), { recursive: true });
27
+ await writeFile(file, html, 'utf-8');
28
+ pages += 1;
29
+ }
30
+ catch (error) {
31
+ failed.push({ path: route.path, error: error instanceof Error ? error.message : String(error) });
32
+ }
33
+ }
34
+ return { pages, failed, outputDir, durationMs: Date.now() - started };
35
+ }
36
+ export function assertSafeOutDir(outDir, root) {
37
+ return resolve(outDir).startsWith(resolve(root) + sep) || resolve(outDir) === resolve(root);
38
+ }
39
+ //# sourceMappingURL=prerender.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"prerender.js","sourceRoot":"","sources":["../src/prerender.ts"],"names":[],"mappings":"AAAA,8EAA8E;AAE9E,OAAO,EAAE,KAAK,EAAE,SAAS,EAAE,MAAM,kBAAkB,CAAC;AACpD,OAAO,EAAE,IAAI,EAAE,OAAO,EAAE,GAAG,EAAE,MAAM,WAAW,CAAC;AAgB/C,oFAAoF;AACpF,MAAM,UAAU,iBAAiB,CAAC,SAAiB;IACjD,MAAM,UAAU,GAAG,SAAS,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,CAAC,CAAE,CAAC,OAAO,CAAC,MAAM,EAAE,GAAG,CAAC,CAAC,OAAO,CAAC,KAAK,EAAE,EAAE,CAAC,CAAC;IACpF,MAAM,IAAI,GAAG,UAAU,KAAK,EAAE,CAAC,CAAC,CAAC,OAAO,CAAC,CAAC,CAAC,UAAU,CAAC,OAAO,CAAC,KAAK,EAAE,EAAE,CAAC,CAAC;IACzE,IAAI,IAAI,CAAC,QAAQ,CAAC,IAAI,CAAC;QAAE,MAAM,IAAI,KAAK,CAAC,oCAAoC,SAAS,EAAE,CAAC,CAAC;IAC1F,OAAO,IAAI,CAAC,IAAI,EAAE,YAAY,CAAC,CAAC;AAClC,CAAC;AAED;;;GAGG;AACH,MAAM,CAAC,KAAK,UAAU,eAAe,CAAC,MAAwB,EAAE,MAAc;IAC5E,MAAM,OAAO,GAAG,IAAI,CAAC,GAAG,EAAE,CAAC;IAC3B,MAAM,SAAS,GAAG,OAAO,CAAC,MAAM,CAAC,CAAC;IAClC,MAAM,KAAK,CAAC,SAAS,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAC;IAE5C,MAAM,MAAM,GAA2C,EAAE,CAAC;IAC1D,IAAI,KAAK,GAAG,CAAC,CAAC;IAEd,KAAK,MAAM,KAAK,IAAI,MAAM,EAAE,CAAC;QAC3B,IAAI,CAAC;YACH,MAAM,IAAI,GAAG,MAAM,KAAK,CAAC,MAAM,EAAE,CAAC;YAClC,MAAM,IAAI,GAAG,IAAI,CAAC,SAAS,EAAE,iBAAiB,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC,CAAC;YAC5D,MAAM,KAAK,CAAC,IAAI,CAAC,IAAI,EAAE,IAAI,CAAC,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAC;YACnD,MAAM,SAAS,CAAC,IAAI,EAAE,IAAI,EAAE,OAAO,CAAC,CAAC;YACrC,KAAK,IAAI,CAAC,CAAC;QACb,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,MAAM,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,KAAK,CAAC,IAAI,EAAE,KAAK,EAAE,KAAK,YAAY,KAAK,CAAC,CAAC,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC,CAAC,MAAM,CAAC,KAAK,CAAC,EAAE,CAAC,CAAC;QACnG,CAAC;IACH,CAAC;IAED,OAAO,EAAE,KAAK,EAAE,MAAM,EAAE,SAAS,EAAE,UAAU,EAAE,IAAI,CAAC,GAAG,EAAE,GAAG,OAAO,EAAE,CAAC;AACxE,CAAC;AAED,MAAM,UAAU,gBAAgB,CAAC,MAAc,EAAE,IAAY;IAC3D,OAAO,OAAO,CAAC,MAAM,CAAC,CAAC,UAAU,CAAC,OAAO,CAAC,IAAI,CAAC,GAAG,GAAG,CAAC,IAAI,OAAO,CAAC,MAAM,CAAC,KAAK,OAAO,CAAC,IAAI,CAAC,CAAC;AAC9F,CAAC"}
@@ -0,0 +1,63 @@
1
+ import type { ThemeComponent, RenderContext, PageProps } from '@oktis-works/theme-sdk';
2
+ type TemplateNode = {
3
+ type: 'text';
4
+ value: string;
5
+ } | {
6
+ type: 'variable';
7
+ name: string;
8
+ raw: boolean;
9
+ } | {
10
+ type: 'each';
11
+ key: string;
12
+ body: TemplateNode[];
13
+ } | {
14
+ type: 'if';
15
+ condition: string;
16
+ body: TemplateNode[];
17
+ };
18
+ interface CompiledTemplate {
19
+ nodes: TemplateNode[];
20
+ }
21
+ interface AssetEntry {
22
+ url: string;
23
+ preload?: boolean;
24
+ }
25
+ interface RenderedPage {
26
+ html: string;
27
+ styles: AssetEntry[];
28
+ scripts: AssetEntry[];
29
+ }
30
+ export declare class ThemeRenderer {
31
+ private layoutCache;
32
+ private componentCache;
33
+ private templateCache;
34
+ private readonly templatesDir?;
35
+ constructor(options?: {
36
+ templatesDir?: string;
37
+ });
38
+ render(page: PageProps, context: RenderContext): Promise<RenderedPage>;
39
+ resolveLayout(name: string): Promise<string>;
40
+ resolveComponent(name: string): Promise<ThemeComponent>;
41
+ renderPartial(name: string, props: Record<string, unknown>): Promise<string>;
42
+ applyStyles(html: string, styles: AssetEntry[], opts?: {
43
+ themeName?: string;
44
+ }): string;
45
+ /**
46
+ * Envelopa body/html com atributo data-theme para isolamento fino.
47
+ * Todo CSS escopado via style-engine usa [data-theme="nome"] como prefixo,
48
+ * garantindo que não vaze para o admin (admin não possui data-theme).
49
+ */
50
+ wrapWithThemeScope(html: string, themeName: string): string;
51
+ compile(template: string): CompiledTemplate;
52
+ registerLayout(name: string, template: string): void;
53
+ registerComponent(component: ThemeComponent): void;
54
+ private parse;
55
+ private findMatchingEnd;
56
+ private execute;
57
+ private renderNode;
58
+ private resolveVariable;
59
+ private escapeHtml;
60
+ private loadTemplate;
61
+ }
62
+ export {};
63
+ //# sourceMappingURL=renderer.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"renderer.d.ts","sourceRoot":"","sources":["../src/renderer.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,cAAc,EAAE,aAAa,EAAE,SAAS,EAAE,MAAM,wBAAwB,CAAC;AAGvF,KAAK,YAAY,GACb;IAAE,IAAI,EAAE,MAAM,CAAC;IAAC,KAAK,EAAE,MAAM,CAAA;CAAE,GAC/B;IAAE,IAAI,EAAE,UAAU,CAAC;IAAC,IAAI,EAAE,MAAM,CAAC;IAAC,GAAG,EAAE,OAAO,CAAA;CAAE,GAChD;IAAE,IAAI,EAAE,MAAM,CAAC;IAAC,GAAG,EAAE,MAAM,CAAC;IAAC,IAAI,EAAE,YAAY,EAAE,CAAA;CAAE,GACnD;IAAE,IAAI,EAAE,IAAI,CAAC;IAAC,SAAS,EAAE,MAAM,CAAC;IAAC,IAAI,EAAE,YAAY,EAAE,CAAA;CAAE,CAAC;AAE5D,UAAU,gBAAgB;IACxB,KAAK,EAAE,YAAY,EAAE,CAAC;CACvB;AAED,UAAU,UAAU;IAClB,GAAG,EAAE,MAAM,CAAC;IACZ,OAAO,CAAC,EAAE,OAAO,CAAC;CACnB;AAED,UAAU,YAAY;IACpB,IAAI,EAAE,MAAM,CAAC;IACb,MAAM,EAAE,UAAU,EAAE,CAAC;IACrB,OAAO,EAAE,UAAU,EAAE,CAAC;CACvB;AAED,qBAAa,aAAa;IACxB,OAAO,CAAC,WAAW,CAA6B;IAChD,OAAO,CAAC,cAAc,CAAqC;IAC3D,OAAO,CAAC,aAAa,CAAuC;IAC5D,OAAO,CAAC,QAAQ,CAAC,YAAY,CAAC,CAAS;gBAE3B,OAAO,GAAE;QAAE,YAAY,CAAC,EAAE,MAAM,CAAA;KAAO;IAI7C,MAAM,CAAC,IAAI,EAAE,SAAS,EAAE,OAAO,EAAE,aAAa,GAAG,OAAO,CAAC,YAAY,CAAC;IA4BtE,aAAa,CAAC,IAAI,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC;IAO5C,gBAAgB,CAAC,IAAI,EAAE,MAAM,GAAG,OAAO,CAAC,cAAc,CAAC;IAOvD,aAAa,CAAC,IAAI,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,OAAO,CAAC,MAAM,CAAC;IAUlF,WAAW,CAAC,IAAI,EAAE,MAAM,EAAE,MAAM,EAAE,UAAU,EAAE,EAAE,IAAI,CAAC,EAAE;QAAE,SAAS,CAAC,EAAE,MAAM,CAAA;KAAE,GAAG,MAAM;IAmBtF;;;;OAIG;IACH,kBAAkB,CAAC,IAAI,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,GAAG,MAAM;IAa3D,OAAO,CAAC,QAAQ,EAAE,MAAM,GAAG,gBAAgB;IAU3C,cAAc,CAAC,IAAI,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,GAAG,IAAI;IAIpD,iBAAiB,CAAC,SAAS,EAAE,cAAc,GAAG,IAAI;IAIlD,OAAO,CAAC,KAAK;IA2Cb,OAAO,CAAC,eAAe;IAmBvB,OAAO,CAAC,OAAO;IAIf,OAAO,CAAC,UAAU;IA0BlB,OAAO,CAAC,eAAe;IAUvB,OAAO,CAAC,UAAU;YAIJ,YAAY;CAW3B"}
@@ -0,0 +1,225 @@
1
+ import { readFileSync } from 'node:fs';
2
+ import { isAbsolute, resolve } from 'node:path';
3
+ import { runWithCurrentContent } from '@oktis-works/theme-sdk';
4
+ export class ThemeRenderer {
5
+ layoutCache = new Map();
6
+ componentCache = new Map();
7
+ templateCache = new Map();
8
+ templatesDir;
9
+ constructor(options = {}) {
10
+ this.templatesDir = options.templatesDir;
11
+ }
12
+ async render(page, context) {
13
+ const layoutTemplate = await this.resolveLayout(page.meta?.['layout'] ?? 'default');
14
+ const compiled = this.compile(layoutTemplate);
15
+ const merged = { title: page.title, content: page.content };
16
+ if (page.meta) {
17
+ for (const [k, v] of Object.entries(page.meta))
18
+ merged[k] = v;
19
+ }
20
+ const body = runWithCurrentContent(context.record ?? {}, () => this.execute(compiled, merged));
21
+ const styles = [];
22
+ const scripts = [];
23
+ if (context.settings['styles']) {
24
+ for (const s of context.settings['styles']) {
25
+ styles.push({ url: s });
26
+ }
27
+ }
28
+ if (context.settings['scripts']) {
29
+ for (const s of context.settings['scripts']) {
30
+ scripts.push({ url: s });
31
+ }
32
+ }
33
+ return { html: body, styles, scripts };
34
+ }
35
+ async resolveLayout(name) {
36
+ if (this.layoutCache.has(name)) {
37
+ return this.layoutCache.get(name);
38
+ }
39
+ throw new Error(`Layout not found: ${name}`);
40
+ }
41
+ async resolveComponent(name) {
42
+ if (this.componentCache.has(name)) {
43
+ return this.componentCache.get(name);
44
+ }
45
+ throw new Error(`Component not found: ${name}`);
46
+ }
47
+ async renderPartial(name, props) {
48
+ const component = await this.resolveComponent(name);
49
+ if (!component.file) {
50
+ throw new Error(`Component file not set: ${name}`);
51
+ }
52
+ const template = await this.loadTemplate(component.file);
53
+ const compiled = this.compile(template);
54
+ return this.execute(compiled, props);
55
+ }
56
+ applyStyles(html, styles, opts) {
57
+ if (styles.length === 0)
58
+ return html;
59
+ const links = styles
60
+ .map(s => {
61
+ const href = `href="${this.escapeHtml(s.url)}"`;
62
+ const dataTheme = opts?.themeName ? ` data-theme-style="${this.escapeHtml(opts.themeName)}"` : '';
63
+ return s.preload
64
+ ? `<link rel="preload" as="style" ${href} onload="this.rel='stylesheet'"${dataTheme} />`
65
+ : `<link rel="stylesheet" ${href}${dataTheme} />`;
66
+ })
67
+ .join('\n');
68
+ if (html.includes('</head>')) {
69
+ return html.replace('</head>', `${links}\n</head>`);
70
+ }
71
+ return `${links}\n${html}`;
72
+ }
73
+ /**
74
+ * Envelopa body/html com atributo data-theme para isolamento fino.
75
+ * Todo CSS escopado via style-engine usa [data-theme="nome"] como prefixo,
76
+ * garantindo que não vaze para o admin (admin não possui data-theme).
77
+ */
78
+ wrapWithThemeScope(html, themeName) {
79
+ const attr = `data-theme="${this.escapeHtml(themeName)}"`;
80
+ // injeta no <main> ou <body> ou cria wrapper
81
+ if (html.includes('data-theme='))
82
+ return html;
83
+ if (html.includes('<main')) {
84
+ return html.replace(/<main\b/, `<main ${attr}`);
85
+ }
86
+ if (html.includes('<body')) {
87
+ return html.replace(/<body\b/, `<body ${attr}`);
88
+ }
89
+ return `<div ${attr}>${html}</div>`;
90
+ }
91
+ compile(template) {
92
+ if (this.templateCache.has(template)) {
93
+ return this.templateCache.get(template);
94
+ }
95
+ const nodes = this.parse(template, 0);
96
+ const compiled = { nodes };
97
+ this.templateCache.set(template, compiled);
98
+ return compiled;
99
+ }
100
+ registerLayout(name, template) {
101
+ this.layoutCache.set(name, template);
102
+ }
103
+ registerComponent(component) {
104
+ this.componentCache.set(component.name, component);
105
+ }
106
+ parse(template, start) {
107
+ const nodes = [];
108
+ let i = start;
109
+ while (i < template.length) {
110
+ if (template[i] === '{' && template[i + 1] === '{') {
111
+ const closeIndex = template.indexOf('}}', i + 2);
112
+ if (closeIndex === -1) {
113
+ nodes.push({ type: 'text', value: template.slice(i) });
114
+ break;
115
+ }
116
+ const raw = template[i + 2] === '{' && template[closeIndex - 1] === '}';
117
+ const innerStart = i + (raw ? 3 : 2);
118
+ const expression = template.slice(innerStart, raw ? closeIndex - 1 : closeIndex).trim();
119
+ if (expression.startsWith('#each ')) {
120
+ const key = expression.slice(6).trim();
121
+ const bodyEnd = this.findMatchingEnd(template, closeIndex + 2, '{{#each ', '{{/each}}');
122
+ const body = this.parse(template.slice(closeIndex + 2, bodyEnd), 0);
123
+ nodes.push({ type: 'each', key, body });
124
+ i = bodyEnd + '{{/each}}'.length;
125
+ }
126
+ else if (expression.startsWith('#if ')) {
127
+ const condition = expression.slice(4).trim();
128
+ const bodyEnd = this.findMatchingEnd(template, closeIndex + 2, '{{#if ', '{{/if}}');
129
+ const body = this.parse(template.slice(closeIndex + 2, bodyEnd), 0);
130
+ nodes.push({ type: 'if', condition, body });
131
+ i = bodyEnd + '{{/if}}'.length;
132
+ }
133
+ else {
134
+ nodes.push({ type: 'variable', name: expression, raw });
135
+ i = closeIndex + 2;
136
+ }
137
+ }
138
+ else {
139
+ let nextTag = template.indexOf('{{', i + 1);
140
+ if (nextTag === -1)
141
+ nextTag = template.length;
142
+ const text = template.slice(i, nextTag);
143
+ if (text)
144
+ nodes.push({ type: 'text', value: text });
145
+ i = nextTag;
146
+ }
147
+ }
148
+ return nodes;
149
+ }
150
+ findMatchingEnd(template, start, openTag, endTag) {
151
+ let depth = 1;
152
+ let i = start;
153
+ while (i < template.length) {
154
+ const nextOpen = template.indexOf(openTag, i);
155
+ const nextEnd = template.indexOf(endTag, i);
156
+ if (nextEnd === -1)
157
+ return template.length;
158
+ if (nextOpen !== -1 && nextOpen < nextEnd) {
159
+ depth++;
160
+ i = nextOpen + openTag.length;
161
+ }
162
+ else {
163
+ depth--;
164
+ if (depth === 0)
165
+ return nextEnd;
166
+ i = nextEnd + endTag.length;
167
+ }
168
+ }
169
+ return template.length;
170
+ }
171
+ execute(compiled, context) {
172
+ return compiled.nodes.map(node => this.renderNode(node, context)).join('');
173
+ }
174
+ renderNode(node, context) {
175
+ switch (node.type) {
176
+ case 'text':
177
+ return node.value;
178
+ case 'variable': {
179
+ const value = String(this.resolveVariable(node.name, context) ?? '');
180
+ return node.raw ? value : this.escapeHtml(value);
181
+ }
182
+ case 'each': {
183
+ const collection = this.resolveVariable(node.key, context);
184
+ if (!Array.isArray(collection))
185
+ return '';
186
+ return collection.map(item => {
187
+ const subContext = { ...context, ...item };
188
+ return node.body.map(n => this.renderNode(n, subContext)).join('');
189
+ }).join('');
190
+ }
191
+ case 'if': {
192
+ const val = this.resolveVariable(node.condition, context);
193
+ if (val && val !== 'false' && val !== '0') {
194
+ return node.body.map(n => this.renderNode(n, context)).join('');
195
+ }
196
+ return '';
197
+ }
198
+ }
199
+ }
200
+ resolveVariable(name, context) {
201
+ const parts = name.split('.');
202
+ let current = context;
203
+ for (const part of parts) {
204
+ if (current === null || current === undefined)
205
+ return '';
206
+ current = current[part];
207
+ }
208
+ return current ?? '';
209
+ }
210
+ escapeHtml(str) {
211
+ return str.replace(/&/g, '&amp;').replace(/"/g, '&quot;').replace(/</g, '&lt;').replace(/>/g, '&gt;');
212
+ }
213
+ async loadTemplate(file) {
214
+ if (!this.templatesDir) {
215
+ throw new Error(`Template file loading not configured: register "${file}" via registerLayout/registerComponent or provide templatesDir`);
216
+ }
217
+ const base = isAbsolute(this.templatesDir) ? this.templatesDir : resolve(process.cwd(), this.templatesDir);
218
+ const target = resolve(base, file);
219
+ if (!target.startsWith(base)) {
220
+ throw new Error(`Template path escapes templates directory: ${file}`);
221
+ }
222
+ return readFileSync(target, 'utf-8');
223
+ }
224
+ }
225
+ //# sourceMappingURL=renderer.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"renderer.js","sourceRoot":"","sources":["../src/renderer.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,31 @@
1
+ import type { ThemeManifest } from '@oktis-works/theme-sdk';
2
+ import { type TemplateContext, type ResolvedTemplate } from './template-resolver.js';
3
+ export interface ResolvedComponent {
4
+ name: string;
5
+ file: string;
6
+ source: 'theme' | 'plugin' | 'core';
7
+ }
8
+ export declare class ThemeResolver {
9
+ private registry;
10
+ private activeTheme;
11
+ private activeThemesByTenant;
12
+ private inheritanceCache;
13
+ resolveTheme(tenantId: string): Promise<ThemeManifest>;
14
+ getActiveTheme(): string | null;
15
+ setActiveTheme(name: string): void;
16
+ setActiveThemeForTenant(tenantId: string, name: string): void;
17
+ clearActiveThemeForTenant(tenantId: string): void;
18
+ getThemeManifest(name: string): ThemeManifest | null;
19
+ loadTheme(manifest: ThemeManifest, path: string): void;
20
+ getInheritanceChain(themeName: string): string[];
21
+ resolveComponent(name: string, overrides?: Map<string, ResolvedComponent>): ResolvedComponent;
22
+ listComponents(): ResolvedComponent[];
23
+ getThemeAssets(themeName: string): string[];
24
+ /**
25
+ * Resolve um template da hierarquia (FEAT-094) considerando os arquivos
26
+ * declarados no manifest do tema ativo e sua cadeia de herança.
27
+ */
28
+ resolve(context: TemplateContext): Promise<ResolvedTemplate>;
29
+ clearCache(): void;
30
+ }
31
+ //# sourceMappingURL=resolver.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"resolver.d.ts","sourceRoot":"","sources":["../src/resolver.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,wBAAwB,CAAC;AAC5D,OAAO,EAA6B,KAAK,eAAe,EAAE,KAAK,gBAAgB,EAAE,MAAM,wBAAwB,CAAC;AAQhH,MAAM,WAAW,iBAAiB;IAChC,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,EAAE,MAAM,CAAC;IACb,MAAM,EAAE,OAAO,GAAG,QAAQ,GAAG,MAAM,CAAC;CACrC;AAED,qBAAa,aAAa;IACxB,OAAO,CAAC,QAAQ,CAAoC;IACpD,OAAO,CAAC,WAAW,CAAuB;IAC1C,OAAO,CAAC,oBAAoB,CAA6B;IACzD,OAAO,CAAC,gBAAgB,CAA+B;IAEjD,YAAY,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC,aAAa,CAAC;IAS5D,cAAc,IAAI,MAAM,GAAG,IAAI;IAI/B,cAAc,CAAC,IAAI,EAAE,MAAM,GAAG,IAAI;IAIlC,uBAAuB,CAAC,QAAQ,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,GAAG,IAAI;IAI7D,yBAAyB,CAAC,QAAQ,EAAE,MAAM,GAAG,IAAI;IAIjD,gBAAgB,CAAC,IAAI,EAAE,MAAM,GAAG,aAAa,GAAG,IAAI;IAKpD,SAAS,CAAC,QAAQ,EAAE,aAAa,EAAE,IAAI,EAAE,MAAM,GAAG,IAAI;IAStD,mBAAmB,CAAC,SAAS,EAAE,MAAM,GAAG,MAAM,EAAE;IAsBhD,gBAAgB,CAAC,IAAI,EAAE,MAAM,EAAE,SAAS,CAAC,EAAE,GAAG,CAAC,MAAM,EAAE,iBAAiB,CAAC,GAAG,iBAAiB;IAuB7F,cAAc,IAAI,iBAAiB,EAAE;IAgBrC,cAAc,CAAC,SAAS,EAAE,MAAM,GAAG,MAAM,EAAE;IAK3C;;;OAGG;IACG,OAAO,CAAC,OAAO,EAAE,eAAe,GAAG,OAAO,CAAC,gBAAgB,CAAC;IAsBlE,UAAU,IAAI,IAAI;CAGnB"}