@azure-net/cli 5.1.1 → 6.0.0-next.2
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/README.md +189 -0
- package/bin/azure-net.js +236 -221
- package/dist/bin/azure-net.d.ts +2 -0
- package/dist/src/checks/architecture.d.ts +20 -0
- package/dist/src/checks/checkDomain.d.ts +1 -0
- package/dist/src/checks/checkFoldersStructure.d.ts +1 -0
- package/dist/src/checks/checkHooks.d.ts +1 -0
- package/dist/src/checks/checkImports.d.ts +1 -0
- package/dist/src/checks/checkInternal.d.ts +1 -0
- package/dist/src/checks/checkLayerBoundaries.d.ts +1 -0
- package/dist/src/checks/checkLayerImports.d.ts +1 -0
- package/dist/src/checks/checkPresenterNames.d.ts +1 -0
- package/dist/src/checks/checkProject.d.ts +1 -0
- package/dist/src/checks/checkProviderGraph.d.ts +1 -0
- package/dist/src/checks/checkProviderNames.d.ts +1 -0
- package/dist/src/generate/layers/generateRepository.d.ts +1 -0
- package/dist/src/generate/layers/generateRepositoryMethod.d.ts +1 -0
- package/dist/src/generate/layers/generateUseCases.d.ts +1 -0
- package/dist/src/generate/module/generateDomain.d.ts +8 -0
- package/dist/src/generate/module/generateModule.d.ts +1 -0
- package/dist/src/generate/module/generateModulePreset.d.ts +1 -0
- package/dist/src/generate/module/generatePresenter.d.ts +29 -0
- package/dist/src/generate/module/generateRepository.d.ts +15 -0
- package/dist/src/generate/module/generateRepositoryMethod.d.ts +2 -0
- package/dist/src/generate/module/generateSchemaFromType.d.ts +9 -0
- package/dist/src/generate/module/generateStore.d.ts +1 -0
- package/dist/src/generate/module/generateTypesJson.d.ts +2 -0
- package/dist/src/generate/module/generateUseCases.d.ts +1 -0
- package/dist/src/generate/module/repositoryModuleShared.d.ts +89 -0
- package/dist/src/generate/routes/generateRoutes.d.ts +14 -0
- package/dist/src/generate/ui/generateComponent.d.ts +1 -0
- package/dist/src/generate/ui/generateDesignComponent.d.ts +1 -0
- package/dist/src/generate/ui/generateWidget.d.ts +1 -0
- package/dist/src/git/commit.d.ts +23 -0
- package/dist/src/git/push.d.ts +11 -0
- package/dist/src/git/runGit.d.ts +2 -0
- package/dist/src/init/initAliases.d.ts +12 -0
- package/dist/src/init/initEdges.d.ts +2 -0
- package/dist/src/init/initStructure.d.ts +1 -0
- package/dist/src/install/configureCommitTools.d.ts +1 -0
- package/dist/src/install/installFresh.d.ts +1 -0
- package/dist/src/migrate/migrate.d.ts +22 -0
- package/dist/src/migrate/presenters.d.ts +7 -0
- package/dist/src/plugins/addLint.d.ts +5 -0
- package/dist/src/scaffolds/createCoreSchema.d.ts +1 -0
- package/dist/src/scaffolds/createDatasource.d.ts +1 -0
- package/dist/src/scaffolds/createProgram.d.ts +1 -0
- package/dist/src/scaffolds/createResponse.d.ts +1 -0
- package/dist/src/scaffolds/createSchemaRule.d.ts +1 -0
- package/dist/src/scaffolds/createTranslationManager.d.ts +1 -0
- package/{src/scaffolds/index.ts → dist/src/scaffolds/index.d.ts} +0 -2
- package/dist/src/scaffolds/registerDatasource.d.ts +2 -0
- package/dist/src/scaffolds/updateDefaultFactoryConfig.d.ts +1 -0
- package/dist/src/utils/architecture.d.ts +31 -0
- package/dist/src/utils/contextUtils.d.ts +6 -0
- package/dist/src/utils/fileUtils.d.ts +5 -0
- package/dist/src/utils/flattenConfig.d.ts +2 -0
- package/dist/src/utils/legacyAliases.d.ts +1 -0
- package/dist/src/utils/loadConfig.d.ts +16 -0
- package/dist/src/utils/packageImports.d.ts +4 -0
- package/dist/src/utils/sharedFoundation.d.ts +20 -0
- package/dist/src/utils/viteConfig.d.ts +9 -0
- package/package.json +48 -36
- package/src/checks/architecture.js +154 -0
- package/src/checks/checkDomain.js +124 -154
- package/src/checks/checkFoldersStructure.js +64 -52
- package/src/checks/checkHooks.js +12 -12
- package/src/checks/checkImports.js +26 -142
- package/src/checks/checkInternal.js +27 -24
- package/src/checks/checkLayerBoundaries.js +22 -197
- package/src/checks/checkLayerImports.js +14 -134
- package/src/checks/checkPresenterNames.js +156 -143
- package/src/checks/checkProject.js +27 -26
- package/src/checks/checkProviderGraph.js +182 -166
- package/src/checks/checkProviderNames.js +123 -112
- package/src/generate/layers/generateRepository.js +1 -109
- package/src/generate/layers/generateRepositoryMethod.js +1 -90
- package/src/generate/layers/generateUseCases.js +1 -44
- package/src/generate/module/generateDomain.js +81 -105
- package/src/generate/module/generateModule.js +34 -68
- package/src/generate/module/generateModulePreset.js +188 -248
- package/src/generate/module/generatePresenter.js +441 -369
- package/src/generate/module/generateRepository.js +102 -121
- package/src/generate/module/generateRepositoryMethod.js +117 -0
- package/src/generate/module/generateSchemaFromType.js +283 -280
- package/src/generate/module/generateStore.js +41 -0
- package/src/generate/module/generateTypesJson.js +196 -195
- package/src/generate/module/generateUseCases.js +47 -55
- package/src/generate/module/repositoryModuleShared.js +480 -459
- package/src/generate/routes/generateRoutes.js +4 -7
- package/src/generate/ui/generateComponent.js +44 -64
- package/src/generate/ui/generateDesignComponent.js +21 -41
- package/src/generate/ui/generateWidget.js +21 -41
- package/src/git/commit.js +67 -0
- package/src/git/push.js +19 -0
- package/src/git/runGit.js +11 -0
- package/src/init/initAliases.js +19 -135
- package/src/init/initEdges.js +79 -54
- package/src/init/initStructure.js +31 -145
- package/src/install/configureCommitTools.js +1 -0
- package/src/install/installFresh.js +39 -68
- package/src/migrate/migrate.js +914 -0
- package/src/migrate/presenters.js +265 -0
- package/src/plugins/addLint.js +52 -219
- package/src/scaffolds/createCoreSchema.js +65 -91
- package/src/scaffolds/createDatasource.js +67 -101
- package/src/scaffolds/createProgram.js +8 -8
- package/src/scaffolds/createResponse.js +29 -29
- package/src/scaffolds/createSchemaRule.js +19 -19
- package/src/scaffolds/createTranslationManager.js +84 -37
- package/src/scaffolds/index.js +0 -2
- package/src/scaffolds/registerDatasource.js +59 -0
- package/src/scaffolds/updateDefaultFactoryConfig.js +31 -0
- package/src/utils/architecture.js +145 -0
- package/src/utils/contextUtils.js +32 -65
- package/src/utils/fileUtils.js +69 -50
- package/src/utils/flattenConfig.js +38 -0
- package/src/utils/legacyAliases.js +75 -0
- package/src/utils/loadConfig.js +76 -40
- package/src/utils/packageImports.js +63 -0
- package/src/utils/sharedFoundation.js +36 -42
- package/src/utils/viteConfig.js +295 -0
- package/.prettierrc +0 -7
- package/bin/azure-net.ts +0 -308
- package/eslint.config.js +0 -34
- package/src/checks/checkDomain.ts +0 -223
- package/src/checks/checkFoldersStructure.ts +0 -85
- package/src/checks/checkHooks.ts +0 -22
- package/src/checks/checkImports.ts +0 -193
- package/src/checks/checkInternal.ts +0 -48
- package/src/checks/checkLayerBoundaries.ts +0 -255
- package/src/checks/checkLayerImports.ts +0 -185
- package/src/checks/checkPresenterNames.ts +0 -203
- package/src/checks/checkProject.ts +0 -45
- package/src/checks/checkProviderGraph.ts +0 -234
- package/src/checks/checkProviderNames.ts +0 -165
- package/src/generate/layers/generateRepository.ts +0 -123
- package/src/generate/layers/generateRepositoryMethod.ts +0 -102
- package/src/generate/layers/generateUseCases.ts +0 -50
- package/src/generate/layers/repositoryShared.js +0 -506
- package/src/generate/layers/repositoryShared.ts +0 -662
- package/src/generate/module/generateDomain.ts +0 -147
- package/src/generate/module/generateModule.ts +0 -84
- package/src/generate/module/generateModulePreset.ts +0 -338
- package/src/generate/module/generatePresenter.ts +0 -498
- package/src/generate/module/generateRepository.ts +0 -158
- package/src/generate/module/generateSchemaFromType.ts +0 -368
- package/src/generate/module/generateTypesJson.ts +0 -259
- package/src/generate/module/generateUseCases.ts +0 -67
- package/src/generate/module/repositoryModuleShared.ts +0 -669
- package/src/generate/routes/generateRoutes.ts +0 -275
- package/src/generate/ui/generateComponent.ts +0 -100
- package/src/generate/ui/generateDesignComponent.ts +0 -71
- package/src/generate/ui/generateWidget.ts +0 -71
- package/src/init/initAliases.ts +0 -172
- package/src/init/initEdges.ts +0 -74
- package/src/init/initStructure.ts +0 -172
- package/src/install/installFresh.ts +0 -93
- package/src/plugins/addLint.ts +0 -274
- package/src/scaffolds/createCoreSchema.ts +0 -130
- package/src/scaffolds/createDatasource.ts +0 -161
- package/src/scaffolds/createDatasourceProvider.js +0 -127
- package/src/scaffolds/createDatasourceProvider.ts +0 -161
- package/src/scaffolds/createPresenterFactory.js +0 -83
- package/src/scaffolds/createPresenterFactory.ts +0 -102
- package/src/scaffolds/createProgram.ts +0 -19
- package/src/scaffolds/createResponse.ts +0 -66
- package/src/scaffolds/createSchemaRule.ts +0 -44
- package/src/scaffolds/createTranslationManager.ts +0 -80
- package/src/utils/contextUtils.ts +0 -88
- package/src/utils/fileUtils.ts +0 -74
- package/src/utils/loadConfig.ts +0 -68
- package/src/utils/sharedFoundation.ts +0 -70
- package/tsconfig.json +0 -19
- /package/{src/checks/index.ts → dist/src/checks/index.d.ts} +0 -0
- /package/{src/plugins/index.ts → dist/src/plugins/index.d.ts} +0 -0
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
import ts from 'typescript';
|
|
2
|
+
/** Flatten literal-only spreads without evaluating user configuration or duplicating effects. */
|
|
3
|
+
export function flattenConfigLiterals(content) {
|
|
4
|
+
const source = ts.createSourceFile('azure-net.config.ts', content, ts.ScriptTarget.Latest, true);
|
|
5
|
+
const exported = source.statements.find(ts.isExportAssignment);
|
|
6
|
+
if (!exported)
|
|
7
|
+
return content;
|
|
8
|
+
const unwrap = (node) => (ts.isParenthesizedExpression(node) ? unwrap(node.expression) : node);
|
|
9
|
+
const root = unwrap(exported.expression);
|
|
10
|
+
if (!ts.isObjectLiteralExpression(root))
|
|
11
|
+
return content;
|
|
12
|
+
let changed = false;
|
|
13
|
+
const flatten = (object) => object.properties.flatMap((property) => {
|
|
14
|
+
if (ts.isSpreadAssignment(property)) {
|
|
15
|
+
const value = unwrap(property.expression);
|
|
16
|
+
if (ts.isObjectLiteralExpression(value) &&
|
|
17
|
+
value.properties.every((p) => !ts.isGetAccessorDeclaration(p) &&
|
|
18
|
+
!ts.isSetAccessorDeclaration(p) &&
|
|
19
|
+
!(p.name && p.name.getText(source).replace(/['"]/g, '') === '__proto__'))) {
|
|
20
|
+
changed = true;
|
|
21
|
+
return flatten(value);
|
|
22
|
+
}
|
|
23
|
+
}
|
|
24
|
+
return [property];
|
|
25
|
+
});
|
|
26
|
+
const properties = flatten(root);
|
|
27
|
+
if (!changed)
|
|
28
|
+
return content;
|
|
29
|
+
const names = properties
|
|
30
|
+
.filter((p) => p.name && !ts.isComputedPropertyName(p.name))
|
|
31
|
+
.map((p) => p.name.getText(source).replace(/['"]/g, ''));
|
|
32
|
+
// Duplicate literal keys can produce invalid TypeScript; retain the original spread semantics.
|
|
33
|
+
if (new Set(names).size !== names.length)
|
|
34
|
+
return content;
|
|
35
|
+
const updated = ts.factory.updateObjectLiteralExpression(root, properties);
|
|
36
|
+
const printed = ts.createPrinter({ newLine: ts.NewLineKind.LineFeed }).printNode(ts.EmitHint.Expression, updated, source);
|
|
37
|
+
return content.slice(0, root.getStart(source)) + printed + content.slice(root.end);
|
|
38
|
+
}
|
|
@@ -0,0 +1,75 @@
|
|
|
1
|
+
import ts from 'typescript';
|
|
2
|
+
export function mergeAliasesInSvelteConfig(content, aliases) {
|
|
3
|
+
const source = ts.createSourceFile('svelte.config.js', content, ts.ScriptTarget.Latest, true, ts.ScriptKind.JS);
|
|
4
|
+
function resolve(expression, seen = new Set()) {
|
|
5
|
+
if (ts.isObjectLiteralExpression(expression))
|
|
6
|
+
return expression;
|
|
7
|
+
if (ts.isParenthesizedExpression(expression) || ts.isAsExpression(expression) || ts.isSatisfiesExpression(expression))
|
|
8
|
+
return resolve(expression.expression, seen);
|
|
9
|
+
if (ts.isIdentifier(expression) && !seen.has(expression.text)) {
|
|
10
|
+
seen.add(expression.text);
|
|
11
|
+
for (const statement of source.statements)
|
|
12
|
+
if (ts.isVariableStatement(statement)) {
|
|
13
|
+
for (const declaration of statement.declarationList.declarations)
|
|
14
|
+
if (ts.isIdentifier(declaration.name) && declaration.name.text === expression.text && declaration.initializer)
|
|
15
|
+
return resolve(declaration.initializer, seen);
|
|
16
|
+
}
|
|
17
|
+
}
|
|
18
|
+
throw new Error('Cannot safely merge Svelte aliases: use an object literal or a local object variable for the config and kit.');
|
|
19
|
+
}
|
|
20
|
+
const exported = source.statements.find(ts.isExportAssignment);
|
|
21
|
+
if (!exported)
|
|
22
|
+
throw new Error('Cannot safely merge Svelte aliases: no default export found.');
|
|
23
|
+
const root = resolve(exported.expression);
|
|
24
|
+
const property = (object, name) => [...object.properties]
|
|
25
|
+
.reverse()
|
|
26
|
+
.find((entry) => entry.name && (ts.isIdentifier(entry.name) || ts.isStringLiteral(entry.name)) && entry.name.text === name);
|
|
27
|
+
const value = (entry) => {
|
|
28
|
+
if (ts.isPropertyAssignment(entry))
|
|
29
|
+
return entry.initializer;
|
|
30
|
+
if (ts.isShorthandPropertyAssignment(entry))
|
|
31
|
+
return entry.name;
|
|
32
|
+
throw new Error('Cannot safely merge Svelte aliases: unsupported property declaration.');
|
|
33
|
+
};
|
|
34
|
+
const insert = (object, text) => {
|
|
35
|
+
const last = object.properties.at(-1);
|
|
36
|
+
const comma = last && !object.properties.hasTrailingComma ? ',' : '';
|
|
37
|
+
// Insert the separator before any trailing line comment.
|
|
38
|
+
let next = content.slice(0, object.end - 1) + `\n${text}\n` + content.slice(object.end - 1);
|
|
39
|
+
if (last && comma)
|
|
40
|
+
next = next.slice(0, last.end) + comma + next.slice(last.end);
|
|
41
|
+
return next;
|
|
42
|
+
};
|
|
43
|
+
const entries = Object.entries(aliases)
|
|
44
|
+
.map(([key, target]) => `${JSON.stringify(key)}: ${JSON.stringify(target)}`)
|
|
45
|
+
.join(',\n');
|
|
46
|
+
const kit = property(root, 'kit');
|
|
47
|
+
if (!kit)
|
|
48
|
+
return insert(root, `kit: { alias: { ${entries} } }`);
|
|
49
|
+
const kitObject = resolve(value(kit));
|
|
50
|
+
const alias = property(kitObject, 'alias');
|
|
51
|
+
if (!alias)
|
|
52
|
+
return insert(kitObject, `alias: { ${entries} }`);
|
|
53
|
+
const expression = value(alias);
|
|
54
|
+
if (ts.isObjectLiteralExpression(expression)) {
|
|
55
|
+
const missing = Object.entries(aliases).filter(([key, target]) => {
|
|
56
|
+
const entry = property(expression, key);
|
|
57
|
+
if (!entry || !ts.isPropertyAssignment(entry) || !ts.isStringLiteral(entry.initializer) || entry.initializer.text !== target)
|
|
58
|
+
return true;
|
|
59
|
+
// Later spreads or computed keys can override an otherwise correct entry.
|
|
60
|
+
return expression.properties
|
|
61
|
+
.slice(expression.properties.indexOf(entry) + 1)
|
|
62
|
+
.some((later) => ts.isSpreadAssignment(later) || (later.name && ts.isComputedPropertyName(later.name)));
|
|
63
|
+
});
|
|
64
|
+
if (!missing.length)
|
|
65
|
+
return content;
|
|
66
|
+
if (missing.every(([key]) => !property(expression, key))) {
|
|
67
|
+
return insert(expression, missing.map(([key, target]) => `${JSON.stringify(key)}: ${JSON.stringify(target)}`).join(',\n'));
|
|
68
|
+
}
|
|
69
|
+
}
|
|
70
|
+
// Preserve every user expression, spread and comment; fixed architecture aliases win.
|
|
71
|
+
const replacement = `{ ...(${expression.getText(source)}), ${entries} }`;
|
|
72
|
+
if (ts.isShorthandPropertyAssignment(alias))
|
|
73
|
+
return content.slice(0, alias.getStart(source)) + `alias: ${replacement}` + content.slice(alias.end);
|
|
74
|
+
return content.slice(0, expression.getStart(source)) + replacement + content.slice(expression.end);
|
|
75
|
+
}
|
package/src/utils/loadConfig.js
CHANGED
|
@@ -1,46 +1,82 @@
|
|
|
1
1
|
import fs from 'node:fs/promises';
|
|
2
2
|
import fsSync from 'node:fs';
|
|
3
3
|
import path from 'node:path';
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
};
|
|
8
|
-
function toObjectFromDefaultExport(content) {
|
|
9
|
-
const source = String(content ?? '').trim();
|
|
10
|
-
if (!source.length) return {};
|
|
11
|
-
const replacedExport = source.replace(/^\s*export\s+default\s+/m, 'return ');
|
|
12
|
-
if (replacedExport === source) return {};
|
|
13
|
-
const withSemicolon = /;\s*$/.test(replacedExport) ? replacedExport : `${replacedExport};`;
|
|
14
|
-
try {
|
|
15
|
-
return new Function(withSemicolon)() ?? {};
|
|
16
|
-
} catch {
|
|
17
|
-
return {};
|
|
18
|
-
}
|
|
19
|
-
}
|
|
4
|
+
import { createRequire } from 'node:module';
|
|
5
|
+
import ts from 'typescript';
|
|
6
|
+
import { flattenConfigLiterals } from './flattenConfig.js';
|
|
20
7
|
export function resolveConfigFile(cwd = process.cwd()) {
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
8
|
+
for (const type of ['ts', 'js']) {
|
|
9
|
+
const filepath = path.join(cwd, `azure-net.config.${type}`);
|
|
10
|
+
if (fsSync.existsSync(filepath))
|
|
11
|
+
return { exists: true, filepath, type };
|
|
12
|
+
}
|
|
13
|
+
return { exists: false, filepath: path.join(cwd, 'azure-net.config.ts'), type: 'ts' };
|
|
14
|
+
}
|
|
15
|
+
export async function loadUserConfig(cwd = process.cwd()) {
|
|
16
|
+
const { exists, filepath } = resolveConfigFile(cwd);
|
|
17
|
+
if (!exists)
|
|
18
|
+
return {};
|
|
19
|
+
try {
|
|
20
|
+
const source = await fs.readFile(filepath, 'utf8');
|
|
21
|
+
const result = ts.transpileModule(source, {
|
|
22
|
+
fileName: filepath,
|
|
23
|
+
reportDiagnostics: true,
|
|
24
|
+
compilerOptions: { target: ts.ScriptTarget.ES2022, module: ts.ModuleKind.CommonJS, esModuleInterop: true }
|
|
25
|
+
});
|
|
26
|
+
const errors = result.diagnostics?.filter((diagnostic) => diagnostic.category === ts.DiagnosticCategory.Error) ?? [];
|
|
27
|
+
if (errors.length)
|
|
28
|
+
throw new Error(errors.map((error) => ts.flattenDiagnosticMessageText(error.messageText, '\n')).join('\n'));
|
|
29
|
+
const module = { exports: {} };
|
|
30
|
+
new Function('module', 'exports', 'require', '__filename', '__dirname', result.outputText)(module, module.exports, createRequire(filepath), filepath, path.dirname(filepath));
|
|
31
|
+
const config = module.exports.default;
|
|
32
|
+
if (!config || typeof config !== 'object' || Array.isArray(config))
|
|
33
|
+
throw new Error('Expected a default-exported configuration object.');
|
|
34
|
+
const parsed = config;
|
|
35
|
+
if (parsed.presentationWorkspaces !== undefined &&
|
|
36
|
+
(!Array.isArray(parsed.presentationWorkspaces) ||
|
|
37
|
+
parsed.presentationWorkspaces.some((name) => typeof name !== 'string' || !/^[A-Za-z][A-Za-z0-9 _-]*$/.test(name.trim()))))
|
|
38
|
+
throw new Error('presentationWorkspaces must be an array of valid workspace names.');
|
|
39
|
+
if (parsed.runChecksBeforePush !== undefined && typeof parsed.runChecksBeforePush !== 'boolean')
|
|
40
|
+
throw new Error('runChecksBeforePush must be a boolean.');
|
|
41
|
+
return parsed;
|
|
42
|
+
}
|
|
43
|
+
catch (error) {
|
|
44
|
+
throw new Error(`Unable to load ${filepath}: ${error instanceof Error ? error.message : String(error)}`, { cause: error });
|
|
45
|
+
}
|
|
30
46
|
}
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
47
|
+
/** Add the default without rewriting or dropping legacy/user configuration. */
|
|
48
|
+
export async function initializeConfigDefaults(cwd = process.cwd()) {
|
|
49
|
+
const existing = resolveConfigFile(cwd);
|
|
50
|
+
if (existing.exists) {
|
|
51
|
+
const original = await fs.readFile(existing.filepath, 'utf8');
|
|
52
|
+
const flattened = flattenConfigLiterals(original);
|
|
53
|
+
if (flattened !== original)
|
|
54
|
+
await fs.writeFile(existing.filepath, flattened);
|
|
55
|
+
}
|
|
56
|
+
const config = await loadUserConfig(cwd);
|
|
57
|
+
if (config.runChecksBeforePush !== undefined)
|
|
58
|
+
return;
|
|
59
|
+
const resolved = resolveConfigFile(cwd);
|
|
60
|
+
if (!resolved.exists) {
|
|
61
|
+
await fs.writeFile(resolved.filepath, 'export default {\n\trunChecksBeforePush: true\n};\n', { flag: 'wx' });
|
|
62
|
+
return;
|
|
63
|
+
}
|
|
64
|
+
const content = await fs.readFile(resolved.filepath, 'utf8');
|
|
65
|
+
const source = ts.createSourceFile(resolved.filepath, content, ts.ScriptTarget.Latest, true);
|
|
66
|
+
const exported = source.statements.find(ts.isExportAssignment);
|
|
67
|
+
if (!exported || exported.isExportEquals)
|
|
68
|
+
throw new Error(`Cannot initialize ${resolved.filepath}: expected a default export.`);
|
|
69
|
+
const expression = exported.expression;
|
|
70
|
+
let nextContent;
|
|
71
|
+
if (ts.isObjectLiteralExpression(expression)) {
|
|
72
|
+
const last = expression.properties.at(-1);
|
|
73
|
+
nextContent = content.slice(0, expression.end - 1) + '\n\trunChecksBeforePush: true\n' + content.slice(expression.end - 1);
|
|
74
|
+
if (last && !expression.properties.hasTrailingComma)
|
|
75
|
+
nextContent = nextContent.slice(0, last.end) + ',' + nextContent.slice(last.end);
|
|
76
|
+
}
|
|
77
|
+
else {
|
|
78
|
+
const replacement = `{ ...(${expression.getText(source)}), runChecksBeforePush: true }`;
|
|
79
|
+
nextContent = content.slice(0, expression.getStart(source)) + replacement + content.slice(expression.end);
|
|
80
|
+
}
|
|
81
|
+
await fs.writeFile(resolved.filepath, nextContent, 'utf8');
|
|
46
82
|
}
|
|
@@ -0,0 +1,63 @@
|
|
|
1
|
+
import fs from 'node:fs/promises';
|
|
2
|
+
import path from 'node:path';
|
|
3
|
+
import { format } from 'prettier';
|
|
4
|
+
export const PACKAGE_IMPORTS = Object.fromEntries(['Contexts', 'Presentation', 'Platform'].flatMap((name) => {
|
|
5
|
+
const key = '#' + name.toLowerCase(), root = './src/app/' + name;
|
|
6
|
+
return [
|
|
7
|
+
[key, root + '/index.ts'],
|
|
8
|
+
[key + '/*', { types: [root + '/*.ts', root + '/*/index.ts', root + '/*'], default: root + '/*' }]
|
|
9
|
+
];
|
|
10
|
+
}));
|
|
11
|
+
export async function mergePackageImports(content) {
|
|
12
|
+
const json = JSON.parse(content);
|
|
13
|
+
if (!json || typeof json !== 'object' || Array.isArray(json))
|
|
14
|
+
throw new Error('Expected a package.json object');
|
|
15
|
+
if (json.imports !== undefined && (!json.imports || typeof json.imports !== 'object' || Array.isArray(json.imports)))
|
|
16
|
+
throw new Error('Expected package.json imports object');
|
|
17
|
+
const imports = { ...json.imports };
|
|
18
|
+
for (const [key, value] of Object.entries(PACKAGE_IMPORTS)) {
|
|
19
|
+
if (key in imports && JSON.stringify(imports[key]) !== JSON.stringify(value))
|
|
20
|
+
throw new Error(`Conflicting package import ${key}; review its target before initialization.`);
|
|
21
|
+
imports[key] = value;
|
|
22
|
+
}
|
|
23
|
+
return format(JSON.stringify({ ...json, imports }), { parser: 'json', useTabs: true });
|
|
24
|
+
}
|
|
25
|
+
export async function initializePackageImports() {
|
|
26
|
+
const file = path.resolve('package.json');
|
|
27
|
+
let content;
|
|
28
|
+
try {
|
|
29
|
+
content = await fs.readFile(file, 'utf8');
|
|
30
|
+
}
|
|
31
|
+
catch (error) {
|
|
32
|
+
if (error.code !== 'ENOENT')
|
|
33
|
+
throw error;
|
|
34
|
+
content = '{}';
|
|
35
|
+
}
|
|
36
|
+
await fs.writeFile(file, await mergePackageImports(content));
|
|
37
|
+
}
|
|
38
|
+
export function resolvePackageImport(imports, specifier, root) {
|
|
39
|
+
const target = (v) => {
|
|
40
|
+
if (typeof v === 'string')
|
|
41
|
+
return v;
|
|
42
|
+
if (Array.isArray(v))
|
|
43
|
+
return v.map(target).find(Boolean);
|
|
44
|
+
if (v && typeof v === 'object') {
|
|
45
|
+
const obj = v;
|
|
46
|
+
return target(obj.default ?? obj.import ?? obj.types);
|
|
47
|
+
}
|
|
48
|
+
};
|
|
49
|
+
for (const key of Object.keys(imports).sort((a, b) => b.replace('*', '').length - a.replace('*', '').length)) {
|
|
50
|
+
const value = target(imports[key]);
|
|
51
|
+
if (!value?.startsWith('./'))
|
|
52
|
+
continue;
|
|
53
|
+
if (!key.includes('*')) {
|
|
54
|
+
if (key === specifier)
|
|
55
|
+
return path.resolve(root, value);
|
|
56
|
+
continue;
|
|
57
|
+
}
|
|
58
|
+
const [prefix, suffix = ''] = key.split('*');
|
|
59
|
+
if (specifier.startsWith(prefix) && specifier.endsWith(suffix))
|
|
60
|
+
return path.resolve(root, value.replace('*', specifier.slice(prefix.length, suffix ? -suffix.length : undefined)));
|
|
61
|
+
}
|
|
62
|
+
return null;
|
|
63
|
+
}
|
|
@@ -1,48 +1,42 @@
|
|
|
1
1
|
import path from 'node:path';
|
|
2
|
-
import {
|
|
3
|
-
import {
|
|
4
|
-
export const SHARED_ESSENTIALS_DIR_NAME = '
|
|
5
|
-
const
|
|
6
|
-
|
|
7
|
-
|
|
2
|
+
import { discoverContexts, getContextPath, getPlatformPath, SHARED_CONTEXT } from './architecture.js';
|
|
3
|
+
import { resolveConfigFile } from './loadConfig.js';
|
|
4
|
+
export const SHARED_ESSENTIALS_DIR_NAME = 'Platform';
|
|
5
|
+
const constructNames = {
|
|
6
|
+
datasource: 'Datasource',
|
|
7
|
+
presenter: 'Presenter',
|
|
8
|
+
provider: 'DI',
|
|
9
|
+
response: 'Response',
|
|
10
|
+
schema: 'Schema'
|
|
8
11
|
};
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
throw new Error(
|
|
22
|
-
`sharedAlias "${sharedAlias}" does not point to any configured context. Add a context with alias "${sharedAlias}" in azure-net.config.ts/js.`
|
|
23
|
-
);
|
|
24
|
-
}
|
|
25
|
-
return {
|
|
26
|
-
contexts,
|
|
27
|
-
sharedAlias,
|
|
28
|
-
sharedContext
|
|
29
|
-
};
|
|
12
|
+
export async function getSharedState() {
|
|
13
|
+
const names = await discoverContexts();
|
|
14
|
+
if (!names.includes(SHARED_CONTEXT))
|
|
15
|
+
names.push(SHARED_CONTEXT);
|
|
16
|
+
const contexts = names.sort().map((name) => ({ name, alias: `#contexts/${name}` }));
|
|
17
|
+
return { contexts, sharedAlias: '#platform', sharedContext: contexts.find((context) => context.name === SHARED_CONTEXT) };
|
|
18
|
+
}
|
|
19
|
+
export const hasSharedAliasConfig = async () => true;
|
|
20
|
+
export const getSharedContextRootPath = (name = SHARED_CONTEXT) => getContextPath(name);
|
|
21
|
+
export const getSharedEssentialsPath = (...compatibility) => {
|
|
22
|
+
void compatibility;
|
|
23
|
+
return getPlatformPath();
|
|
30
24
|
};
|
|
31
|
-
export const
|
|
32
|
-
|
|
33
|
-
|
|
25
|
+
export const getFoundationRootPath = (...compatibility) => {
|
|
26
|
+
void compatibility;
|
|
27
|
+
return path.join(getPlatformPath(), 'Foundation');
|
|
28
|
+
};
|
|
29
|
+
export const getFoundationConstructPath = (name, construct) => path.join(getFoundationRootPath(name), constructNames[construct]);
|
|
30
|
+
export const getFoundationConstructImportPath = (_alias, construct) => `#platform/Foundation/${constructNames[construct]}`;
|
|
31
|
+
export const getLocalizationPath = (...compatibility) => {
|
|
32
|
+
void compatibility;
|
|
33
|
+
return path.join(getPlatformPath(), 'Bootstrap', 'Localization');
|
|
34
|
+
};
|
|
35
|
+
export const getLocalizationImportPath = (...compatibility) => {
|
|
36
|
+
void compatibility;
|
|
37
|
+
return '#platform/Bootstrap/Localization';
|
|
34
38
|
};
|
|
35
|
-
export const getSharedContextRootPath = (sharedContextName) => path.join(process.cwd(), 'src', 'app', sharedContextName);
|
|
36
|
-
export const getSharedEssentialsPath = (sharedContextName) =>
|
|
37
|
-
path.join(getSharedContextRootPath(sharedContextName), SHARED_ESSENTIALS_DIR_NAME);
|
|
38
|
-
export const getFoundationRootPath = (sharedContextName) =>
|
|
39
|
-
path.join(getSharedEssentialsPath(sharedContextName), 'foundation', 'constructs');
|
|
40
|
-
export const getFoundationConstructPath = (sharedContextName, construct) => path.join(getFoundationRootPath(sharedContextName), construct);
|
|
41
|
-
export const getFoundationConstructImportPath = (sharedAlias, construct) =>
|
|
42
|
-
`${sharedAlias}/${SHARED_ESSENTIALS_DIR_NAME}/foundation/constructs/${construct}`;
|
|
43
|
-
export const getLocalizationPath = (sharedContextName) => path.join(getSharedEssentialsPath(sharedContextName), 'localization');
|
|
44
|
-
export const getLocalizationImportPath = (sharedAlias) => `${sharedAlias}/${SHARED_ESSENTIALS_DIR_NAME}/localization`;
|
|
45
39
|
export const getConfigFileLabel = () => {
|
|
46
|
-
|
|
47
|
-
|
|
40
|
+
const config = resolveConfigFile();
|
|
41
|
+
return config.exists ? path.basename(config.filepath) : 'azure-net.config.ts/js';
|
|
48
42
|
};
|