@powerhousedao/vetra 4.1.0-dev.81 → 4.1.0-dev.83

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 (60) hide show
  1. package/dist/document-models/app-module/src/reducers/base-operations.d.ts.map +1 -1
  2. package/dist/document-models/app-module/src/reducers/base-operations.js +5 -1
  3. package/dist/document-models/app-module/src/tests/base-operations.test.js +157 -30
  4. package/dist/document-models/app-module/src/tests/dnd-operations.test.js +38 -7
  5. package/dist/document-models/app-module/src/tests/document-model.test.js +80 -8
  6. package/dist/document-models/document-editor/src/reducers/base-operations.d.ts.map +1 -1
  7. package/dist/document-models/document-editor/src/reducers/base-operations.js +10 -1
  8. package/dist/document-models/document-editor/src/tests/base-operations.test.js +137 -23
  9. package/dist/document-models/document-editor/src/tests/document-model.test.js +91 -8
  10. package/dist/document-models/processor-module/src/reducers/base-operations.d.ts.map +1 -1
  11. package/dist/document-models/processor-module/src/reducers/base-operations.js +15 -2
  12. package/dist/document-models/processor-module/src/tests/base-operations.test.js +153 -33
  13. package/dist/document-models/processor-module/src/tests/document-model.test.js +96 -8
  14. package/dist/document-models/subgraph-module/src/reducers/base-operations.d.ts.map +1 -1
  15. package/dist/document-models/subgraph-module/src/reducers/base-operations.js +5 -1
  16. package/dist/document-models/subgraph-module/src/tests/base-operations.test.js +33 -12
  17. package/dist/document-models/subgraph-module/src/tests/document-model.test.js +25 -8
  18. package/dist/document-models/vetra-package/src/reducers/base-operations.d.ts.map +1 -1
  19. package/dist/document-models/vetra-package/src/reducers/base-operations.js +5 -0
  20. package/dist/document-models/vetra-package/src/tests/base-operations.test.js +171 -75
  21. package/dist/document-models/vetra-package/src/tests/document-model.test.js +101 -8
  22. package/dist/editors/app-editor/components/AppEditorForm.d.ts.map +1 -1
  23. package/dist/editors/app-editor/components/AppEditorForm.js +2 -2
  24. package/dist/editors/app-editor/editor.test.d.ts +2 -0
  25. package/dist/editors/app-editor/editor.test.d.ts.map +1 -0
  26. package/dist/editors/app-editor/editor.test.js +422 -0
  27. package/dist/editors/document-editor/components/DocumentEditorForm.d.ts.map +1 -1
  28. package/dist/editors/document-editor/components/DocumentEditorForm.js +1 -1
  29. package/dist/editors/document-editor/editor.test.d.ts +2 -0
  30. package/dist/editors/document-editor/editor.test.d.ts.map +1 -0
  31. package/dist/editors/document-editor/editor.test.js +374 -0
  32. package/dist/editors/processor-editor/components/ProcessorEditorForm.d.ts.map +1 -1
  33. package/dist/editors/processor-editor/components/ProcessorEditorForm.js +1 -1
  34. package/dist/editors/processor-editor/editor.test.d.ts +2 -0
  35. package/dist/editors/processor-editor/editor.test.d.ts.map +1 -0
  36. package/dist/editors/processor-editor/editor.test.js +459 -0
  37. package/dist/editors/subgraph-editor/components/SubgraphEditorForm.d.ts.map +1 -1
  38. package/dist/editors/subgraph-editor/components/SubgraphEditorForm.js +3 -3
  39. package/dist/editors/subgraph-editor/editor.test.d.ts +2 -0
  40. package/dist/editors/subgraph-editor/editor.test.d.ts.map +1 -0
  41. package/dist/editors/subgraph-editor/editor.test.js +201 -0
  42. package/dist/editors/vetra-package/components/MetaForm.d.ts.map +1 -1
  43. package/dist/editors/vetra-package/components/MetaForm.js +3 -3
  44. package/dist/editors/vetra-package/editor.test.d.ts +2 -0
  45. package/dist/editors/vetra-package/editor.test.d.ts.map +1 -0
  46. package/dist/editors/vetra-package/editor.test.js +330 -0
  47. package/dist/processors/codegen/__tests__/codegen-processor-e2e.test.d.ts +2 -0
  48. package/dist/processors/codegen/__tests__/codegen-processor-e2e.test.d.ts.map +1 -0
  49. package/dist/processors/codegen/__tests__/codegen-processor-e2e.test.js +615 -0
  50. package/dist/processors/codegen/__tests__/factory.test.d.ts +2 -0
  51. package/dist/processors/codegen/__tests__/factory.test.d.ts.map +1 -0
  52. package/dist/processors/codegen/__tests__/factory.test.js +190 -0
  53. package/dist/setupTests.d.ts +2 -0
  54. package/dist/setupTests.d.ts.map +1 -0
  55. package/dist/setupTests.js +1 -0
  56. package/dist/style.css +9 -0
  57. package/dist/tsconfig.tsbuildinfo +1 -1
  58. package/dist/vitest.config.d.ts.map +1 -1
  59. package/dist/vitest.config.js +9 -0
  60. package/package.json +19 -14
@@ -0,0 +1,615 @@
1
+ import { beforeEach, describe, expect, it, vi } from "vitest";
2
+ import { CodegenProcessor } from "../index.js";
3
+ // Mock ONLY the external codegen library boundary
4
+ vi.mock("@powerhousedao/codegen", () => ({
5
+ generateEditor: vi.fn(),
6
+ generateFromDocument: vi.fn(),
7
+ generateSubgraphFromDocumentModel: vi.fn(),
8
+ generateManifest: vi.fn(),
9
+ validateDocumentModelState: vi.fn(() => ({ isValid: true })),
10
+ generateDriveEditor: vi.fn(),
11
+ generateSubgraph: vi.fn(),
12
+ generateProcessor: vi.fn(),
13
+ }));
14
+ // Mock config functions
15
+ vi.mock("@powerhousedao/config/node", () => ({
16
+ getConfig: vi.fn(() => "/test/config/path"),
17
+ }));
18
+ // Mock kebabCase
19
+ vi.mock("change-case", () => ({
20
+ kebabCase: vi.fn((str) => str.toLowerCase().replace(/\s+/g, "-")),
21
+ }));
22
+ // Mock logger
23
+ vi.mock("../logger.js", () => ({
24
+ logger: {
25
+ debug: vi.fn(),
26
+ info: vi.fn(),
27
+ warn: vi.fn(),
28
+ error: vi.fn(),
29
+ },
30
+ }));
31
+ describe("CodegenProcessor E2E Tests", () => {
32
+ let processor;
33
+ let mockConfig;
34
+ beforeEach(async () => {
35
+ vi.clearAllMocks();
36
+ // Use fake timers to control setTimeout
37
+ vi.useFakeTimers();
38
+ mockConfig = {
39
+ PH_CONFIG: "/test/config/path",
40
+ // Use the actual working directory for consistency
41
+ CURRENT_WORKING_DIR: process.cwd(),
42
+ };
43
+ // Create a REAL processor instance (not mocked)
44
+ processor = new CodegenProcessor();
45
+ // Reset all codegen function mocks to resolve successfully
46
+ const codegen = await import("@powerhousedao/codegen");
47
+ vi.mocked(codegen.generateEditor).mockResolvedValue(undefined);
48
+ vi.mocked(codegen.generateFromDocument).mockResolvedValue(undefined);
49
+ vi.mocked(codegen.generateSubgraphFromDocumentModel).mockResolvedValue(undefined);
50
+ vi.mocked(codegen.generateManifest).mockResolvedValue(undefined);
51
+ vi.mocked(codegen.generateDriveEditor).mockResolvedValue(undefined);
52
+ vi.mocked(codegen.generateSubgraph).mockResolvedValue(undefined);
53
+ vi.mocked(codegen.generateProcessor).mockResolvedValue(undefined);
54
+ vi.mocked(codegen.validateDocumentModelState).mockReturnValue({
55
+ isValid: true,
56
+ });
57
+ });
58
+ afterEach(() => {
59
+ // Restore timers
60
+ vi.useRealTimers();
61
+ });
62
+ describe("Document Editor E2E", () => {
63
+ it("should process valid document-editor strand and call generateEditor with correct arguments", async () => {
64
+ const { generateEditor, generateManifest } = await import("@powerhousedao/codegen");
65
+ const validState = {
66
+ name: "Test Editor",
67
+ documentTypes: [
68
+ { id: "dt-1", documentType: "powerhouse/document-model" },
69
+ { id: "dt-2", documentType: "powerhouse/budget-statement" },
70
+ ],
71
+ status: "CONFIRMED",
72
+ };
73
+ const strand = {
74
+ documentId: "test-doc-1",
75
+ documentType: "powerhouse/document-editor",
76
+ state: validState,
77
+ };
78
+ await processor.onStrands([strand]);
79
+ // Advance timers to trigger debounced generation
80
+ await vi.runAllTimersAsync();
81
+ expect(generateEditor).toHaveBeenCalledWith("Test Editor", ["powerhouse/document-model", "powerhouse/budget-statement"], mockConfig.PH_CONFIG, "test-editor");
82
+ expect(generateManifest).toHaveBeenCalledWith({
83
+ editors: [
84
+ {
85
+ id: "test-editor",
86
+ name: "Test Editor",
87
+ documentTypes: [
88
+ "powerhouse/document-model",
89
+ "powerhouse/budget-statement",
90
+ ],
91
+ },
92
+ ],
93
+ }, mockConfig.CURRENT_WORKING_DIR);
94
+ });
95
+ it("should not call codegen functions for invalid document-editor strand (missing name)", async () => {
96
+ const { generateEditor, generateManifest } = await import("@powerhousedao/codegen");
97
+ const invalidState = {
98
+ name: "",
99
+ documentTypes: [
100
+ { id: "dt-1", documentType: "powerhouse/document-model" },
101
+ ],
102
+ status: "CONFIRMED",
103
+ };
104
+ const strand = {
105
+ documentId: "test-doc-1",
106
+ documentType: "powerhouse/document-editor",
107
+ state: invalidState,
108
+ };
109
+ await processor.onStrands([strand]);
110
+ await vi.runAllTimersAsync();
111
+ expect(generateEditor).not.toHaveBeenCalled();
112
+ expect(generateManifest).not.toHaveBeenCalled();
113
+ });
114
+ it("should not call codegen functions for invalid document-editor strand (DRAFT status)", async () => {
115
+ const { generateEditor, generateManifest } = await import("@powerhousedao/codegen");
116
+ const invalidState = {
117
+ name: "Test Editor",
118
+ documentTypes: [
119
+ { id: "dt-1", documentType: "powerhouse/document-model" },
120
+ ],
121
+ status: "DRAFT",
122
+ };
123
+ const strand = {
124
+ documentId: "test-doc-1",
125
+ documentType: "powerhouse/document-editor",
126
+ state: invalidState,
127
+ };
128
+ await processor.onStrands([strand]);
129
+ await vi.runAllTimersAsync();
130
+ expect(generateEditor).not.toHaveBeenCalled();
131
+ expect(generateManifest).not.toHaveBeenCalled();
132
+ });
133
+ it("should not call codegen functions for invalid document-editor strand (empty documentTypes)", async () => {
134
+ const { generateEditor, generateManifest } = await import("@powerhousedao/codegen");
135
+ const invalidState = {
136
+ name: "Test Editor",
137
+ documentTypes: [],
138
+ status: "CONFIRMED",
139
+ };
140
+ const strand = {
141
+ documentId: "test-doc-1",
142
+ documentType: "powerhouse/document-editor",
143
+ state: invalidState,
144
+ };
145
+ await processor.onStrands([strand]);
146
+ await vi.runAllTimersAsync();
147
+ expect(generateEditor).not.toHaveBeenCalled();
148
+ expect(generateManifest).not.toHaveBeenCalled();
149
+ });
150
+ });
151
+ describe("Document Model E2E", () => {
152
+ it("should process valid document-model strand and call all three codegen functions", async () => {
153
+ const { generateFromDocument, generateSubgraphFromDocumentModel, generateManifest, } = await import("@powerhousedao/codegen");
154
+ const validState = {
155
+ id: "test-model-id",
156
+ name: "Test Model",
157
+ };
158
+ const strand = {
159
+ documentId: "test-doc-1",
160
+ documentType: "powerhouse/document-model",
161
+ state: validState,
162
+ };
163
+ await processor.onStrands([strand]);
164
+ await vi.runAllTimersAsync();
165
+ expect(generateFromDocument).toHaveBeenCalledWith(validState, mockConfig.PH_CONFIG, { verbose: false });
166
+ expect(generateSubgraphFromDocumentModel).toHaveBeenCalledWith("Test Model", validState, mockConfig.PH_CONFIG, { verbose: false });
167
+ expect(generateManifest).toHaveBeenCalledWith({
168
+ documentModels: [
169
+ {
170
+ id: "test-model-id",
171
+ name: "Test Model",
172
+ },
173
+ ],
174
+ }, mockConfig.CURRENT_WORKING_DIR);
175
+ });
176
+ it("should not call codegen functions when validateDocumentModelState returns invalid", async () => {
177
+ const { validateDocumentModelState, generateFromDocument, generateSubgraphFromDocumentModel, generateManifest, } = await import("@powerhousedao/codegen");
178
+ vi.mocked(validateDocumentModelState).mockReturnValue({
179
+ isValid: false,
180
+ errors: ["Name is required"],
181
+ });
182
+ const invalidState = {
183
+ id: "test-model-id",
184
+ };
185
+ const strand = {
186
+ documentId: "test-doc-1",
187
+ documentType: "powerhouse/document-model",
188
+ state: invalidState,
189
+ };
190
+ await processor.onStrands([strand]);
191
+ await vi.runAllTimersAsync();
192
+ expect(generateFromDocument).not.toHaveBeenCalled();
193
+ expect(generateSubgraphFromDocumentModel).not.toHaveBeenCalled();
194
+ expect(generateManifest).not.toHaveBeenCalled();
195
+ });
196
+ it("should not call subsequent codegen functions when generateFromDocument fails", async () => {
197
+ const { generateFromDocument, generateSubgraphFromDocumentModel, generateManifest, } = await import("@powerhousedao/codegen");
198
+ vi.mocked(generateFromDocument).mockRejectedValueOnce(new Error("Document generation failed"));
199
+ const validState = {
200
+ id: "test-model-id",
201
+ name: "Test Model",
202
+ };
203
+ const strand = {
204
+ documentId: "test-doc-1",
205
+ documentType: "powerhouse/document-model",
206
+ state: validState,
207
+ };
208
+ await processor.onStrands([strand]);
209
+ await vi.runAllTimersAsync();
210
+ expect(generateFromDocument).toHaveBeenCalled();
211
+ // Subsequent calls should not happen
212
+ expect(generateSubgraphFromDocumentModel).not.toHaveBeenCalled();
213
+ expect(generateManifest).not.toHaveBeenCalled();
214
+ });
215
+ });
216
+ describe("Processor E2E", () => {
217
+ it("should process valid analytics processor strand and call generateProcessor", async () => {
218
+ const { generateProcessor } = await import("@powerhousedao/codegen");
219
+ const validState = {
220
+ name: "Test Processor",
221
+ type: "analytics",
222
+ documentTypes: [
223
+ { id: "dt-1", documentType: "powerhouse/document-model" },
224
+ { id: "dt-2", documentType: "powerhouse/budget-statement" },
225
+ ],
226
+ status: "CONFIRMED",
227
+ };
228
+ const strand = {
229
+ documentId: "test-doc-1",
230
+ documentType: "powerhouse/processor",
231
+ state: validState,
232
+ };
233
+ await processor.onStrands([strand]);
234
+ await vi.runAllTimersAsync();
235
+ expect(generateProcessor).toHaveBeenCalledWith("Test Processor", "analytics", ["powerhouse/document-model", "powerhouse/budget-statement"], mockConfig.PH_CONFIG);
236
+ });
237
+ it("should map relational type to relationalDb when processing processor strand", async () => {
238
+ const { generateProcessor } = await import("@powerhousedao/codegen");
239
+ const validState = {
240
+ name: "Test Processor",
241
+ type: "relational",
242
+ documentTypes: [
243
+ { id: "dt-1", documentType: "powerhouse/document-model" },
244
+ ],
245
+ status: "CONFIRMED",
246
+ };
247
+ const strand = {
248
+ documentId: "test-doc-1",
249
+ documentType: "powerhouse/processor",
250
+ state: validState,
251
+ };
252
+ await processor.onStrands([strand]);
253
+ await vi.runAllTimersAsync();
254
+ expect(generateProcessor).toHaveBeenCalledWith("Test Processor", "relationalDb", ["powerhouse/document-model"], mockConfig.PH_CONFIG);
255
+ });
256
+ it("should not call generateProcessor for unsupported processor type", async () => {
257
+ const { generateProcessor } = await import("@powerhousedao/codegen");
258
+ const invalidState = {
259
+ name: "Test Processor",
260
+ type: "unsupported",
261
+ documentTypes: [
262
+ { id: "dt-1", documentType: "powerhouse/document-model" },
263
+ ],
264
+ status: "CONFIRMED",
265
+ };
266
+ const strand = {
267
+ documentId: "test-doc-1",
268
+ documentType: "powerhouse/processor",
269
+ state: invalidState,
270
+ };
271
+ await processor.onStrands([strand]);
272
+ await vi.runAllTimersAsync();
273
+ expect(generateProcessor).not.toHaveBeenCalled();
274
+ });
275
+ it("should not call generateProcessor for invalid processor strand (empty documentTypes)", async () => {
276
+ const { generateProcessor } = await import("@powerhousedao/codegen");
277
+ const invalidState = {
278
+ name: "Test Processor",
279
+ type: "analytics",
280
+ documentTypes: [],
281
+ status: "CONFIRMED",
282
+ };
283
+ const strand = {
284
+ documentId: "test-doc-1",
285
+ documentType: "powerhouse/processor",
286
+ state: invalidState,
287
+ };
288
+ await processor.onStrands([strand]);
289
+ await vi.runAllTimersAsync();
290
+ expect(generateProcessor).not.toHaveBeenCalled();
291
+ });
292
+ });
293
+ describe("App E2E", () => {
294
+ it("should process valid app strand without dragAndDrop", async () => {
295
+ const { generateDriveEditor, generateManifest } = await import("@powerhousedao/codegen");
296
+ const validState = {
297
+ name: "Test App",
298
+ status: "CONFIRMED",
299
+ isDragAndDropEnabled: false,
300
+ allowedDocumentTypes: [],
301
+ };
302
+ const strand = {
303
+ documentId: "test-doc-1",
304
+ documentType: "powerhouse/app",
305
+ state: validState,
306
+ };
307
+ await processor.onStrands([strand]);
308
+ await vi.runAllTimersAsync();
309
+ expect(generateDriveEditor).toHaveBeenCalledWith({
310
+ name: "Test App",
311
+ config: mockConfig.PH_CONFIG,
312
+ appId: "test-app",
313
+ allowedDocumentTypes: "",
314
+ isDragAndDropEnabled: false,
315
+ });
316
+ expect(generateManifest).toHaveBeenCalledWith({
317
+ apps: [
318
+ {
319
+ id: "test-app",
320
+ name: "Test App",
321
+ driveEditor: "test-app",
322
+ },
323
+ ],
324
+ }, mockConfig.CURRENT_WORKING_DIR);
325
+ });
326
+ it("should process valid app strand with dragAndDrop enabled", async () => {
327
+ const { generateDriveEditor, generateManifest } = await import("@powerhousedao/codegen");
328
+ const validState = {
329
+ name: "Test App",
330
+ status: "CONFIRMED",
331
+ isDragAndDropEnabled: true,
332
+ allowedDocumentTypes: [
333
+ "powerhouse/document-model",
334
+ "powerhouse/budget-statement",
335
+ ],
336
+ };
337
+ const strand = {
338
+ documentId: "test-doc-1",
339
+ documentType: "powerhouse/app",
340
+ state: validState,
341
+ };
342
+ await processor.onStrands([strand]);
343
+ await vi.runAllTimersAsync();
344
+ expect(generateDriveEditor).toHaveBeenCalledWith({
345
+ name: "Test App",
346
+ config: mockConfig.PH_CONFIG,
347
+ appId: "test-app",
348
+ allowedDocumentTypes: "powerhouse/document-model,powerhouse/budget-statement",
349
+ isDragAndDropEnabled: true,
350
+ });
351
+ expect(generateManifest).toHaveBeenCalled();
352
+ });
353
+ it("should not call codegen functions for invalid app strand (DRAFT status)", async () => {
354
+ const { generateDriveEditor, generateManifest } = await import("@powerhousedao/codegen");
355
+ const invalidState = {
356
+ name: "Test App",
357
+ status: "DRAFT",
358
+ isDragAndDropEnabled: false,
359
+ allowedDocumentTypes: [],
360
+ };
361
+ const strand = {
362
+ documentId: "test-doc-1",
363
+ documentType: "powerhouse/app",
364
+ state: invalidState,
365
+ };
366
+ await processor.onStrands([strand]);
367
+ await vi.runAllTimersAsync();
368
+ expect(generateDriveEditor).not.toHaveBeenCalled();
369
+ expect(generateManifest).not.toHaveBeenCalled();
370
+ });
371
+ });
372
+ describe("Subgraph E2E", () => {
373
+ it("should process valid subgraph strand and call generateSubgraph with null", async () => {
374
+ const { generateSubgraph, generateManifest } = await import("@powerhousedao/codegen");
375
+ const validState = {
376
+ name: "Test Subgraph",
377
+ status: "CONFIRMED",
378
+ };
379
+ const strand = {
380
+ documentId: "test-doc-1",
381
+ documentType: "powerhouse/subgraph",
382
+ state: validState,
383
+ };
384
+ await processor.onStrands([strand]);
385
+ await vi.runAllTimersAsync();
386
+ expect(generateSubgraph).toHaveBeenCalledWith("Test Subgraph", null, mockConfig.PH_CONFIG);
387
+ expect(generateManifest).toHaveBeenCalledWith({
388
+ subgraphs: [
389
+ {
390
+ id: "test-subgraph",
391
+ name: "Test Subgraph",
392
+ documentTypes: [],
393
+ },
394
+ ],
395
+ }, mockConfig.CURRENT_WORKING_DIR);
396
+ });
397
+ it("should not call codegen functions for invalid subgraph strand (DRAFT status)", async () => {
398
+ const { generateSubgraph, generateManifest } = await import("@powerhousedao/codegen");
399
+ const invalidState = {
400
+ name: "Test Subgraph",
401
+ status: "DRAFT",
402
+ };
403
+ const strand = {
404
+ documentId: "test-doc-1",
405
+ documentType: "powerhouse/subgraph",
406
+ state: invalidState,
407
+ };
408
+ await processor.onStrands([strand]);
409
+ await vi.runAllTimersAsync();
410
+ expect(generateSubgraph).not.toHaveBeenCalled();
411
+ expect(generateManifest).not.toHaveBeenCalled();
412
+ });
413
+ });
414
+ describe("Package E2E", () => {
415
+ it("should process valid package strand and call generateManifest", async () => {
416
+ const { generateManifest } = await import("@powerhousedao/codegen");
417
+ const validState = {
418
+ name: "Test Package",
419
+ category: "utility",
420
+ description: "A test package",
421
+ author: {
422
+ name: "Test Author",
423
+ website: "https://example.com",
424
+ },
425
+ };
426
+ const strand = {
427
+ documentId: "test-doc-1",
428
+ documentType: "powerhouse/package",
429
+ state: validState,
430
+ };
431
+ await processor.onStrands([strand]);
432
+ await vi.runAllTimersAsync();
433
+ expect(generateManifest).toHaveBeenCalledWith({
434
+ name: "Test Package",
435
+ category: "utility",
436
+ description: "A test package",
437
+ publisher: {
438
+ name: "Test Author",
439
+ url: "https://example.com",
440
+ },
441
+ }, mockConfig.CURRENT_WORKING_DIR);
442
+ });
443
+ it("should process package strand with missing optional fields", async () => {
444
+ const { generateManifest } = await import("@powerhousedao/codegen");
445
+ const stateWithoutAuthor = {
446
+ name: "Test Package",
447
+ category: "utility",
448
+ description: "A test package",
449
+ };
450
+ const strand = {
451
+ documentId: "test-doc-1",
452
+ documentType: "powerhouse/package",
453
+ state: stateWithoutAuthor,
454
+ };
455
+ await processor.onStrands([strand]);
456
+ await vi.runAllTimersAsync();
457
+ expect(generateManifest).toHaveBeenCalledWith({
458
+ name: "Test Package",
459
+ category: "utility",
460
+ description: "A test package",
461
+ publisher: {
462
+ name: "",
463
+ url: "",
464
+ },
465
+ }, mockConfig.CURRENT_WORKING_DIR);
466
+ });
467
+ });
468
+ describe("Multi-Strand E2E", () => {
469
+ it("should process multiple valid strands of different types in one batch", async () => {
470
+ const { generateEditor, generateSubgraph, generateManifest } = await import("@powerhousedao/codegen");
471
+ const editorState = {
472
+ name: "Test Editor",
473
+ documentTypes: [
474
+ { id: "dt-1", documentType: "powerhouse/document-model" },
475
+ ],
476
+ status: "CONFIRMED",
477
+ };
478
+ const subgraphState = {
479
+ name: "Test Subgraph",
480
+ status: "CONFIRMED",
481
+ };
482
+ const strands = [
483
+ {
484
+ documentId: "test-doc-1",
485
+ documentType: "powerhouse/document-editor",
486
+ state: editorState,
487
+ },
488
+ {
489
+ documentId: "test-doc-2",
490
+ documentType: "powerhouse/subgraph",
491
+ state: subgraphState,
492
+ },
493
+ ];
494
+ await processor.onStrands(strands);
495
+ await vi.runAllTimersAsync();
496
+ expect(generateEditor).toHaveBeenCalledWith("Test Editor", ["powerhouse/document-model"], mockConfig.PH_CONFIG, "test-editor");
497
+ expect(generateSubgraph).toHaveBeenCalledWith("Test Subgraph", null, mockConfig.PH_CONFIG);
498
+ // generateManifest should be called twice (once for each strand)
499
+ expect(generateManifest).toHaveBeenCalledTimes(2);
500
+ });
501
+ it("should process valid strands and skip invalid strands in the same batch", async () => {
502
+ const { generateEditor, generateSubgraph } = await import("@powerhousedao/codegen");
503
+ const validEditorState = {
504
+ name: "Test Editor",
505
+ documentTypes: [
506
+ { id: "dt-1", documentType: "powerhouse/document-model" },
507
+ ],
508
+ status: "CONFIRMED",
509
+ };
510
+ const invalidSubgraphState = {
511
+ name: "Test Subgraph",
512
+ status: "DRAFT", // Invalid - should be skipped
513
+ };
514
+ const strands = [
515
+ {
516
+ documentId: "test-doc-1",
517
+ documentType: "powerhouse/document-editor",
518
+ state: validEditorState,
519
+ },
520
+ {
521
+ documentId: "test-doc-2",
522
+ documentType: "powerhouse/subgraph",
523
+ state: invalidSubgraphState,
524
+ },
525
+ ];
526
+ await processor.onStrands(strands);
527
+ await vi.runAllTimersAsync();
528
+ // Valid strand should be processed
529
+ expect(generateEditor).toHaveBeenCalledWith("Test Editor", ["powerhouse/document-model"], mockConfig.PH_CONFIG, "test-editor");
530
+ // Invalid strand should NOT be processed
531
+ expect(generateSubgraph).not.toHaveBeenCalled();
532
+ });
533
+ it("should not process any strands when all are invalid", async () => {
534
+ const { generateEditor, generateSubgraph, generateManifest } = await import("@powerhousedao/codegen");
535
+ const invalidEditorState = {
536
+ name: "", // Invalid - missing name
537
+ documentTypes: [
538
+ { id: "dt-1", documentType: "powerhouse/document-model" },
539
+ ],
540
+ status: "CONFIRMED",
541
+ };
542
+ const invalidSubgraphState = {
543
+ name: "Test Subgraph",
544
+ status: "DRAFT", // Invalid - draft status
545
+ };
546
+ const strands = [
547
+ {
548
+ documentId: "test-doc-1",
549
+ documentType: "powerhouse/document-editor",
550
+ state: invalidEditorState,
551
+ },
552
+ {
553
+ documentId: "test-doc-2",
554
+ documentType: "powerhouse/subgraph",
555
+ state: invalidSubgraphState,
556
+ },
557
+ ];
558
+ await processor.onStrands(strands);
559
+ await vi.runAllTimersAsync();
560
+ // No strands should be processed
561
+ expect(generateEditor).not.toHaveBeenCalled();
562
+ expect(generateSubgraph).not.toHaveBeenCalled();
563
+ expect(generateManifest).not.toHaveBeenCalled();
564
+ });
565
+ });
566
+ describe("Edge Cases E2E", () => {
567
+ it("should not process strand with unsupported document type", async () => {
568
+ const { generateEditor, generateProcessor, generateManifest } = await import("@powerhousedao/codegen");
569
+ const strand = {
570
+ documentId: "test-doc-1",
571
+ documentType: "unsupported/document-type",
572
+ state: { name: "Test" },
573
+ };
574
+ await processor.onStrands([strand]);
575
+ await vi.runAllTimersAsync();
576
+ // No codegen functions should be called for unsupported types
577
+ expect(generateEditor).not.toHaveBeenCalled();
578
+ expect(generateProcessor).not.toHaveBeenCalled();
579
+ expect(generateManifest).not.toHaveBeenCalled();
580
+ });
581
+ it("should not process strand with missing documentId", async () => {
582
+ const { generateEditor, generateManifest } = await import("@powerhousedao/codegen");
583
+ const validState = {
584
+ name: "Test Editor",
585
+ documentTypes: [
586
+ { id: "dt-1", documentType: "powerhouse/document-model" },
587
+ ],
588
+ status: "CONFIRMED",
589
+ };
590
+ const strand = {
591
+ documentId: "",
592
+ documentType: "powerhouse/document-editor",
593
+ state: validState,
594
+ };
595
+ await processor.onStrands([strand]);
596
+ await vi.runAllTimersAsync();
597
+ // Should not process strand with empty documentId
598
+ expect(generateEditor).not.toHaveBeenCalled();
599
+ expect(generateManifest).not.toHaveBeenCalled();
600
+ });
601
+ it("should not process strand with missing state", async () => {
602
+ const { generateEditor, generateManifest } = await import("@powerhousedao/codegen");
603
+ const strand = {
604
+ documentId: "test-doc-1",
605
+ documentType: "powerhouse/document-editor",
606
+ state: undefined,
607
+ };
608
+ await processor.onStrands([strand]);
609
+ await vi.runAllTimersAsync();
610
+ // Should not process strand with undefined state
611
+ expect(generateEditor).not.toHaveBeenCalled();
612
+ expect(generateManifest).not.toHaveBeenCalled();
613
+ });
614
+ });
615
+ });
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=factory.test.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"factory.test.d.ts","sourceRoot":"","sources":["../../../../processors/codegen/__tests__/factory.test.ts"],"names":[],"mappings":""}