@auto-engineer/server-generator-apollo-emmett 0.8.5 → 0.8.7
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/.turbo/turbo-build.log +2 -2
- package/CHANGELOG.md +16 -0
- package/dist/src/codegen/scaffoldFromSchema.d.ts +3 -3
- package/dist/src/codegen/scaffoldFromSchema.d.ts.map +1 -1
- package/dist/src/codegen/scaffoldFromSchema.js +54 -18
- package/dist/src/codegen/scaffoldFromSchema.js.map +1 -1
- package/dist/{codegen → src/codegen}/templates/command/commands.specs.ts +1 -2
- package/dist/{codegen → src/codegen}/templates/command/decide.specs.specs.ts +3 -3
- package/dist/{codegen → src/codegen}/templates/command/decide.specs.ts +1 -5
- package/dist/{codegen → src/codegen}/templates/command/events.specs.ts +1 -2
- package/dist/{codegen → src/codegen}/templates/command/evolve.specs.ts +1 -2
- package/dist/{codegen → src/codegen}/templates/command/handle.specs.ts +1 -3
- package/dist/src/codegen/templates/command/mutation.resolver.specs.ts +363 -0
- package/dist/src/codegen/templates/command/mutation.resolver.ts.ejs +99 -0
- package/dist/{codegen → src/codegen}/templates/command/register.specs.ts +1 -2
- package/dist/{codegen → src/codegen}/templates/command/state.specs.ts +1 -2
- package/dist/{codegen → src/codegen}/templates/query/projection.specs.specs..ts +3 -3
- package/dist/{codegen → src/codegen}/templates/query/projection.specs.ts +5 -9
- package/dist/{codegen → src/codegen}/templates/query/query.resolver.specs.ts +194 -23
- package/dist/src/codegen/templates/query/query.resolver.ts.ejs +137 -0
- package/dist/{codegen → src/codegen}/templates/query/state.specs.ts +1 -2
- package/dist/{codegen → src/codegen}/templates/react/react.specs.specs.ts +2 -2
- package/dist/{codegen → src/codegen}/templates/react/react.specs.ts +3 -3
- package/dist/{codegen → src/codegen}/templates/react/register.specs.ts +3 -3
- package/dist/src/codegen/test-data/specVariant1.d.ts +1 -1
- package/dist/src/codegen/test-data/specVariant1.d.ts.map +1 -1
- package/dist/src/codegen/test-data/specVariant1.js +4 -2
- package/dist/src/codegen/test-data/specVariant1.js.map +1 -1
- package/dist/src/commands/generate-server.d.ts.map +1 -1
- package/dist/src/commands/generate-server.js +34 -24
- package/dist/src/commands/generate-server.js.map +1 -1
- package/dist/tsconfig.tsbuildinfo +1 -1
- package/package.json +8 -7
- package/src/codegen/scaffoldFromSchema.ts +52 -20
- package/src/codegen/templates/command/commands.specs.ts +1 -2
- package/src/codegen/templates/command/decide.specs.specs.ts +3 -3
- package/src/codegen/templates/command/decide.specs.ts +1 -5
- package/src/codegen/templates/command/events.specs.ts +1 -2
- package/src/codegen/templates/command/evolve.specs.ts +1 -2
- package/src/codegen/templates/command/handle.specs.ts +1 -3
- package/src/codegen/templates/command/mutation.resolver.specs.ts +247 -8
- package/src/codegen/templates/command/mutation.resolver.ts.ejs +86 -12
- package/src/codegen/templates/command/register.specs.ts +1 -2
- package/src/codegen/templates/command/state.specs.ts +1 -2
- package/src/codegen/templates/query/projection.specs.specs..ts +3 -3
- package/src/codegen/templates/query/projection.specs.ts +5 -9
- package/src/codegen/templates/query/query.resolver.specs.ts +194 -23
- package/src/codegen/templates/query/query.resolver.ts.ejs +84 -45
- package/src/codegen/templates/query/state.specs.ts +1 -2
- package/src/codegen/templates/react/react.specs.specs.ts +2 -2
- package/src/codegen/templates/react/react.specs.ts +3 -3
- package/src/codegen/templates/react/register.specs.ts +3 -3
- package/src/codegen/test-data/specVariant1.ts +5 -3
- package/src/commands/generate-server.ts +38 -30
- package/tsconfig.test.json +9 -0
- package/.turbo/turbo-test.log +0 -14
- package/.turbo/turbo-type-check.log +0 -4
- package/dist/codegen/templates/command/mutation.resolver.specs.ts +0 -124
- package/dist/codegen/templates/command/mutation.resolver.ts.ejs +0 -25
- package/dist/codegen/templates/query/query.resolver.ts.ejs +0 -98
- package/dist/src/codegen/templates/command/commands.specs.d.ts +0 -2
- package/dist/src/codegen/templates/command/commands.specs.d.ts.map +0 -1
- package/dist/src/codegen/templates/command/commands.specs.js +0 -96
- package/dist/src/codegen/templates/command/commands.specs.js.map +0 -1
- package/dist/src/codegen/templates/command/decide.specs.d.ts +0 -2
- package/dist/src/codegen/templates/command/decide.specs.d.ts.map +0 -1
- package/dist/src/codegen/templates/command/decide.specs.js +0 -567
- package/dist/src/codegen/templates/command/decide.specs.js.map +0 -1
- package/dist/src/codegen/templates/command/decide.specs.specs.d.ts +0 -2
- package/dist/src/codegen/templates/command/decide.specs.specs.d.ts.map +0 -1
- package/dist/src/codegen/templates/command/decide.specs.specs.js +0 -278
- package/dist/src/codegen/templates/command/decide.specs.specs.js.map +0 -1
- package/dist/src/codegen/templates/command/events.specs.d.ts +0 -2
- package/dist/src/codegen/templates/command/events.specs.d.ts.map +0 -1
- package/dist/src/codegen/templates/command/events.specs.js +0 -112
- package/dist/src/codegen/templates/command/events.specs.js.map +0 -1
- package/dist/src/codegen/templates/command/evolve.specs.d.ts +0 -2
- package/dist/src/codegen/templates/command/evolve.specs.d.ts.map +0 -1
- package/dist/src/codegen/templates/command/evolve.specs.js +0 -108
- package/dist/src/codegen/templates/command/evolve.specs.js.map +0 -1
- package/dist/src/codegen/templates/command/handle.specs.d.ts +0 -2
- package/dist/src/codegen/templates/command/handle.specs.d.ts.map +0 -1
- package/dist/src/codegen/templates/command/handle.specs.js +0 -326
- package/dist/src/codegen/templates/command/handle.specs.js.map +0 -1
- package/dist/src/codegen/templates/command/mutation.resolver.specs.d.ts +0 -2
- package/dist/src/codegen/templates/command/mutation.resolver.specs.d.ts.map +0 -1
- package/dist/src/codegen/templates/command/mutation.resolver.specs.js +0 -121
- package/dist/src/codegen/templates/command/mutation.resolver.specs.js.map +0 -1
- package/dist/src/codegen/templates/command/register.specs.d.ts +0 -2
- package/dist/src/codegen/templates/command/register.specs.d.ts.map +0 -1
- package/dist/src/codegen/templates/command/register.specs.js +0 -113
- package/dist/src/codegen/templates/command/register.specs.js.map +0 -1
- package/dist/src/codegen/templates/command/state.specs.d.ts +0 -2
- package/dist/src/codegen/templates/command/state.specs.d.ts.map +0 -1
- package/dist/src/codegen/templates/command/state.specs.js +0 -133
- package/dist/src/codegen/templates/command/state.specs.js.map +0 -1
- package/dist/src/codegen/templates/query/projection.specs.d.ts +0 -2
- package/dist/src/codegen/templates/query/projection.specs.d.ts.map +0 -1
- package/dist/src/codegen/templates/query/projection.specs.js +0 -363
- package/dist/src/codegen/templates/query/projection.specs.js.map +0 -1
- package/dist/src/codegen/templates/query/projection.specs.specs..d.ts +0 -2
- package/dist/src/codegen/templates/query/projection.specs.specs..d.ts.map +0 -1
- package/dist/src/codegen/templates/query/projection.specs.specs..js +0 -293
- package/dist/src/codegen/templates/query/projection.specs.specs..js.map +0 -1
- package/dist/src/codegen/templates/query/query.resolver.specs.d.ts +0 -2
- package/dist/src/codegen/templates/query/query.resolver.specs.d.ts.map +0 -1
- package/dist/src/codegen/templates/query/query.resolver.specs.js +0 -249
- package/dist/src/codegen/templates/query/query.resolver.specs.js.map +0 -1
- package/dist/src/codegen/templates/query/state.specs.d.ts +0 -2
- package/dist/src/codegen/templates/query/state.specs.d.ts.map +0 -1
- package/dist/src/codegen/templates/query/state.specs.js +0 -67
- package/dist/src/codegen/templates/query/state.specs.js.map +0 -1
- package/dist/src/codegen/templates/react/react.specs.d.ts +0 -2
- package/dist/src/codegen/templates/react/react.specs.d.ts.map +0 -1
- package/dist/src/codegen/templates/react/react.specs.js +0 -265
- package/dist/src/codegen/templates/react/react.specs.js.map +0 -1
- package/dist/src/codegen/templates/react/react.specs.specs.d.ts +0 -2
- package/dist/src/codegen/templates/react/react.specs.specs.d.ts.map +0 -1
- package/dist/src/codegen/templates/react/react.specs.specs.js +0 -229
- package/dist/src/codegen/templates/react/react.specs.specs.js.map +0 -1
- package/dist/src/codegen/templates/react/register.specs.d.ts +0 -2
- package/dist/src/codegen/templates/react/register.specs.d.ts.map +0 -1
- package/dist/src/codegen/templates/react/register.specs.js +0 -246
- package/dist/src/codegen/templates/react/register.specs.js.map +0 -1
- /package/dist/{codegen → src/codegen}/templates/command/commands.ts.ejs +0 -0
- /package/dist/{codegen → src/codegen}/templates/command/decide.specs.ts.ejs +0 -0
- /package/dist/{codegen → src/codegen}/templates/command/decide.ts.ejs +0 -0
- /package/dist/{codegen → src/codegen}/templates/command/events.ts.ejs +0 -0
- /package/dist/{codegen → src/codegen}/templates/command/evolve.ts.ejs +0 -0
- /package/dist/{codegen → src/codegen}/templates/command/handle.ts.ejs +0 -0
- /package/dist/{codegen → src/codegen}/templates/command/register.ts.ejs +0 -0
- /package/dist/{codegen → src/codegen}/templates/command/state.ts.ejs +0 -0
- /package/dist/{codegen → src/codegen}/templates/query/projection.specs.ts.ejs +0 -0
- /package/dist/{codegen → src/codegen}/templates/query/projection.ts.ejs +0 -0
- /package/dist/{codegen → src/codegen}/templates/query/state.ts.ejs +0 -0
- /package/dist/{codegen → src/codegen}/templates/react/react.specs.ts.ejs +0 -0
- /package/dist/{codegen → src/codegen}/templates/react/react.ts.ejs +0 -0
- /package/dist/{codegen → src/codegen}/templates/react/register.ts.ejs +0 -0
- /package/dist/{domain → src/domain}/shared/ReadModel.ts +0 -0
- /package/dist/{domain → src/domain}/shared/index.ts +0 -0
- /package/dist/{domain → src/domain}/shared/reactorSpecification.ts +0 -0
- /package/dist/{domain → src/domain}/shared/sendCommand.ts +0 -0
- /package/dist/{domain → src/domain}/shared/types.ts +0 -0
- /package/dist/{server.ts → src/server.ts} +0 -0
- /package/dist/{utils → src/utils}/index.ts +0 -0
- /package/dist/{utils → src/utils}/loadProjections.ts +0 -0
- /package/dist/{utils → src/utils}/loadRegisterFiles.ts +0 -0
- /package/dist/{utils → src/utils}/loadResolvers.ts +0 -0
package/package.json
CHANGED
|
@@ -5,8 +5,8 @@
|
|
|
5
5
|
"types": "./dist/src/index.d.ts",
|
|
6
6
|
"exports": {
|
|
7
7
|
".": {
|
|
8
|
-
"types": "./dist/index.d.ts",
|
|
9
|
-
"import": "./dist/index.js"
|
|
8
|
+
"types": "./dist/src/index.d.ts",
|
|
9
|
+
"import": "./dist/src/index.js"
|
|
10
10
|
}
|
|
11
11
|
},
|
|
12
12
|
"dependencies": {
|
|
@@ -25,10 +25,11 @@
|
|
|
25
25
|
"reflect-metadata": "^0.2.2",
|
|
26
26
|
"type-fest": "^4.41.0",
|
|
27
27
|
"type-graphql": "^2.0.0-rc.2",
|
|
28
|
+
"graphql-type-json": "^0.3.2",
|
|
28
29
|
"uuid": "^10.0.0",
|
|
29
30
|
"web-streams-polyfill": "^4.1.0",
|
|
30
|
-
"@auto-engineer/
|
|
31
|
-
"@auto-engineer/
|
|
31
|
+
"@auto-engineer/message-bus": "0.8.7",
|
|
32
|
+
"@auto-engineer/flow": "0.8.7"
|
|
32
33
|
},
|
|
33
34
|
"publishConfig": {
|
|
34
35
|
"access": "public"
|
|
@@ -36,12 +37,12 @@
|
|
|
36
37
|
"devDependencies": {
|
|
37
38
|
"@types/ejs": "^3.1.5",
|
|
38
39
|
"@types/fs-extra": "^11.0.4",
|
|
39
|
-
"@auto-engineer/cli": "0.8.
|
|
40
|
+
"@auto-engineer/cli": "0.8.7"
|
|
40
41
|
},
|
|
41
|
-
"version": "0.8.
|
|
42
|
+
"version": "0.8.7",
|
|
42
43
|
"scripts": {
|
|
43
44
|
"generate:server": "tsx src/cli/index.ts",
|
|
44
|
-
"build": "tsc && tsx ../../scripts/fix-esm-imports.ts && rm -rf dist/codegen/templates && mkdir -p dist/codegen && cp -r src/codegen/templates dist/codegen/templates && cp src/server.ts dist/ && cp -r src/utils dist/ && cp -r src/domain dist/",
|
|
45
|
+
"build": "tsc && tsx ../../scripts/fix-esm-imports.ts && rm -rf dist/src/codegen/templates && mkdir -p dist/src/codegen && cp -r src/codegen/templates dist/src/codegen/templates && cp src/server.ts dist/src && cp -r src/utils dist/src && cp -r src/domain dist/src",
|
|
45
46
|
"test": "vitest run --reporter=dot",
|
|
46
47
|
"type-check": "tsc --noEmit --project tsconfig.json",
|
|
47
48
|
"lint": "eslint 'src/**/*.ts' --ignore-pattern '**/*.specs.ts' --ignore-pattern '**/.tmp/**' --max-warnings 0 --config ../../eslint.config.ts",
|
|
@@ -6,7 +6,7 @@ import ejs from 'ejs';
|
|
|
6
6
|
import { ensureDirExists, ensureDirPath, toKebabCase } from './utils/path';
|
|
7
7
|
import { camelCase, pascalCase } from 'change-case';
|
|
8
8
|
import prettier from 'prettier';
|
|
9
|
-
import { Flow, Slice,
|
|
9
|
+
import { Flow, Slice, Model } from '@auto-engineer/flow';
|
|
10
10
|
import createDebug from 'debug';
|
|
11
11
|
|
|
12
12
|
const debug = createDebug('emmett:scaffold');
|
|
@@ -59,28 +59,56 @@ async function renderTemplate(templatePath: string, data: Record<string, unknown
|
|
|
59
59
|
});
|
|
60
60
|
debugTemplate('Template compiled successfully');
|
|
61
61
|
|
|
62
|
-
const
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
if (
|
|
67
|
-
if (
|
|
68
|
-
if (
|
|
69
|
-
|
|
70
|
-
if (
|
|
71
|
-
if (
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
}
|
|
62
|
+
const isInlineObject = (s: string) => /^\{[\s\S]*\}$/.test(s.trim());
|
|
63
|
+
const isStringLiteralUnion = (s: string) => /^"(?:[^"]+)"\s*(\|\s*"(?:[^"]+)")+$/.test(s.trim());
|
|
64
|
+
const convertPrimitiveType = (base: string): string => {
|
|
65
|
+
// GraphQL-native scalars
|
|
66
|
+
if (base === 'ID') return 'ID';
|
|
67
|
+
if (base === 'Int') return 'Int';
|
|
68
|
+
if (base === 'Float') return 'Float';
|
|
69
|
+
// TS primitives
|
|
70
|
+
if (base === 'string') return 'String';
|
|
71
|
+
if (base === 'number') return 'Float';
|
|
72
|
+
if (base === 'boolean') return 'Boolean';
|
|
73
|
+
if (base === 'Date') return 'GraphQLISODateTime';
|
|
75
74
|
return 'String';
|
|
76
75
|
};
|
|
77
76
|
|
|
77
|
+
const graphqlType = (rawTs: string): string => {
|
|
78
|
+
const t = (rawTs ?? '').trim();
|
|
79
|
+
if (!t) return 'String';
|
|
80
|
+
const base = t.replace(/\s*\|\s*null\b/g, '').trim();
|
|
81
|
+
// arrays
|
|
82
|
+
const arr1 = base.match(/^Array<(.*)>$/);
|
|
83
|
+
const arr2 = base.match(/^(.*)\[\]$/);
|
|
84
|
+
if (arr1) return `[${graphqlType(arr1[1].trim())}]`;
|
|
85
|
+
if (arr2) return `[${graphqlType(arr2[1].trim())}]`;
|
|
86
|
+
// JSON
|
|
87
|
+
if (base === 'unknown' || base === 'any') return 'GraphQLJSON';
|
|
88
|
+
if (base === 'object') return 'JSON';
|
|
89
|
+
if (isInlineObject(base)) return 'JSON';
|
|
90
|
+
if (isStringLiteralUnion(base)) return 'String';
|
|
91
|
+
return convertPrimitiveType(base);
|
|
92
|
+
};
|
|
93
|
+
|
|
94
|
+
const toTsFieldType = (ts: string): string => {
|
|
95
|
+
if (!ts) return 'string';
|
|
96
|
+
const t = ts.trim();
|
|
97
|
+
const arr = t.match(/^Array<(.*)>$/);
|
|
98
|
+
if (arr) return `${arr[1].trim()}[]`;
|
|
99
|
+
return t;
|
|
100
|
+
};
|
|
101
|
+
|
|
102
|
+
const isNullable = (rawTs: string): boolean => /\|\s*null\b/.test(rawTs);
|
|
103
|
+
|
|
78
104
|
const result = await template({
|
|
79
105
|
...data,
|
|
80
106
|
pascalCase,
|
|
81
107
|
toKebabCase,
|
|
82
108
|
camelCase,
|
|
83
109
|
graphqlType,
|
|
110
|
+
isNullable,
|
|
111
|
+
toTsFieldType,
|
|
84
112
|
formatTsValue,
|
|
85
113
|
formatDataObject,
|
|
86
114
|
messages: data.messages,
|
|
@@ -201,7 +229,7 @@ async function prepareTemplateData(
|
|
|
201
229
|
commandSchemasByName: Record<string, Message>,
|
|
202
230
|
projectionIdField: string | undefined,
|
|
203
231
|
allMessages?: MessageDefinition[],
|
|
204
|
-
integrations?:
|
|
232
|
+
integrations?: Model['integrations'],
|
|
205
233
|
): Promise<Record<string, unknown>> {
|
|
206
234
|
debug('Preparing template data for slice: %s (flow: %s)', slice.name, flow.name);
|
|
207
235
|
debug(' Commands: %d', commands.length);
|
|
@@ -226,12 +254,16 @@ async function prepareTemplateData(
|
|
|
226
254
|
const uniqueCommands = Array.from(new Map(commands.map((c) => [c.type, c])).values());
|
|
227
255
|
debug(' Unique commands: %d', uniqueCommands.length);
|
|
228
256
|
|
|
257
|
+
const allowedForSlice = new Set(Object.keys(gwtMapping));
|
|
258
|
+
const filteredCommands =
|
|
259
|
+
allowedForSlice.size > 0 ? uniqueCommands.filter((c) => allowedForSlice.has(c.type)) : uniqueCommands;
|
|
260
|
+
|
|
229
261
|
return {
|
|
230
262
|
flowName: flow.name,
|
|
231
263
|
sliceName: slice.name,
|
|
232
264
|
slice,
|
|
233
265
|
stream: { pattern: streamPattern, id: streamId },
|
|
234
|
-
commands:
|
|
266
|
+
commands: filteredCommands,
|
|
235
267
|
events,
|
|
236
268
|
states,
|
|
237
269
|
gwtMapping,
|
|
@@ -343,7 +375,7 @@ async function generateFilesForSlice(
|
|
|
343
375
|
sliceDir: string,
|
|
344
376
|
messages: MessageDefinition[],
|
|
345
377
|
flows: Flow[],
|
|
346
|
-
integrations?:
|
|
378
|
+
integrations?: Model['integrations'],
|
|
347
379
|
): Promise<FilePlan[]> {
|
|
348
380
|
debugSlice('Generating files for slice: %s (type: %s)', slice.name, slice.type);
|
|
349
381
|
debugSlice(' Flow: %s', flow.name);
|
|
@@ -391,8 +423,8 @@ async function generateFilesForSlice(
|
|
|
391
423
|
|
|
392
424
|
export async function generateScaffoldFilePlans(
|
|
393
425
|
flows: Flow[],
|
|
394
|
-
messages:
|
|
395
|
-
integrations?:
|
|
426
|
+
messages: Model['messages'],
|
|
427
|
+
integrations?: Model['integrations'],
|
|
396
428
|
baseDir = 'src/domain/flows',
|
|
397
429
|
): Promise<FilePlan[]> {
|
|
398
430
|
debug('Generating scaffold file plans');
|
|
@@ -445,7 +477,7 @@ export async function writeScaffoldFilePlans(plans: FilePlan[]) {
|
|
|
445
477
|
|
|
446
478
|
export async function scaffoldFromSchema(
|
|
447
479
|
flows: Flow[],
|
|
448
|
-
messages:
|
|
480
|
+
messages: Model['messages'],
|
|
449
481
|
baseDir = 'src/domain/flows',
|
|
450
482
|
): Promise<void> {
|
|
451
483
|
debug('Starting scaffold from schema');
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { describe, it, expect } from 'vitest';
|
|
2
|
-
import {
|
|
2
|
+
import { Model as SpecsSchema } from '@auto-engineer/flow';
|
|
3
3
|
import { generateScaffoldFilePlans } from '../../scaffoldFromSchema';
|
|
4
4
|
|
|
5
5
|
describe('commands.ts.ejs', () => {
|
|
@@ -15,7 +15,6 @@ describe('commands.ts.ejs', () => {
|
|
|
15
15
|
name: 'Create listing',
|
|
16
16
|
client: {
|
|
17
17
|
description: 'test',
|
|
18
|
-
specs: [],
|
|
19
18
|
},
|
|
20
19
|
server: {
|
|
21
20
|
description: 'test',
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { describe, it, expect } from 'vitest';
|
|
2
|
-
import {
|
|
2
|
+
import { Model as SpecsSchema } from '@auto-engineer/flow';
|
|
3
3
|
import { generateScaffoldFilePlans } from '../../scaffoldFromSchema';
|
|
4
4
|
|
|
5
5
|
describe('spec.ts.ejs', () => {
|
|
@@ -13,7 +13,7 @@ describe('spec.ts.ejs', () => {
|
|
|
13
13
|
{
|
|
14
14
|
type: 'command',
|
|
15
15
|
name: 'Create listing',
|
|
16
|
-
client: { description: ''
|
|
16
|
+
client: { description: '' },
|
|
17
17
|
server: {
|
|
18
18
|
description: '',
|
|
19
19
|
specs: {
|
|
@@ -153,7 +153,7 @@ describe('spec.ts.ejs', () => {
|
|
|
153
153
|
{
|
|
154
154
|
type: 'command',
|
|
155
155
|
name: 'Remove listing',
|
|
156
|
-
client: { description: ''
|
|
156
|
+
client: { description: '' },
|
|
157
157
|
server: {
|
|
158
158
|
description: '',
|
|
159
159
|
specs: {
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { describe, it, expect } from 'vitest';
|
|
2
|
-
import {
|
|
2
|
+
import { Model as SpecsSchema } from '@auto-engineer/flow';
|
|
3
3
|
import { generateScaffoldFilePlans } from '../../scaffoldFromSchema';
|
|
4
4
|
|
|
5
5
|
describe('decide.ts.ejs', () => {
|
|
@@ -15,7 +15,6 @@ describe('decide.ts.ejs', () => {
|
|
|
15
15
|
name: 'Create listing',
|
|
16
16
|
client: {
|
|
17
17
|
description: 'test',
|
|
18
|
-
specs: [],
|
|
19
18
|
},
|
|
20
19
|
server: {
|
|
21
20
|
description: 'test',
|
|
@@ -126,7 +125,6 @@ describe('decide.ts.ejs', () => {
|
|
|
126
125
|
name: 'Remove listing',
|
|
127
126
|
client: {
|
|
128
127
|
description: 'test',
|
|
129
|
-
specs: [],
|
|
130
128
|
},
|
|
131
129
|
server: {
|
|
132
130
|
description: 'test',
|
|
@@ -252,7 +250,6 @@ describe('decide.ts.ejs', () => {
|
|
|
252
250
|
name: 'Create listing',
|
|
253
251
|
client: {
|
|
254
252
|
description: 'test',
|
|
255
|
-
specs: [],
|
|
256
253
|
},
|
|
257
254
|
server: {
|
|
258
255
|
description: 'test',
|
|
@@ -398,7 +395,6 @@ describe('decide.ts.ejs', () => {
|
|
|
398
395
|
stream: 'session-${sessionId}',
|
|
399
396
|
client: {
|
|
400
397
|
description: 'test',
|
|
401
|
-
specs: [],
|
|
402
398
|
},
|
|
403
399
|
server: {
|
|
404
400
|
description: '',
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { describe, it, expect } from 'vitest';
|
|
2
|
-
import {
|
|
2
|
+
import { Model as SpecsSchema } from '@auto-engineer/flow';
|
|
3
3
|
import { generateScaffoldFilePlans } from '../../scaffoldFromSchema';
|
|
4
4
|
|
|
5
5
|
describe('events.ts.ejs', () => {
|
|
@@ -15,7 +15,6 @@ describe('events.ts.ejs', () => {
|
|
|
15
15
|
name: 'Create listing',
|
|
16
16
|
client: {
|
|
17
17
|
description: 'test',
|
|
18
|
-
specs: [],
|
|
19
18
|
},
|
|
20
19
|
server: {
|
|
21
20
|
description: 'test',
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { describe, it, expect } from 'vitest';
|
|
2
|
-
import {
|
|
2
|
+
import { Model as SpecsSchema } from '@auto-engineer/flow';
|
|
3
3
|
import { generateScaffoldFilePlans } from '../../scaffoldFromSchema';
|
|
4
4
|
|
|
5
5
|
describe('evolve.ts.ejs', () => {
|
|
@@ -15,7 +15,6 @@ describe('evolve.ts.ejs', () => {
|
|
|
15
15
|
name: 'Create listing',
|
|
16
16
|
client: {
|
|
17
17
|
description: 'test',
|
|
18
|
-
specs: [],
|
|
19
18
|
},
|
|
20
19
|
server: {
|
|
21
20
|
description: 'test',
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { describe, it, expect } from 'vitest';
|
|
2
2
|
import { generateScaffoldFilePlans } from '../../scaffoldFromSchema';
|
|
3
|
-
import {
|
|
3
|
+
import { Model as SpecsSchema } from '@auto-engineer/flow';
|
|
4
4
|
|
|
5
5
|
describe('generateScaffoldFilePlans', () => {
|
|
6
6
|
it('should generate a valid handle file', async () => {
|
|
@@ -16,7 +16,6 @@ describe('generateScaffoldFilePlans', () => {
|
|
|
16
16
|
stream: 'listing-${propertyId}',
|
|
17
17
|
client: {
|
|
18
18
|
description: 'test',
|
|
19
|
-
specs: [],
|
|
20
19
|
},
|
|
21
20
|
server: {
|
|
22
21
|
description: 'test',
|
|
@@ -142,7 +141,6 @@ describe('generateScaffoldFilePlans', () => {
|
|
|
142
141
|
stream: 'session-${sessionId}',
|
|
143
142
|
client: {
|
|
144
143
|
description: 'test',
|
|
145
|
-
specs: [],
|
|
146
144
|
},
|
|
147
145
|
server: {
|
|
148
146
|
description: '',
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { describe, it, expect } from 'vitest';
|
|
2
2
|
import { generateScaffoldFilePlans } from '../../scaffoldFromSchema';
|
|
3
|
-
import {
|
|
3
|
+
import { Model as SpecsSchema } from '@auto-engineer/flow';
|
|
4
4
|
|
|
5
5
|
describe('mutation.resolver.ts.ejs', () => {
|
|
6
6
|
it('should generate a valid mutation resolver file', async () => {
|
|
@@ -15,7 +15,6 @@ describe('mutation.resolver.ts.ejs', () => {
|
|
|
15
15
|
name: 'Create listing',
|
|
16
16
|
client: {
|
|
17
17
|
description: 'A form that allows users to add a new listing',
|
|
18
|
-
specs: [],
|
|
19
18
|
},
|
|
20
19
|
server: {
|
|
21
20
|
description: 'Handles listing creation',
|
|
@@ -77,30 +76,40 @@ describe('mutation.resolver.ts.ejs', () => {
|
|
|
77
76
|
const mutationFile = plans.find((p) => p.outputPath.endsWith('mutation.resolver.ts'));
|
|
78
77
|
|
|
79
78
|
expect(mutationFile?.contents).toMatchInlineSnapshot(`
|
|
80
|
-
"import { Mutation, Resolver, Arg, Ctx, Field, InputType } from 'type-graphql';
|
|
79
|
+
"import { Mutation, Resolver, Arg, Ctx, Field, InputType, GraphQLISODateTime } from 'type-graphql';
|
|
80
|
+
import { GraphQLJSON } from 'graphql-type-json';
|
|
81
81
|
import { type GraphQLContext, sendCommand, MutationResponse } from '../../../shared';
|
|
82
82
|
|
|
83
83
|
@InputType()
|
|
84
84
|
export class CreateListingInput {
|
|
85
85
|
@Field(() => String)
|
|
86
86
|
propertyId!: string;
|
|
87
|
+
|
|
87
88
|
@Field(() => String)
|
|
88
89
|
title!: string;
|
|
89
|
-
|
|
90
|
+
|
|
91
|
+
@Field(() => Float)
|
|
90
92
|
pricePerNight!: number;
|
|
91
|
-
|
|
93
|
+
|
|
94
|
+
@Field(() => Float)
|
|
92
95
|
maxGuests!: number;
|
|
96
|
+
|
|
93
97
|
@Field(() => [String])
|
|
94
98
|
amenities!: string[];
|
|
99
|
+
|
|
95
100
|
@Field(() => Boolean)
|
|
96
101
|
available!: boolean;
|
|
102
|
+
|
|
97
103
|
@Field(() => [String])
|
|
98
104
|
tags!: string[];
|
|
99
|
-
|
|
105
|
+
|
|
106
|
+
@Field(() => Float)
|
|
100
107
|
rating!: number;
|
|
101
|
-
|
|
108
|
+
|
|
109
|
+
@Field(() => JSON)
|
|
102
110
|
metadata!: object;
|
|
103
|
-
|
|
111
|
+
|
|
112
|
+
@Field(() => GraphQLISODateTime)
|
|
104
113
|
listedAt!: Date;
|
|
105
114
|
}
|
|
106
115
|
|
|
@@ -121,4 +130,234 @@ describe('mutation.resolver.ts.ejs', () => {
|
|
|
121
130
|
"
|
|
122
131
|
`);
|
|
123
132
|
});
|
|
133
|
+
|
|
134
|
+
it('should generate the mutation resolver for AnswerQuestion', async () => {
|
|
135
|
+
const spec: SpecsSchema = {
|
|
136
|
+
variant: 'specs',
|
|
137
|
+
flows: [
|
|
138
|
+
{
|
|
139
|
+
name: 'Questionnaires',
|
|
140
|
+
slices: [
|
|
141
|
+
{
|
|
142
|
+
name: 'submits a questionnaire answer',
|
|
143
|
+
type: 'command',
|
|
144
|
+
client: {
|
|
145
|
+
description: '',
|
|
146
|
+
specs: {
|
|
147
|
+
name: '',
|
|
148
|
+
rules: [
|
|
149
|
+
'display a success message when the answer is submitted',
|
|
150
|
+
'display an error message when the answer submission is rejected',
|
|
151
|
+
],
|
|
152
|
+
},
|
|
153
|
+
},
|
|
154
|
+
request:
|
|
155
|
+
'mutation AnswerQuestion($input: AnswerQuestionInput!) {\\n answerQuestion(input: $input) {\\n success\\n }\\n}',
|
|
156
|
+
server: {
|
|
157
|
+
description: '',
|
|
158
|
+
data: [
|
|
159
|
+
{
|
|
160
|
+
target: { type: 'Event', name: 'QuestionAnswered' },
|
|
161
|
+
destination: { type: 'stream', pattern: 'questionnaire-participantId' },
|
|
162
|
+
},
|
|
163
|
+
{
|
|
164
|
+
target: { type: 'Event', name: 'QuestionnaireEditRejected' },
|
|
165
|
+
destination: { type: 'stream', pattern: 'questionnaire-participantId' },
|
|
166
|
+
},
|
|
167
|
+
],
|
|
168
|
+
specs: {
|
|
169
|
+
name: '',
|
|
170
|
+
rules: [
|
|
171
|
+
{
|
|
172
|
+
description: 'answers are allowed while the questionnaire has not been submitted',
|
|
173
|
+
examples: [
|
|
174
|
+
{
|
|
175
|
+
description: 'no questions have been answered yet',
|
|
176
|
+
when: {
|
|
177
|
+
commandRef: 'AnswerQuestion',
|
|
178
|
+
exampleData: {
|
|
179
|
+
questionnaireId: 'q-001',
|
|
180
|
+
participantId: 'participant-abc',
|
|
181
|
+
questionId: 'q1',
|
|
182
|
+
answer: 'Yes',
|
|
183
|
+
},
|
|
184
|
+
},
|
|
185
|
+
then: [
|
|
186
|
+
{
|
|
187
|
+
eventRef: 'QuestionAnswered',
|
|
188
|
+
exampleData: {
|
|
189
|
+
questionnaireId: 'q-001',
|
|
190
|
+
participantId: 'participant-abc',
|
|
191
|
+
questionId: 'q1',
|
|
192
|
+
answer: 'Yes',
|
|
193
|
+
savedAt: '2030-01-01T09:05:00.000Z',
|
|
194
|
+
},
|
|
195
|
+
},
|
|
196
|
+
],
|
|
197
|
+
},
|
|
198
|
+
],
|
|
199
|
+
},
|
|
200
|
+
],
|
|
201
|
+
},
|
|
202
|
+
},
|
|
203
|
+
},
|
|
204
|
+
],
|
|
205
|
+
},
|
|
206
|
+
],
|
|
207
|
+
messages: [
|
|
208
|
+
{
|
|
209
|
+
type: 'command',
|
|
210
|
+
name: 'AnswerQuestion',
|
|
211
|
+
fields: [
|
|
212
|
+
{ name: 'questionnaireId', type: 'string', required: true },
|
|
213
|
+
{ name: 'participantId', type: 'string', required: true },
|
|
214
|
+
{ name: 'questionId', type: 'string', required: true },
|
|
215
|
+
{ name: 'answer', type: 'unknown', required: true },
|
|
216
|
+
],
|
|
217
|
+
metadata: { version: 1 },
|
|
218
|
+
},
|
|
219
|
+
],
|
|
220
|
+
integrations: [],
|
|
221
|
+
};
|
|
222
|
+
|
|
223
|
+
const plans = await generateScaffoldFilePlans(spec.flows, spec.messages, undefined, 'src/domain/flows');
|
|
224
|
+
const mutationFile = plans.find(
|
|
225
|
+
(p) =>
|
|
226
|
+
p.outputPath.endsWith('mutation.resolver.ts') && p.contents.includes('export class AnswerQuestionResolver'),
|
|
227
|
+
);
|
|
228
|
+
|
|
229
|
+
expect(mutationFile?.contents).toMatchInlineSnapshot(`
|
|
230
|
+
"import { Mutation, Resolver, Arg, Ctx, Field, InputType } from 'type-graphql';
|
|
231
|
+
import { GraphQLJSON } from 'graphql-type-json';
|
|
232
|
+
import { type GraphQLContext, sendCommand, MutationResponse } from '../../../shared';
|
|
233
|
+
|
|
234
|
+
@InputType()
|
|
235
|
+
export class AnswerQuestionInput {
|
|
236
|
+
@Field(() => String)
|
|
237
|
+
questionnaireId!: string;
|
|
238
|
+
|
|
239
|
+
@Field(() => String)
|
|
240
|
+
participantId!: string;
|
|
241
|
+
|
|
242
|
+
@Field(() => String)
|
|
243
|
+
questionId!: string;
|
|
244
|
+
|
|
245
|
+
@Field(() => GraphQLJSON)
|
|
246
|
+
answer!: unknown;
|
|
247
|
+
}
|
|
248
|
+
|
|
249
|
+
@Resolver()
|
|
250
|
+
export class AnswerQuestionResolver {
|
|
251
|
+
@Mutation(() => MutationResponse)
|
|
252
|
+
async answerQuestion(
|
|
253
|
+
@Arg('input', () => AnswerQuestionInput) input: AnswerQuestionInput,
|
|
254
|
+
@Ctx() ctx: GraphQLContext,
|
|
255
|
+
): Promise<MutationResponse> {
|
|
256
|
+
return await sendCommand(ctx.messageBus, {
|
|
257
|
+
type: 'AnswerQuestion',
|
|
258
|
+
kind: 'Command',
|
|
259
|
+
data: { ...input },
|
|
260
|
+
});
|
|
261
|
+
}
|
|
262
|
+
}
|
|
263
|
+
"
|
|
264
|
+
`);
|
|
265
|
+
});
|
|
266
|
+
|
|
267
|
+
it('generates nested input types for inline object arrays in a mutation', async () => {
|
|
268
|
+
const spec: SpecsSchema = {
|
|
269
|
+
variant: 'specs',
|
|
270
|
+
flows: [
|
|
271
|
+
{
|
|
272
|
+
name: 'Cart',
|
|
273
|
+
slices: [
|
|
274
|
+
{
|
|
275
|
+
type: 'command',
|
|
276
|
+
name: 'Add items to cart',
|
|
277
|
+
client: { description: '' },
|
|
278
|
+
server: {
|
|
279
|
+
description: '',
|
|
280
|
+
specs: {
|
|
281
|
+
name: '',
|
|
282
|
+
rules: [
|
|
283
|
+
{
|
|
284
|
+
description: 'add items',
|
|
285
|
+
examples: [
|
|
286
|
+
{
|
|
287
|
+
description: 'happy path',
|
|
288
|
+
when: {
|
|
289
|
+
commandRef: 'AddItemsToCart',
|
|
290
|
+
exampleData: {
|
|
291
|
+
sessionId: 's-1',
|
|
292
|
+
items: [{ productId: 'p1', quantity: 2 }],
|
|
293
|
+
},
|
|
294
|
+
},
|
|
295
|
+
then: [],
|
|
296
|
+
},
|
|
297
|
+
],
|
|
298
|
+
},
|
|
299
|
+
],
|
|
300
|
+
},
|
|
301
|
+
},
|
|
302
|
+
},
|
|
303
|
+
],
|
|
304
|
+
},
|
|
305
|
+
],
|
|
306
|
+
messages: [
|
|
307
|
+
{
|
|
308
|
+
type: 'command',
|
|
309
|
+
name: 'AddItemsToCart',
|
|
310
|
+
fields: [
|
|
311
|
+
{ name: 'sessionId', type: 'string', required: true },
|
|
312
|
+
{ name: 'items', type: 'Array<{ productId: string; quantity: number }>', required: true },
|
|
313
|
+
],
|
|
314
|
+
},
|
|
315
|
+
],
|
|
316
|
+
};
|
|
317
|
+
|
|
318
|
+
const plans = await generateScaffoldFilePlans(spec.flows, spec.messages, undefined, 'src/domain/flows');
|
|
319
|
+
const mutationFile = plans.find(
|
|
320
|
+
(p) =>
|
|
321
|
+
p.outputPath.endsWith('mutation.resolver.ts') && p.contents.includes('export class AddItemsToCartResolver'),
|
|
322
|
+
);
|
|
323
|
+
|
|
324
|
+
expect(mutationFile?.contents).toMatchInlineSnapshot(`
|
|
325
|
+
"import { Mutation, Resolver, Arg, Ctx, Field, InputType } from 'type-graphql';
|
|
326
|
+
import { type GraphQLContext, sendCommand, MutationResponse } from '../../../shared';
|
|
327
|
+
|
|
328
|
+
@InputType()
|
|
329
|
+
export class AddItemsToCartItemsInput {
|
|
330
|
+
@Field(() => String)
|
|
331
|
+
productId!: string;
|
|
332
|
+
|
|
333
|
+
@Field(() => Float)
|
|
334
|
+
quantity!: number;
|
|
335
|
+
}
|
|
336
|
+
|
|
337
|
+
@InputType()
|
|
338
|
+
export class AddItemsToCartInput {
|
|
339
|
+
@Field(() => String)
|
|
340
|
+
sessionId!: string;
|
|
341
|
+
|
|
342
|
+
@Field(() => [AddItemsToCartItemsInput])
|
|
343
|
+
items!: AddItemsToCartItemsInput[];
|
|
344
|
+
}
|
|
345
|
+
|
|
346
|
+
@Resolver()
|
|
347
|
+
export class AddItemsToCartResolver {
|
|
348
|
+
@Mutation(() => MutationResponse)
|
|
349
|
+
async addItemsToCart(
|
|
350
|
+
@Arg('input', () => AddItemsToCartInput) input: AddItemsToCartInput,
|
|
351
|
+
@Ctx() ctx: GraphQLContext,
|
|
352
|
+
): Promise<MutationResponse> {
|
|
353
|
+
return await sendCommand(ctx.messageBus, {
|
|
354
|
+
type: 'AddItemsToCart',
|
|
355
|
+
kind: 'Command',
|
|
356
|
+
data: { ...input },
|
|
357
|
+
});
|
|
358
|
+
}
|
|
359
|
+
}
|
|
360
|
+
"
|
|
361
|
+
`);
|
|
362
|
+
});
|
|
124
363
|
});
|