@crewx/sdk 0.8.0-rc.78 → 0.8.0-rc.80

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.
Files changed (82) hide show
  1. package/dist/plugin/plugin-provider.js +1 -1
  2. package/dist/provider/bridge.js +1 -0
  3. package/package.json +1 -1
  4. package/dist/esm/agent/resolver.js +0 -41
  5. package/dist/esm/boxing/box-storage.interface.js +0 -5
  6. package/dist/esm/boxing/box.service.js +0 -69
  7. package/dist/esm/boxing/box.types.js +0 -5
  8. package/dist/esm/boxing/context-builder.js +0 -76
  9. package/dist/esm/client/CrewxClient.js +0 -82
  10. package/dist/esm/client/index.js +0 -2
  11. package/dist/esm/config/loader.browser.js +0 -54
  12. package/dist/esm/config/loader.js +0 -77
  13. package/dist/esm/events/TypedEventEmitter.js +0 -61
  14. package/dist/esm/events/types.js +0 -8
  15. package/dist/esm/facade/Crewx.browser.js +0 -310
  16. package/dist/esm/facade/Crewx.js +0 -941
  17. package/dist/esm/hooks/define.js +0 -10
  18. package/dist/esm/hooks/dispatch.js +0 -76
  19. package/dist/esm/hooks/index.js +0 -6
  20. package/dist/esm/hooks/observer.js +0 -56
  21. package/dist/esm/hooks/plugin.js +0 -12
  22. package/dist/esm/hooks/types.js +0 -9
  23. package/dist/esm/index.browser.js +0 -15
  24. package/dist/esm/index.js +0 -60
  25. package/dist/esm/layout/loader.js +0 -268
  26. package/dist/esm/layout/props-validator.js +0 -297
  27. package/dist/esm/layout/renderer.js +0 -180
  28. package/dist/esm/layout/types.js +0 -31
  29. package/dist/esm/parallel/agent-runtime.js +0 -21
  30. package/dist/esm/parallel/helpers.js +0 -214
  31. package/dist/esm/parallel/index.js +0 -5
  32. package/dist/esm/parallel/parallel-runner.js +0 -221
  33. package/dist/esm/parallel/types.js +0 -5
  34. package/dist/esm/parsers/agent-call.util.js +0 -15
  35. package/dist/esm/parsers/claude.parser.js +0 -64
  36. package/dist/esm/parsers/codex.parser.js +0 -97
  37. package/dist/esm/parsers/copilot.parser.js +0 -63
  38. package/dist/esm/parsers/gemini.parser.js +0 -43
  39. package/dist/esm/parsers/opencode.parser.js +0 -73
  40. package/dist/esm/parsers/router.js +0 -53
  41. package/dist/esm/platform/BrowserFsAdapter.js +0 -80
  42. package/dist/esm/platform/IFsAdapter.js +0 -2
  43. package/dist/esm/platform/NodeFsAdapter.js +0 -34
  44. package/dist/esm/plugin/plugin-provider.js +0 -202
  45. package/dist/esm/plugin/types.js +0 -8
  46. package/dist/esm/plugin.js +0 -25
  47. package/dist/esm/provider/bridge.browser.js +0 -43
  48. package/dist/esm/provider/bridge.js +0 -373
  49. package/dist/esm/provider/parse-usage.js +0 -80
  50. package/dist/esm/provider/register-api.js +0 -21
  51. package/dist/esm/provider/vercel-runtime.js +0 -310
  52. package/dist/esm/remote/index.js +0 -10
  53. package/dist/esm/remote/remote-agent-manager.js +0 -194
  54. package/dist/esm/remote/remote-provider.js +0 -98
  55. package/dist/esm/remote/remote-transport.js +0 -79
  56. package/dist/esm/remote/types.js +0 -8
  57. package/dist/esm/server/auth.js +0 -31
  58. package/dist/esm/server/handler.js +0 -72
  59. package/dist/esm/server/index.js +0 -5
  60. package/dist/esm/server/tool-adapter.js +0 -92
  61. package/dist/esm/template/engine.js +0 -100
  62. package/dist/esm/template/helpers/exec.browser.js +0 -31
  63. package/dist/esm/template/helpers/exec.js +0 -220
  64. package/dist/esm/template/helpers/fenced_code.js +0 -17
  65. package/dist/esm/template/helpers/include.js +0 -20
  66. package/dist/esm/template/helpers/p1p2.js +0 -83
  67. package/dist/esm/template/loader/DocumentLoader.js +0 -124
  68. package/dist/esm/template/types.js +0 -5
  69. package/dist/esm/tools/delegate.js +0 -57
  70. package/dist/esm/tools/index.js +0 -5
  71. package/dist/esm/tools/node/builtin.js +0 -541
  72. package/dist/esm/tools/node/index.js +0 -54
  73. package/dist/esm/types/index.js +0 -27
  74. package/dist/esm/types/task-log.types.js +0 -5
  75. package/dist/esm/utils/env-defaults.js +0 -23
  76. package/dist/esm/utils/glob-match.js +0 -38
  77. package/dist/esm/utils/id.js +0 -46
  78. package/dist/esm/utils/workspace.js +0 -21
  79. package/dist/parsers/api.parser.d.ts +0 -10
  80. package/dist/parsers/api.parser.js +0 -26
  81. package/dist/provider/mastra-runtime.d.ts +0 -45
  82. package/dist/provider/mastra-runtime.js +0 -208
@@ -1,10 +0,0 @@
1
- import { ToolObserverPlugin } from './observer';
2
- export function definePlugin(def) {
3
- return new (class extends ToolObserverPlugin {
4
- name = def.name;
5
- version = def.version;
6
- on = def.on;
7
- run = def.run;
8
- })();
9
- }
10
- //# sourceMappingURL=define.js.map
@@ -1,76 +0,0 @@
1
- import { resolve, relative } from 'path';
2
- const MAX_REASON_LENGTH = 200;
3
- export function sanitizeDenyReason(reason) {
4
- const cleaned = reason.replace(/[\x00-\x1f\x7f]/g, '');
5
- if (cleaned.length <= MAX_REASON_LENGTH) {
6
- return cleaned;
7
- }
8
- return cleaned.slice(0, MAX_REASON_LENGTH - 11) + ' [redacted]';
9
- }
10
- export function isPathSafe(pluginPath, projectRoot) {
11
- const resolved = resolve(pluginPath);
12
- const root = resolve(projectRoot);
13
- const rel = relative(root, resolved);
14
- if (rel.startsWith('..') || resolve(resolved).startsWith('/etc/') || resolve(resolved).startsWith('/usr/')) {
15
- return false;
16
- }
17
- if (resolved.includes('node_modules')) {
18
- return false;
19
- }
20
- return true;
21
- }
22
- export function buildHookContext(input, cwd) {
23
- return {
24
- event: 'beforeTool',
25
- traceId: input.tool_use_id || '',
26
- agent: { id: '', role: '', team: '' },
27
- provider: 'cli/claude',
28
- thread: { id: '' },
29
- tool: {
30
- name: input.tool_name,
31
- rawName: input.tool_name,
32
- input: input.tool_input,
33
- },
34
- cwd: cwd || input.cwd,
35
- sessionId: input.session_id,
36
- pass: () => ({ type: 'pass' }),
37
- deny: (r) => ({ type: 'deny', reason: r }),
38
- inject: (m) => ({ type: 'inject', message: m }),
39
- modify: (p) => ({ type: 'modify', patch: p }),
40
- };
41
- }
42
- export async function evaluateHook(plugin, input, cwd) {
43
- const ctx = buildHookContext(input, cwd);
44
- const result = await plugin.run(ctx);
45
- const baseOutput = {
46
- hookSpecificOutput: {
47
- hookEventName: input.hook_event_name,
48
- permissionDecision: 'allow',
49
- },
50
- };
51
- switch (result.type) {
52
- case 'pass':
53
- return { exitCode: 0, stdout: baseOutput };
54
- case 'deny': {
55
- const sanitizedReason = sanitizeDenyReason(result.reason);
56
- return {
57
- exitCode: 2,
58
- stdout: {
59
- hookSpecificOutput: {
60
- hookEventName: input.hook_event_name,
61
- permissionDecision: 'deny',
62
- permissionDecisionReason: sanitizedReason,
63
- },
64
- },
65
- };
66
- }
67
- case 'inject':
68
- case 'modify':
69
- console.error(`[crewx] Hook result type '${result.type}' is not supported in Phase 0. ` +
70
- `Plugin: ${plugin.name}. Treating as pass.`);
71
- return { exitCode: 0, stdout: baseOutput };
72
- default:
73
- return { exitCode: 0, stdout: baseOutput };
74
- }
75
- }
76
- //# sourceMappingURL=dispatch.js.map
@@ -1,6 +0,0 @@
1
- export { ToolObserverPlugin } from './observer';
2
- export { HookPlugin, defineHookPlugin } from './plugin';
3
- export { definePlugin } from './define';
4
- export { Tools } from './types';
5
- export { evaluateHook, sanitizeDenyReason, isPathSafe, buildHookContext, } from './dispatch';
6
- //# sourceMappingURL=index.js.map
@@ -1,56 +0,0 @@
1
- import { CrewxPlugin } from '../plugin';
2
- export class ToolObserverPlugin extends CrewxPlugin {
3
- unsubs = [];
4
- attach(crewx) {
5
- if (this.on.beforeTool) {
6
- const unsub = crewx.on('tool:observed:before', async (e) => {
7
- if (!this.matchesTool(this.on.beforeTool, e.tool.name))
8
- return;
9
- const ctx = this.buildContext('beforeTool', e);
10
- await this.run(ctx);
11
- });
12
- this.unsubs.push(unsub);
13
- }
14
- if (this.on.afterTool) {
15
- const unsub = crewx.on('tool:observed:after', async (e) => {
16
- if (!this.matchesTool(this.on.afterTool, e.tool.name))
17
- return;
18
- const ctx = this.buildContext('afterTool', e);
19
- await this.run(ctx);
20
- });
21
- this.unsubs.push(unsub);
22
- }
23
- }
24
- async detach(_crewx) {
25
- for (const unsub of this.unsubs)
26
- unsub();
27
- this.unsubs = [];
28
- }
29
- matchesTool(filter, toolName) {
30
- if (filter === true)
31
- return true;
32
- return filter.includes(toolName);
33
- }
34
- buildContext(event, e) {
35
- return {
36
- event,
37
- traceId: e.traceId,
38
- agent: {
39
- id: e.agentId || e.agentRef,
40
- role: '',
41
- team: '',
42
- },
43
- provider: e.provider,
44
- thread: { id: e.threadId || '' },
45
- tool: {
46
- name: e.tool.name,
47
- rawName: e.tool.rawName,
48
- input: 'input' in e.tool ? e.tool.input : undefined,
49
- },
50
- cwd: process.cwd(),
51
- sessionId: e.sessionId || '',
52
- pass: () => ({ type: 'pass' }),
53
- };
54
- }
55
- }
56
- //# sourceMappingURL=observer.js.map
@@ -1,12 +0,0 @@
1
- export class HookPlugin {
2
- capabilities = { required: [] };
3
- }
4
- export function defineHookPlugin(def) {
5
- return new (class extends HookPlugin {
6
- name = def.name;
7
- version = def.version;
8
- capabilities = def.capabilities ?? { required: [] };
9
- run = def.run;
10
- })();
11
- }
12
- //# sourceMappingURL=plugin.js.map
@@ -1,9 +0,0 @@
1
- export const Tools = {
2
- FileRead: 'file.read',
3
- FileWrite: 'file.write',
4
- FileEdit: 'file.edit',
5
- Shell: 'shell',
6
- Search: 'search',
7
- Other: 'other',
8
- };
9
- //# sourceMappingURL=types.js.map
@@ -1,15 +0,0 @@
1
- /**
2
- * @crewx/sdk browser entry point.
3
- *
4
- * Exports only browser-safe modules — no Node.js dependencies
5
- * (child_process, fs, path, crypto, events).
6
- */
7
- // Browser-safe facade
8
- export { Crewx } from './facade/Crewx.browser.js';
9
- // Browser-safe provider bridge (registry only, no CLI spawn)
10
- export { registerProviderFactory, createProvider, ProviderError } from './provider/bridge.browser.js';
11
- // Config — browser-safe (no fs import)
12
- export { parseYamlContent, ConfigLoadError } from './config/loader.browser.js';
13
- // Platform adapters
14
- export { BrowserFsAdapter } from './platform/BrowserFsAdapter.js';
15
- //# sourceMappingURL=index.browser.js.map
package/dist/esm/index.js DELETED
@@ -1,60 +0,0 @@
1
- /**
2
- * @crewx/sdk public API surface.
3
- */
4
- // Main facade
5
- export { Crewx } from './facade/Crewx';
6
- // Plugin system
7
- export { CrewxPlugin } from './plugin';
8
- // Event system
9
- export { TypedEventEmitter } from './events/TypedEventEmitter';
10
- // Layout system
11
- export { LayoutLoader } from './layout/loader';
12
- export { LayoutRenderer } from './layout/renderer';
13
- export { PropsValidator } from './layout/props-validator';
14
- export { LayoutLoadError, PropsValidationError } from './layout/types';
15
- // Template engine
16
- export { TemplateEngine } from './template/engine';
17
- // Document loader
18
- export { DocumentLoader } from './template/loader/DocumentLoader';
19
- export { NodeFsAdapter, defaultFsAdapter } from './platform/NodeFsAdapter';
20
- export { BrowserFsAdapter } from './platform/BrowserFsAdapter';
21
- // P1/P2 helpers (exported for direct use if needed)
22
- export { truncateHelper, lengthHelper, escapeHandlebarsHelper, formatFileSizeHelper, formatTimestampHelper, } from './template/helpers/p1p2';
23
- // Exec audit log control
24
- export { setAuditVerbose } from './template/helpers/exec';
25
- // Config utilities
26
- export { loadYamlFile, parseYamlContent, ConfigLoadError } from './config/loader';
27
- // Agent utilities
28
- export { resolveAgent, AgentNotFoundError } from './agent/resolver';
29
- // Provider utilities
30
- export { createProvider, ProviderError, ClientToolCallRequiredError, registerProviderFactory } from './provider/bridge';
31
- export { VercelProviderRuntime } from './provider/vercel-runtime';
32
- export { registerApiProviders } from './provider/register-api';
33
- // Tools
34
- export { createDelegateTool } from './tools/delegate';
35
- // Env utilities
36
- export { resolveCrewxCli, resolveCrewxWorkspace } from './utils/env-defaults';
37
- // ID utilities (backward-compat for @crewx/* built-in packages)
38
- export { generateId, generateFingerprint } from './utils/id';
39
- // Workspace utilities
40
- export { hashWorkspaceId, normalizeWorkspacePath } from './utils/workspace';
41
- // Boxing module
42
- export { SdkBoxService } from './boxing/box.service';
43
- export { buildContext } from './boxing/context-builder';
44
- // Parsers
45
- export { parseStdoutEvent } from './parsers/router';
46
- // Provider utilities
47
- export { parseUsage } from './provider/parse-usage';
48
- // Parallel execution
49
- export { ParallelRunner, ParallelRunnerTimeoutError } from './parallel/parallel-runner';
50
- export { runQueriesParallel, runExecutesParallel } from './parallel/helpers';
51
- export { AgentRuntime } from './parallel/agent-runtime';
52
- // Plugin provider module
53
- export { PluginProviderRuntime, createPluginProviderFactory } from './plugin/plugin-provider';
54
- // Remote agent module
55
- export { RemoteProviderRuntime, createRemoteProviderFactory } from './remote/remote-provider';
56
- export { RemoteAgentManager } from './remote/remote-agent-manager';
57
- export { McpHttpTransport } from './remote/remote-transport';
58
- // Server module (MCP handler)
59
- export { createHandler } from './server/handler';
60
- //# sourceMappingURL=index.js.map
@@ -1,268 +0,0 @@
1
- /**
2
- * LayoutLoader — loads layout templates from templates/agents/*.yaml files.
3
- * Ported 1:1 from packages/sdk-bak/src/services/layout-loader.service.ts.
4
- * Only import paths and DEFAULT_OPTIONS.templatesPath are changed.
5
- */
6
- import { readFileSync, readdirSync, existsSync } from 'fs';
7
- import * as path from 'path';
8
- import { load as loadYaml } from 'js-yaml';
9
- import { LayoutLoadError, } from './types';
10
- /**
11
- * Default loader options — points to SDK's bundled templates directory.
12
- */
13
- const DEFAULT_OPTIONS = {
14
- templatesPath: path.join(__dirname, '../../../templates/agents'),
15
- validationMode: 'lenient',
16
- fallbackLayoutId: 'crewx/default',
17
- };
18
- /**
19
- * Layout loader service.
20
- * Loads and caches layout definitions from YAML files.
21
- * Provides fallback mechanism and prop override support.
22
- */
23
- export class LayoutLoader {
24
- layouts = new Map();
25
- options;
26
- constructor(options) {
27
- this.options = { ...DEFAULT_OPTIONS, ...options };
28
- this.loadAllLayouts();
29
- }
30
- /**
31
- * Load a layout by ID with optional props override.
32
- */
33
- load(layoutId, propsOverride) {
34
- let layout = this.layouts.get(layoutId);
35
- if (!layout) {
36
- const normalizedId = this.normalizeLayoutId(layoutId);
37
- layout = this.layouts.get(normalizedId);
38
- }
39
- if (!layout) {
40
- console.warn(`Layout not found: ${layoutId}, falling back to ${this.options.fallbackLayoutId}`);
41
- layout = this.layouts.get(this.options.fallbackLayoutId);
42
- if (!layout) {
43
- throw new LayoutLoadError(`Fallback layout not found: ${this.options.fallbackLayoutId}`, this.options.fallbackLayoutId);
44
- }
45
- }
46
- if (propsOverride && Object.keys(propsOverride).length > 0) {
47
- return {
48
- ...layout,
49
- defaultProps: { ...layout.defaultProps, ...propsOverride },
50
- };
51
- }
52
- return layout;
53
- }
54
- getLayoutIds() {
55
- return Array.from(this.layouts.keys());
56
- }
57
- hasLayout(layoutId) {
58
- if (this.layouts.has(layoutId))
59
- return true;
60
- const normalizedId = this.normalizeLayoutId(layoutId);
61
- return this.layouts.has(normalizedId);
62
- }
63
- reload() {
64
- this.layouts.clear();
65
- this.loadAllLayouts();
66
- }
67
- /**
68
- * Register or override a layout at runtime.
69
- */
70
- registerLayout(layoutId, layoutConfig) {
71
- if (!layoutId || typeof layoutId !== 'string') {
72
- throw new LayoutLoadError('Layout ID must be a non-empty string', layoutId);
73
- }
74
- const config = typeof layoutConfig === 'string'
75
- ? { template: layoutConfig }
76
- : layoutConfig;
77
- const template = typeof config.template === 'string' ? config.template : '';
78
- if (!template || template.trim().length === 0) {
79
- throw new LayoutLoadError(`Custom layout template is empty for ${layoutId}`, layoutId);
80
- }
81
- const propsSchemaRaw = config.propsSchema || {};
82
- const defaultPropsFromSchema = this.extractDefaultProps(propsSchemaRaw);
83
- const explicitDefaults = config.defaultProps || {};
84
- const layoutDefinition = {
85
- id: layoutId,
86
- version: config.version || '1.0.0',
87
- description: config.description || `Custom layout ${layoutId}`,
88
- template,
89
- propsSchema: this.parsePropsSchema(propsSchemaRaw),
90
- defaultProps: { ...defaultPropsFromSchema, ...explicitDefaults },
91
- };
92
- const existingLayout = this.layouts.get(layoutId);
93
- const templatesEqual = existingLayout?.template === template &&
94
- JSON.stringify(existingLayout?.defaultProps ?? {}) === JSON.stringify(layoutDefinition.defaultProps ?? {}) &&
95
- JSON.stringify(existingLayout?.propsSchema ?? {}) === JSON.stringify(layoutDefinition.propsSchema ?? {});
96
- this.layouts.set(layoutId, layoutDefinition);
97
- if (process.env.CREWX_VERBOSE === '1') {
98
- if (!existingLayout) {
99
- console.error(`Registered custom layout: ${layoutId}`);
100
- }
101
- else if (!templatesEqual) {
102
- console.error(`Updated custom layout: ${layoutId}`);
103
- }
104
- }
105
- }
106
- /**
107
- * Register multiple layouts from a map.
108
- */
109
- registerLayouts(layoutsMap) {
110
- for (const [id, config] of Object.entries(layoutsMap)) {
111
- try {
112
- this.registerLayout(id, config);
113
- }
114
- catch (error) {
115
- console.warn(`Failed to register custom layout ${id}:`, error instanceof Error ? error.message : error);
116
- }
117
- }
118
- }
119
- loadAllLayouts() {
120
- const layoutsDir = this.options.templatesPath;
121
- if (!existsSync(layoutsDir)) {
122
- throw new LayoutLoadError(`Templates directory not found: ${layoutsDir}`, undefined, new Error(`Directory does not exist: ${layoutsDir}`));
123
- }
124
- try {
125
- const files = readdirSync(layoutsDir).filter(f => f.endsWith('.yaml') || f.endsWith('.yml'));
126
- if (files.length === 0) {
127
- console.warn(`No layout files found in ${layoutsDir}`);
128
- }
129
- for (const file of files) {
130
- const layoutName = file.replace(/\.(yaml|yml)$/, '');
131
- const layoutPath = path.join(layoutsDir, file);
132
- try {
133
- const layout = this.loadLayoutFile(layoutPath, layoutName);
134
- const layoutId = `crewx/${layoutName}`;
135
- this.layouts.set(layoutId, layout);
136
- if (layoutId !== 'crewx/minimal') {
137
- if (process.env.CREWX_VERBOSE === '1')
138
- console.error(`Loaded layout: ${layoutId} from ${file}`);
139
- }
140
- }
141
- catch (error) {
142
- console.error(`Failed to load layout file ${file}:`, error);
143
- }
144
- }
145
- if (process.env.CREWX_VERBOSE === '1')
146
- console.error(`Loaded ${this.layouts.size} layouts from ${layoutsDir}`);
147
- }
148
- catch (error) {
149
- throw new LayoutLoadError(`Failed to read layouts directory: ${layoutsDir}`, undefined, error instanceof Error ? error : new Error(String(error)));
150
- }
151
- }
152
- loadLayoutFile(filePath, layoutName) {
153
- try {
154
- const content = readFileSync(filePath, 'utf-8');
155
- if (!content || content.trim().length === 0) {
156
- console.warn(`Empty YAML file: ${filePath}, will use fallback`);
157
- throw new LayoutLoadError(`Empty YAML file: ${filePath}`, layoutName, new Error('File content is empty'));
158
- }
159
- const parsed = loadYaml(content);
160
- if (!parsed || typeof parsed !== 'object') {
161
- console.warn(`Invalid YAML content in ${filePath} (parsed as ${typeof parsed}), will use fallback`);
162
- throw new LayoutLoadError(`Invalid or empty YAML in ${filePath}`, layoutName, new Error('YAML parsing returned null/undefined or non-object'));
163
- }
164
- // Format 2: layouts map (templates/agents/default.yaml format)
165
- if (parsed.layouts && typeof parsed.layouts === 'object') {
166
- const entry = this.resolveLayoutEntry(parsed.layouts, layoutName);
167
- if (!entry || entry.template.trim().length === 0) {
168
- console.warn(`Empty or missing layout template in ${filePath} for ${layoutName}`);
169
- throw new LayoutLoadError(`Layout template not found or empty in layouts map: ${layoutName}`, layoutName);
170
- }
171
- // propsSchema may be inline in the layout entry object (e.g. default.yaml) or at the top level
172
- const propsSchemaRaw = entry.propsSchema || parsed.propsSchema || {};
173
- return {
174
- id: `crewx/${layoutName}`,
175
- version: parsed.version || '1.0.0',
176
- description: parsed.description || `CrewX ${layoutName} layout`,
177
- template: entry.template,
178
- propsSchema: this.parsePropsSchema(propsSchemaRaw),
179
- defaultProps: this.extractDefaultProps(propsSchemaRaw),
180
- };
181
- }
182
- else {
183
- // Format 1: direct layout definition
184
- if (!parsed.template || (typeof parsed.template === 'string' && parsed.template.trim().length === 0)) {
185
- console.warn(`Empty or missing template field in ${filePath}`);
186
- throw new LayoutLoadError(`Layout template is missing or empty in ${filePath}`, layoutName);
187
- }
188
- return {
189
- id: parsed.id || `crewx/${layoutName}`,
190
- version: parsed.version || '1.0.0',
191
- description: parsed.description || '',
192
- template: parsed.template,
193
- propsSchema: this.parsePropsSchema(parsed.propsSchema || {}),
194
- defaultProps: this.extractDefaultProps(parsed.propsSchema || {}),
195
- };
196
- }
197
- }
198
- catch (error) {
199
- throw new LayoutLoadError(`Failed to load layout file: ${filePath}`, layoutName, error instanceof Error ? error : new Error(String(error)));
200
- }
201
- }
202
- parsePropsSchema(raw) {
203
- const schema = {};
204
- for (const [key, value] of Object.entries(raw)) {
205
- if (typeof value === 'object' && value !== null) {
206
- schema[key] = value;
207
- }
208
- }
209
- return schema;
210
- }
211
- extractDefaultProps(propsSchema) {
212
- const defaults = {};
213
- for (const [key, schema] of Object.entries(propsSchema)) {
214
- if (schema && typeof schema === 'object') {
215
- if ('defaultValue' in schema) {
216
- defaults[key] = schema.defaultValue;
217
- }
218
- else if ('default' in schema) {
219
- defaults[key] = schema.default;
220
- }
221
- }
222
- }
223
- return defaults;
224
- }
225
- normalizeLayoutId(layoutId) {
226
- if (!layoutId)
227
- return this.options.fallbackLayoutId;
228
- if (layoutId.includes('/'))
229
- return layoutId;
230
- return `crewx/${layoutId}`;
231
- }
232
- resolveLayoutEntry(layoutsMap, layoutName) {
233
- const candidates = new Set();
234
- if (layoutName) {
235
- candidates.add(layoutName);
236
- if (layoutName.includes('/')) {
237
- const parts = layoutName.split('/');
238
- const last = parts[parts.length - 1];
239
- if (last)
240
- candidates.add(last);
241
- }
242
- else {
243
- candidates.add(`crewx/${layoutName}`);
244
- }
245
- }
246
- candidates.add('default');
247
- for (const key of candidates) {
248
- const value = layoutsMap[key];
249
- if (typeof value === 'string' && value.trim().length > 0) {
250
- return { template: value };
251
- }
252
- if (value && typeof value === 'object' && typeof value.template === 'string' && value.template.trim().length > 0) {
253
- return { template: value.template, propsSchema: value.propsSchema };
254
- }
255
- }
256
- for (const value of Object.values(layoutsMap)) {
257
- if (typeof value === 'string' && value.trim().length > 0) {
258
- return { template: value };
259
- }
260
- const v = value;
261
- if (v && typeof v === 'object' && typeof v.template === 'string' && v.template.trim().length > 0) {
262
- return { template: v.template, propsSchema: v.propsSchema };
263
- }
264
- }
265
- return undefined;
266
- }
267
- }
268
- //# sourceMappingURL=loader.js.map