@almadar/core 2.14.3 → 3.0.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.
- package/dist/builders.d.ts +2 -2
- package/dist/builders.js +590 -64
- package/dist/builders.js.map +1 -1
- package/dist/{compose-behaviors-CQC8hsaL.d.ts → compose-behaviors-tUJ7EcaX.d.ts} +1 -1
- package/dist/domain-language/index.d.ts +1 -1
- package/dist/domain-language/index.js +33 -4
- package/dist/domain-language/index.js.map +1 -1
- package/dist/index.d.ts +3 -3
- package/dist/index.js +46 -5
- package/dist/index.js.map +1 -1
- package/dist/{schema-BFnZrBhm.d.ts → schema-COvHzxfu.d.ts} +9049 -2878
- package/dist/types/index.d.ts +2 -2
- package/dist/types/index.js +30 -4
- package/dist/types/index.js.map +1 -1
- package/package.json +1 -1
package/dist/builders.d.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import { T as TraitEventContract, E as EntityField, a as EntityPersistence, b as EntityRow, O as OrbitalDefinition, c as OrbitalSchema, d as Trait, e as Entity, P as Page } from './schema-
|
|
2
|
-
export { C as ComposeBehaviorsInput, a as ComposeBehaviorsResult, E as EventWiringEntry, L as LayoutStrategy, b as applyEventWiring, c as composeBehaviors, d as detectLayoutStrategy } from './compose-behaviors-
|
|
1
|
+
import { T as TraitEventContract, E as EntityField, a as EntityPersistence, b as EntityRow, O as OrbitalDefinition, c as OrbitalSchema, d as Trait, e as Entity, P as Page } from './schema-COvHzxfu.js';
|
|
2
|
+
export { C as ComposeBehaviorsInput, a as ComposeBehaviorsResult, E as EventWiringEntry, L as LayoutStrategy, b as applyEventWiring, c as composeBehaviors, d as detectLayoutStrategy } from './compose-behaviors-tUJ7EcaX.js';
|
|
3
3
|
import 'zod';
|
|
4
4
|
import '@almadar/patterns';
|
|
5
5
|
|
package/dist/builders.js
CHANGED
|
@@ -1,66 +1,181 @@
|
|
|
1
1
|
import { z } from 'zod';
|
|
2
2
|
|
|
3
|
-
// src/
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
3
|
+
// src/types/orbital.ts
|
|
4
|
+
var FieldTypeSchema = z.enum([
|
|
5
|
+
"string",
|
|
6
|
+
"number",
|
|
7
|
+
"boolean",
|
|
8
|
+
"date",
|
|
9
|
+
"timestamp",
|
|
10
|
+
"datetime",
|
|
11
|
+
"array",
|
|
12
|
+
"object",
|
|
13
|
+
"enum",
|
|
14
|
+
"relation"
|
|
15
|
+
]);
|
|
16
|
+
var RelationCardinalitySchema = z.enum([
|
|
17
|
+
"one",
|
|
18
|
+
"many",
|
|
19
|
+
"one-to-many",
|
|
20
|
+
"many-to-one",
|
|
21
|
+
"many-to-many"
|
|
22
|
+
]);
|
|
23
|
+
var RelationConfigSchema = z.object({
|
|
24
|
+
entity: z.string().min(1, "Target entity is required"),
|
|
25
|
+
field: z.string().optional(),
|
|
26
|
+
cardinality: RelationCardinalitySchema.optional(),
|
|
27
|
+
onDelete: z.enum(["cascade", "nullify", "restrict"]).optional(),
|
|
28
|
+
// Legacy compatibility fields
|
|
29
|
+
foreignKey: z.string().optional(),
|
|
30
|
+
target: z.string().optional(),
|
|
31
|
+
type: RelationCardinalitySchema.optional()
|
|
32
|
+
}).transform((data) => {
|
|
33
|
+
const normalized = {
|
|
34
|
+
entity: data.entity || data.target || "",
|
|
35
|
+
cardinality: data.cardinality || data.type,
|
|
36
|
+
field: data.field,
|
|
37
|
+
onDelete: data.onDelete
|
|
38
|
+
};
|
|
39
|
+
return normalized;
|
|
40
|
+
});
|
|
41
|
+
var FieldFormatSchema = z.enum([
|
|
42
|
+
"email",
|
|
43
|
+
"url",
|
|
44
|
+
"phone",
|
|
45
|
+
"date",
|
|
46
|
+
"datetime",
|
|
47
|
+
"uuid"
|
|
48
|
+
]);
|
|
49
|
+
var EntityFieldSchema = z.lazy(
|
|
50
|
+
() => z.object({
|
|
51
|
+
name: z.string().min(1, "Field name is required"),
|
|
52
|
+
type: FieldTypeSchema,
|
|
53
|
+
required: z.boolean().optional(),
|
|
54
|
+
default: z.unknown().optional(),
|
|
55
|
+
values: z.array(z.string()).optional(),
|
|
56
|
+
enum: z.array(z.string()).optional(),
|
|
57
|
+
format: FieldFormatSchema.optional(),
|
|
58
|
+
min: z.number().optional(),
|
|
59
|
+
max: z.number().optional(),
|
|
60
|
+
items: EntityFieldSchema.optional(),
|
|
61
|
+
relation: RelationConfigSchema.optional()
|
|
62
|
+
}).refine(
|
|
63
|
+
(field) => field.type !== "relation" || field.relation !== void 0,
|
|
64
|
+
{ message: 'Relation config is required when type is "relation"', path: ["relation"] }
|
|
65
|
+
)
|
|
66
|
+
);
|
|
67
|
+
var ENTITY_ROLES = [
|
|
68
|
+
"player",
|
|
69
|
+
"enemy",
|
|
70
|
+
"npc",
|
|
71
|
+
"item",
|
|
72
|
+
"tile",
|
|
73
|
+
"projectile",
|
|
74
|
+
"effect",
|
|
75
|
+
"ui",
|
|
76
|
+
"decoration",
|
|
77
|
+
"vehicle"
|
|
78
|
+
];
|
|
79
|
+
var EntityRoleSchema = z.enum(ENTITY_ROLES);
|
|
80
|
+
var VISUAL_STYLES = ["pixel", "vector", "hd", "1-bit", "isometric"];
|
|
81
|
+
var VisualStyleSchema = z.enum(VISUAL_STYLES);
|
|
82
|
+
var GAME_TYPES = [
|
|
83
|
+
"platformer",
|
|
84
|
+
"roguelike",
|
|
85
|
+
"top-down",
|
|
86
|
+
"puzzle",
|
|
87
|
+
"racing",
|
|
88
|
+
"card",
|
|
89
|
+
"board",
|
|
90
|
+
"shooter",
|
|
91
|
+
"rpg"
|
|
92
|
+
];
|
|
93
|
+
var GameTypeSchema = z.enum(GAME_TYPES);
|
|
94
|
+
var AnimationDefSchema = z.object({
|
|
95
|
+
frames: z.union([z.array(z.number()), z.array(z.string())]),
|
|
96
|
+
fps: z.number().positive(),
|
|
97
|
+
loop: z.boolean()
|
|
98
|
+
});
|
|
99
|
+
var SemanticAssetRefSchema = z.object({
|
|
100
|
+
role: EntityRoleSchema,
|
|
101
|
+
category: z.string().min(1),
|
|
102
|
+
animations: z.array(z.string()).optional(),
|
|
103
|
+
style: VisualStyleSchema.optional(),
|
|
104
|
+
variant: z.string().optional()
|
|
105
|
+
});
|
|
106
|
+
z.object({
|
|
107
|
+
basePath: z.string(),
|
|
108
|
+
path: z.string(),
|
|
109
|
+
tiles: z.array(z.number()).optional(),
|
|
110
|
+
tileSize: z.number().positive().optional(),
|
|
111
|
+
files: z.array(z.string()).optional(),
|
|
112
|
+
animations: z.record(AnimationDefSchema).optional()
|
|
113
|
+
});
|
|
114
|
+
var AssetMappingSchema = z.object({
|
|
115
|
+
path: z.string(),
|
|
116
|
+
tiles: z.array(z.number()).optional(),
|
|
117
|
+
tileSize: z.number().positive().optional(),
|
|
118
|
+
files: z.array(z.string()).optional(),
|
|
119
|
+
animations: z.record(AnimationDefSchema).optional()
|
|
120
|
+
});
|
|
121
|
+
z.object({
|
|
122
|
+
gameType: GameTypeSchema,
|
|
123
|
+
style: VisualStyleSchema,
|
|
124
|
+
basePath: z.string(),
|
|
125
|
+
mappings: z.record(AssetMappingSchema)
|
|
126
|
+
});
|
|
127
|
+
|
|
128
|
+
// src/types/entity.ts
|
|
129
|
+
var EntityPersistenceSchema = z.enum([
|
|
130
|
+
"persistent",
|
|
131
|
+
"runtime",
|
|
132
|
+
"singleton",
|
|
133
|
+
"instance",
|
|
134
|
+
"local"
|
|
135
|
+
]);
|
|
136
|
+
var OrbitalEntitySchema = z.object({
|
|
137
|
+
name: z.string().min(1, "Entity name is required"),
|
|
138
|
+
persistence: EntityPersistenceSchema.default("persistent"),
|
|
139
|
+
collection: z.string().optional(),
|
|
140
|
+
fields: z.array(EntityFieldSchema).min(1, "At least one field is required"),
|
|
141
|
+
instances: z.array(z.record(z.unknown())).optional(),
|
|
142
|
+
timestamps: z.boolean().optional(),
|
|
143
|
+
softDelete: z.boolean().optional(),
|
|
144
|
+
description: z.string().optional(),
|
|
145
|
+
visual_prompt: z.string().optional(),
|
|
146
|
+
assetRef: SemanticAssetRefSchema.optional()
|
|
147
|
+
});
|
|
148
|
+
var EntitySchema = OrbitalEntitySchema;
|
|
149
|
+
var ViewTypeSchema = z.enum([
|
|
150
|
+
"list",
|
|
151
|
+
"detail",
|
|
152
|
+
"create",
|
|
153
|
+
"edit",
|
|
154
|
+
"dashboard",
|
|
155
|
+
"custom"
|
|
156
|
+
]);
|
|
157
|
+
var PageTraitRefSchema = z.object({
|
|
158
|
+
ref: z.string().min(1, "Trait ref is required"),
|
|
159
|
+
linkedEntity: z.string().optional(),
|
|
160
|
+
config: z.record(z.unknown()).optional()
|
|
161
|
+
});
|
|
162
|
+
z.object({
|
|
163
|
+
name: z.string().min(1, "Page name is required"),
|
|
164
|
+
path: z.string().min(1, "Page path is required").startsWith("/", "Path must start with /"),
|
|
165
|
+
primaryEntity: z.string().min(1, "Primary entity is required"),
|
|
166
|
+
traits: z.array(PageTraitRefSchema).min(1, "Page must have at least one trait"),
|
|
167
|
+
title: z.string().optional()
|
|
168
|
+
}).strict();
|
|
169
|
+
var OrbitalPageSchema = z.object({
|
|
170
|
+
name: z.string().min(1, "Page name is required"),
|
|
171
|
+
path: z.string().min(1, "Page path is required").startsWith("/", "Path must start with /"),
|
|
172
|
+
viewType: ViewTypeSchema.optional(),
|
|
173
|
+
title: z.string().optional(),
|
|
174
|
+
primaryEntity: z.string().optional(),
|
|
175
|
+
traits: z.array(PageTraitRefSchema).optional(),
|
|
176
|
+
isInitial: z.boolean().optional()
|
|
177
|
+
}).strict();
|
|
178
|
+
var PageSchema = OrbitalPageSchema;
|
|
64
179
|
var UI_SLOTS = [
|
|
65
180
|
// App slots
|
|
66
181
|
"main",
|
|
@@ -244,6 +359,8 @@ var RequiredFieldSchema = z.object({
|
|
|
244
359
|
z.object({
|
|
245
360
|
ref: z.string().min(1),
|
|
246
361
|
linkedEntity: z.string().optional(),
|
|
362
|
+
name: z.string().optional(),
|
|
363
|
+
events: z.record(z.string(), z.string()).optional(),
|
|
247
364
|
config: z.record(z.record(z.unknown())).optional(),
|
|
248
365
|
appliesTo: z.array(z.string()).optional()
|
|
249
366
|
});
|
|
@@ -262,12 +379,14 @@ var TraitSchema = z.object({
|
|
|
262
379
|
listens: z.array(TraitEventListenerSchema).optional(),
|
|
263
380
|
ui: z.record(z.unknown()).optional()
|
|
264
381
|
});
|
|
265
|
-
z.union([
|
|
382
|
+
var TraitRefSchema = z.union([
|
|
266
383
|
z.string().min(1),
|
|
267
384
|
z.object({
|
|
268
385
|
ref: z.string().min(1),
|
|
269
386
|
config: z.record(z.unknown()).optional(),
|
|
270
|
-
linkedEntity: z.string().optional()
|
|
387
|
+
linkedEntity: z.string().optional(),
|
|
388
|
+
name: z.string().optional(),
|
|
389
|
+
events: z.record(z.string(), z.string()).optional()
|
|
271
390
|
}),
|
|
272
391
|
TraitSchema
|
|
273
392
|
// Allow inline trait definitions
|
|
@@ -275,6 +394,403 @@ z.union([
|
|
|
275
394
|
function isInlineTrait(traitRef) {
|
|
276
395
|
return typeof traitRef === "object" && "name" in traitRef && !("ref" in traitRef);
|
|
277
396
|
}
|
|
397
|
+
z.enum([
|
|
398
|
+
"healthcare",
|
|
399
|
+
"education",
|
|
400
|
+
"finance",
|
|
401
|
+
"ecommerce",
|
|
402
|
+
"real-estate",
|
|
403
|
+
"logistics",
|
|
404
|
+
"hospitality",
|
|
405
|
+
"hr-management",
|
|
406
|
+
"project-management",
|
|
407
|
+
"social",
|
|
408
|
+
"content-management",
|
|
409
|
+
"iot",
|
|
410
|
+
"analytics",
|
|
411
|
+
"game",
|
|
412
|
+
"custom"
|
|
413
|
+
]);
|
|
414
|
+
var AGENT_DOMAIN_CATEGORIES = [
|
|
415
|
+
"game",
|
|
416
|
+
"business",
|
|
417
|
+
"dashboard",
|
|
418
|
+
"form",
|
|
419
|
+
"content",
|
|
420
|
+
"social",
|
|
421
|
+
"ecommerce",
|
|
422
|
+
"workflow"
|
|
423
|
+
];
|
|
424
|
+
var AgentDomainCategorySchema = z.enum([...AGENT_DOMAIN_CATEGORIES]);
|
|
425
|
+
z.enum([
|
|
426
|
+
"platformer",
|
|
427
|
+
"shooter",
|
|
428
|
+
"puzzle",
|
|
429
|
+
"rpg",
|
|
430
|
+
"board",
|
|
431
|
+
"racing",
|
|
432
|
+
"fighting",
|
|
433
|
+
"tower-defense",
|
|
434
|
+
"endless-runner",
|
|
435
|
+
"simulation",
|
|
436
|
+
"arcade",
|
|
437
|
+
"adventure"
|
|
438
|
+
]);
|
|
439
|
+
z.enum(["domain", "system"]);
|
|
440
|
+
z.enum([
|
|
441
|
+
"pending",
|
|
442
|
+
"active",
|
|
443
|
+
"completed",
|
|
444
|
+
"cancelled",
|
|
445
|
+
"error",
|
|
446
|
+
"suspended",
|
|
447
|
+
"blocked",
|
|
448
|
+
"domain_workflow",
|
|
449
|
+
"domain_status",
|
|
450
|
+
"system_loading",
|
|
451
|
+
"system_error",
|
|
452
|
+
"system_idle",
|
|
453
|
+
"system_editing",
|
|
454
|
+
"system_confirming"
|
|
455
|
+
]);
|
|
456
|
+
z.enum([
|
|
457
|
+
"domain_action",
|
|
458
|
+
"domain_trigger",
|
|
459
|
+
"system_crud",
|
|
460
|
+
"system_navigation",
|
|
461
|
+
"system_form",
|
|
462
|
+
"system_ui"
|
|
463
|
+
]);
|
|
464
|
+
z.enum([
|
|
465
|
+
"domain_core",
|
|
466
|
+
"domain_supporting",
|
|
467
|
+
"domain_reference",
|
|
468
|
+
"system_user",
|
|
469
|
+
"system_config",
|
|
470
|
+
"system_audit"
|
|
471
|
+
]);
|
|
472
|
+
var DomainVocabularySchema = z.record(z.string(), z.string()).optional();
|
|
473
|
+
var UserPersonaSchema = z.object({
|
|
474
|
+
name: z.string().min(1),
|
|
475
|
+
role: z.string().optional(),
|
|
476
|
+
device: z.enum(["mobile", "tablet", "desktop"]).optional()
|
|
477
|
+
});
|
|
478
|
+
var DomainContextSchema = z.object({
|
|
479
|
+
request: z.string().min(1, "Original request is required"),
|
|
480
|
+
requestFragment: z.string().optional(),
|
|
481
|
+
category: AgentDomainCategorySchema,
|
|
482
|
+
subDomain: z.string().optional(),
|
|
483
|
+
personas: z.array(UserPersonaSchema).optional(),
|
|
484
|
+
vocabulary: DomainVocabularySchema.optional()
|
|
485
|
+
});
|
|
486
|
+
var UXHintsSchema = z.object({
|
|
487
|
+
flowPattern: z.string().optional(),
|
|
488
|
+
listPattern: z.string().optional(),
|
|
489
|
+
formPattern: z.string().optional(),
|
|
490
|
+
detailPattern: z.string().optional(),
|
|
491
|
+
relatedLinks: z.array(z.lazy(() => RelatedLinkSchema)).optional()
|
|
492
|
+
});
|
|
493
|
+
var RelatedLinkSchema = z.object({
|
|
494
|
+
relation: z.string().min(1),
|
|
495
|
+
label: z.string().min(1),
|
|
496
|
+
targetView: z.enum(["list", "detail"]).optional()
|
|
497
|
+
});
|
|
498
|
+
var SuggestedGuardSchema = z.object({
|
|
499
|
+
id: z.string().min(1),
|
|
500
|
+
description: z.string().min(1),
|
|
501
|
+
appliesTo: z.array(z.string().min(1))
|
|
502
|
+
});
|
|
503
|
+
var DesignPreferencesSchema = z.object({
|
|
504
|
+
style: z.enum(["minimal", "modern", "playful", "data-driven", "immersive"]).optional(),
|
|
505
|
+
primaryColor: z.string().regex(/^#[0-9A-Fa-f]{6}$/, "Must be valid hex color").optional(),
|
|
506
|
+
device: z.enum(["mobile", "tablet", "desktop", "all"]).optional(),
|
|
507
|
+
darkMode: z.boolean().optional(),
|
|
508
|
+
uxHints: UXHintsSchema.optional()
|
|
509
|
+
});
|
|
510
|
+
var ThemeTokensSchema = z.object({
|
|
511
|
+
colors: z.record(z.string(), z.string()).optional(),
|
|
512
|
+
radii: z.record(z.string(), z.string()).optional(),
|
|
513
|
+
spacing: z.record(z.string(), z.string()).optional(),
|
|
514
|
+
typography: z.record(z.string(), z.string()).optional(),
|
|
515
|
+
shadows: z.record(z.string(), z.string()).optional()
|
|
516
|
+
});
|
|
517
|
+
var ThemeVariantSchema = z.object({
|
|
518
|
+
colors: z.record(z.string(), z.string()).optional(),
|
|
519
|
+
radii: z.record(z.string(), z.string()).optional(),
|
|
520
|
+
spacing: z.record(z.string(), z.string()).optional(),
|
|
521
|
+
typography: z.record(z.string(), z.string()).optional(),
|
|
522
|
+
shadows: z.record(z.string(), z.string()).optional()
|
|
523
|
+
});
|
|
524
|
+
var ThemeDefinitionSchema = z.object({
|
|
525
|
+
name: z.string().min(1, "Theme name is required"),
|
|
526
|
+
tokens: ThemeTokensSchema,
|
|
527
|
+
variants: z.record(z.string(), ThemeVariantSchema).optional()
|
|
528
|
+
});
|
|
529
|
+
var ThemeRefStringSchema = z.string().regex(
|
|
530
|
+
/^[A-Z][a-zA-Z0-9]*\.theme$/,
|
|
531
|
+
'Theme reference must be in format "Alias.theme" (e.g., "Ocean.theme")'
|
|
532
|
+
);
|
|
533
|
+
var ThemeRefSchema = z.union([
|
|
534
|
+
ThemeDefinitionSchema,
|
|
535
|
+
ThemeRefStringSchema
|
|
536
|
+
]);
|
|
537
|
+
z.record(z.string(), z.record(z.string(), z.string())).optional();
|
|
538
|
+
var ALLOWED_CUSTOM_COMPONENTS = [
|
|
539
|
+
"div",
|
|
540
|
+
"span",
|
|
541
|
+
"button",
|
|
542
|
+
"a",
|
|
543
|
+
"p",
|
|
544
|
+
"h1",
|
|
545
|
+
"h2",
|
|
546
|
+
"h3",
|
|
547
|
+
"h4",
|
|
548
|
+
"h5",
|
|
549
|
+
"h6",
|
|
550
|
+
"header",
|
|
551
|
+
"footer",
|
|
552
|
+
"section",
|
|
553
|
+
"article",
|
|
554
|
+
"nav",
|
|
555
|
+
"main",
|
|
556
|
+
"aside",
|
|
557
|
+
"ul",
|
|
558
|
+
"ol",
|
|
559
|
+
"li",
|
|
560
|
+
"img",
|
|
561
|
+
"label",
|
|
562
|
+
"input",
|
|
563
|
+
"form"
|
|
564
|
+
];
|
|
565
|
+
var CustomPatternDefinitionSchema = z.object({
|
|
566
|
+
type: z.literal("custom"),
|
|
567
|
+
component: z.enum(ALLOWED_CUSTOM_COMPONENTS),
|
|
568
|
+
className: z.string(),
|
|
569
|
+
slots: z.array(z.string()).optional(),
|
|
570
|
+
props: z.array(z.string()).optional()
|
|
571
|
+
});
|
|
572
|
+
z.record(z.string(), CustomPatternDefinitionSchema).optional();
|
|
573
|
+
var SERVICE_TYPES = ["rest", "socket", "mcp"];
|
|
574
|
+
z.enum(SERVICE_TYPES);
|
|
575
|
+
var RestAuthConfigSchema = z.object({
|
|
576
|
+
type: z.enum(["api-key", "bearer", "basic", "oauth2"]),
|
|
577
|
+
keyName: z.string().optional(),
|
|
578
|
+
location: z.enum(["query", "header"]).optional(),
|
|
579
|
+
secretEnv: z.string().optional()
|
|
580
|
+
});
|
|
581
|
+
var RestServiceDefSchema = z.object({
|
|
582
|
+
name: z.string().min(1, "Service name is required"),
|
|
583
|
+
type: z.literal("rest"),
|
|
584
|
+
description: z.string().optional(),
|
|
585
|
+
baseUrl: z.string().url("Base URL must be a valid URL"),
|
|
586
|
+
headers: z.record(z.string()).optional(),
|
|
587
|
+
auth: RestAuthConfigSchema.optional(),
|
|
588
|
+
timeout: z.number().positive().optional()
|
|
589
|
+
});
|
|
590
|
+
var SocketEventsSchema = z.object({
|
|
591
|
+
inbound: z.array(z.string()),
|
|
592
|
+
outbound: z.array(z.string())
|
|
593
|
+
});
|
|
594
|
+
var SocketServiceDefSchema = z.object({
|
|
595
|
+
name: z.string().min(1, "Service name is required"),
|
|
596
|
+
type: z.literal("socket"),
|
|
597
|
+
description: z.string().optional(),
|
|
598
|
+
url: z.string().url("WebSocket URL must be valid"),
|
|
599
|
+
events: SocketEventsSchema,
|
|
600
|
+
reconnect: z.object({
|
|
601
|
+
enabled: z.boolean(),
|
|
602
|
+
maxAttempts: z.number().positive().optional(),
|
|
603
|
+
delayMs: z.number().positive().optional()
|
|
604
|
+
}).optional()
|
|
605
|
+
});
|
|
606
|
+
var McpServiceDefSchema = z.object({
|
|
607
|
+
name: z.string().min(1, "Service name is required"),
|
|
608
|
+
type: z.literal("mcp"),
|
|
609
|
+
description: z.string().optional(),
|
|
610
|
+
serverPath: z.string().min(1, "Server path is required"),
|
|
611
|
+
capabilities: z.array(z.string()).min(1, "At least one capability is required"),
|
|
612
|
+
env: z.record(z.string()).optional()
|
|
613
|
+
});
|
|
614
|
+
var ServiceDefinitionSchema = z.discriminatedUnion("type", [
|
|
615
|
+
RestServiceDefSchema,
|
|
616
|
+
SocketServiceDefSchema,
|
|
617
|
+
McpServiceDefSchema
|
|
618
|
+
]);
|
|
619
|
+
var ServiceRefStringSchema = z.string().regex(
|
|
620
|
+
/^[A-Z][a-zA-Z0-9]*\.services\.[a-zA-Z][a-zA-Z0-9]*$/,
|
|
621
|
+
'Service reference must be in format "Alias.services.ServiceName" (e.g., "Weather.services.openweather")'
|
|
622
|
+
);
|
|
623
|
+
var ServiceRefSchema = z.union([
|
|
624
|
+
ServiceDefinitionSchema,
|
|
625
|
+
ServiceRefStringSchema
|
|
626
|
+
]);
|
|
627
|
+
|
|
628
|
+
// src/types/orbital.ts
|
|
629
|
+
var UseDeclarationSchema = z.object({
|
|
630
|
+
from: z.string().min(1, "Import source is required"),
|
|
631
|
+
as: z.string().min(1, "Alias is required").regex(
|
|
632
|
+
/^[A-Z][a-zA-Z0-9]*$/,
|
|
633
|
+
'Alias must be PascalCase (e.g., "Health", "GameCore")'
|
|
634
|
+
)
|
|
635
|
+
});
|
|
636
|
+
function isEntityReference(entity) {
|
|
637
|
+
return typeof entity === "string";
|
|
638
|
+
}
|
|
639
|
+
function isEntityCall(entity) {
|
|
640
|
+
return typeof entity === "object" && entity !== null && "extends" in entity;
|
|
641
|
+
}
|
|
642
|
+
var EntityRefStringSchema = z.string().regex(
|
|
643
|
+
/^[A-Z][a-zA-Z0-9]*\.entity$/,
|
|
644
|
+
'Entity reference must be in format "Alias.entity" (e.g., "Goblin.entity")'
|
|
645
|
+
);
|
|
646
|
+
var EntityCallSchema = z.object({
|
|
647
|
+
extends: z.string().regex(
|
|
648
|
+
/^[A-Z][a-zA-Z0-9]*\.entity$/,
|
|
649
|
+
'EntityCall "extends" must be in format "Alias.entity"'
|
|
650
|
+
),
|
|
651
|
+
name: z.string().optional(),
|
|
652
|
+
fields: z.array(EntityFieldSchema).optional(),
|
|
653
|
+
persistence: EntityPersistenceSchema.optional(),
|
|
654
|
+
collection: z.string().optional()
|
|
655
|
+
});
|
|
656
|
+
var EntityRefSchema = z.union([
|
|
657
|
+
EntitySchema,
|
|
658
|
+
EntityRefStringSchema,
|
|
659
|
+
EntityCallSchema
|
|
660
|
+
]);
|
|
661
|
+
var PageRefStringSchema = z.string().regex(
|
|
662
|
+
/^[A-Z][a-zA-Z0-9]*\.pages\.[A-Z][a-zA-Z0-9]*$/,
|
|
663
|
+
'Page reference must be in format "Alias.pages.PageName" (e.g., "User.pages.Profile")'
|
|
664
|
+
);
|
|
665
|
+
var PageRefObjectSchema = z.object({
|
|
666
|
+
ref: PageRefStringSchema,
|
|
667
|
+
path: z.string().startsWith("/").optional(),
|
|
668
|
+
linkedEntity: z.string().optional(),
|
|
669
|
+
traits: z.array(TraitRefSchema).optional()
|
|
670
|
+
});
|
|
671
|
+
var PageRefSchema = z.union([
|
|
672
|
+
PageSchema,
|
|
673
|
+
PageRefStringSchema,
|
|
674
|
+
PageRefObjectSchema
|
|
675
|
+
]);
|
|
676
|
+
z.string().regex(
|
|
677
|
+
/^([A-Z][a-zA-Z0-9]*\.traits\.)?[A-Z][a-zA-Z0-9]*$/,
|
|
678
|
+
'Trait reference must be "TraitName" or "Alias.traits.TraitName"'
|
|
679
|
+
);
|
|
680
|
+
function parseEntityRef(ref) {
|
|
681
|
+
const match = ref.match(/^([A-Z][a-zA-Z0-9]*)\.entity$/);
|
|
682
|
+
if (!match) return null;
|
|
683
|
+
return { alias: match[1] };
|
|
684
|
+
}
|
|
685
|
+
z.object({
|
|
686
|
+
event: z.string().min(1),
|
|
687
|
+
triggers: z.string().min(1),
|
|
688
|
+
guard: z.string().optional()
|
|
689
|
+
});
|
|
690
|
+
var EventSourceSchema = z.object({
|
|
691
|
+
trait: z.string().min(1),
|
|
692
|
+
transition: z.string().optional(),
|
|
693
|
+
tick: z.string().optional()
|
|
694
|
+
});
|
|
695
|
+
var ComputedEventContractSchema = z.object({
|
|
696
|
+
event: z.string().min(1),
|
|
697
|
+
originalEvent: z.string().min(1),
|
|
698
|
+
source: EventSourceSchema,
|
|
699
|
+
description: z.string().optional(),
|
|
700
|
+
payload: z.array(EventPayloadFieldSchema).optional()
|
|
701
|
+
});
|
|
702
|
+
var ComputedEventListenerSchema = z.object({
|
|
703
|
+
event: z.string().min(1),
|
|
704
|
+
source: EventSourceSchema,
|
|
705
|
+
triggers: z.string().min(1),
|
|
706
|
+
guard: ExpressionSchema.optional(),
|
|
707
|
+
payloadMapping: z.record(z.string()).optional()
|
|
708
|
+
});
|
|
709
|
+
z.object({
|
|
710
|
+
name: z.string().min(1, "Orbital name is required"),
|
|
711
|
+
description: z.string().optional(),
|
|
712
|
+
visual_prompt: z.string().optional(),
|
|
713
|
+
// Import system
|
|
714
|
+
uses: z.array(UseDeclarationSchema).optional(),
|
|
715
|
+
// Theme & Services
|
|
716
|
+
theme: ThemeRefSchema.optional(),
|
|
717
|
+
services: z.array(ServiceRefSchema).optional(),
|
|
718
|
+
// Components (inline or reference)
|
|
719
|
+
entity: EntityRefSchema,
|
|
720
|
+
traits: z.array(TraitRefSchema),
|
|
721
|
+
pages: z.array(PageRefSchema),
|
|
722
|
+
// Event interface (trait-centric model) - computed by resolver
|
|
723
|
+
emits: z.array(ComputedEventContractSchema).optional(),
|
|
724
|
+
listens: z.array(ComputedEventListenerSchema).optional(),
|
|
725
|
+
// Filter for exposed events (trait-centric model)
|
|
726
|
+
exposes: z.array(z.string()).optional(),
|
|
727
|
+
// Context fields - persisted throughout orbital lifecycle
|
|
728
|
+
domainContext: DomainContextSchema.optional(),
|
|
729
|
+
design: DesignPreferencesSchema.optional(),
|
|
730
|
+
suggestedGuards: z.array(SuggestedGuardSchema).optional()
|
|
731
|
+
});
|
|
732
|
+
|
|
733
|
+
// src/builders/layout-strategy.ts
|
|
734
|
+
function hasSequentialChain(wiring) {
|
|
735
|
+
if (wiring.length < 2) {
|
|
736
|
+
return false;
|
|
737
|
+
}
|
|
738
|
+
const adjacency = /* @__PURE__ */ new Map();
|
|
739
|
+
const allTargets = /* @__PURE__ */ new Set();
|
|
740
|
+
for (const entry of wiring) {
|
|
741
|
+
let targets = adjacency.get(entry.from);
|
|
742
|
+
if (!targets) {
|
|
743
|
+
targets = /* @__PURE__ */ new Set();
|
|
744
|
+
adjacency.set(entry.from, targets);
|
|
745
|
+
}
|
|
746
|
+
targets.add(entry.to);
|
|
747
|
+
allTargets.add(entry.to);
|
|
748
|
+
}
|
|
749
|
+
const roots = [];
|
|
750
|
+
for (const from of adjacency.keys()) {
|
|
751
|
+
if (!allTargets.has(from)) {
|
|
752
|
+
roots.push(from);
|
|
753
|
+
}
|
|
754
|
+
}
|
|
755
|
+
const starts = roots.length > 0 ? roots : [...adjacency.keys()];
|
|
756
|
+
for (const start of starts) {
|
|
757
|
+
let current = start;
|
|
758
|
+
let length = 1;
|
|
759
|
+
const visited = /* @__PURE__ */ new Set([current]);
|
|
760
|
+
while (true) {
|
|
761
|
+
const nexts = adjacency.get(current);
|
|
762
|
+
if (!nexts || nexts.size === 0) break;
|
|
763
|
+
let advanced = false;
|
|
764
|
+
for (const next of nexts) {
|
|
765
|
+
if (!visited.has(next)) {
|
|
766
|
+
visited.add(next);
|
|
767
|
+
current = next;
|
|
768
|
+
length++;
|
|
769
|
+
advanced = true;
|
|
770
|
+
break;
|
|
771
|
+
}
|
|
772
|
+
}
|
|
773
|
+
if (!advanced) break;
|
|
774
|
+
}
|
|
775
|
+
if (length >= 3) {
|
|
776
|
+
return true;
|
|
777
|
+
}
|
|
778
|
+
}
|
|
779
|
+
return false;
|
|
780
|
+
}
|
|
781
|
+
function detectLayoutStrategy(orbitals, eventWiring) {
|
|
782
|
+
if (eventWiring && eventWiring.length > 0 && hasSequentialChain(eventWiring)) {
|
|
783
|
+
return "wizard-flow";
|
|
784
|
+
}
|
|
785
|
+
const count = orbitals.length;
|
|
786
|
+
if (count <= 1) {
|
|
787
|
+
return "single";
|
|
788
|
+
}
|
|
789
|
+
if (count <= 4) {
|
|
790
|
+
return "tabs";
|
|
791
|
+
}
|
|
792
|
+
return "sidebar";
|
|
793
|
+
}
|
|
278
794
|
|
|
279
795
|
// src/builders/event-wiring.ts
|
|
280
796
|
function findInlineTrait(orbitals, name) {
|
|
@@ -420,6 +936,16 @@ function ensureIdField(fields) {
|
|
|
420
936
|
function plural(name) {
|
|
421
937
|
return name + "s";
|
|
422
938
|
}
|
|
939
|
+
function resolveEntityNameForBuilder(ref) {
|
|
940
|
+
if (isEntityReference(ref)) {
|
|
941
|
+
return parseEntityRef(ref)?.alias ?? ref;
|
|
942
|
+
}
|
|
943
|
+
if (isEntityCall(ref)) {
|
|
944
|
+
if (ref.name) return ref.name;
|
|
945
|
+
return parseEntityRef(ref.extends)?.alias ?? ref.extends;
|
|
946
|
+
}
|
|
947
|
+
return ref.name;
|
|
948
|
+
}
|
|
423
949
|
function makeEntity(opts) {
|
|
424
950
|
const fields = ensureIdField(opts.fields);
|
|
425
951
|
const persistence = opts.persistence ?? "runtime";
|
|
@@ -552,7 +1078,7 @@ function pipe(orbitals, events, appName) {
|
|
|
552
1078
|
}
|
|
553
1079
|
}
|
|
554
1080
|
const pages = cloned.map((o, i) => {
|
|
555
|
-
const entityName =
|
|
1081
|
+
const entityName = resolveEntityNameForBuilder(o.entity);
|
|
556
1082
|
const traitNames = o.traits.map((t) => t.name);
|
|
557
1083
|
return {
|
|
558
1084
|
name: `${entityName}Page`,
|