@flarum/cli 1.0.0 → 2.0.0-beta.1
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 +2 -2
- package/bin/run +5 -3
- package/boilerplate/skeleton/extension/.gitattributes +16 -3
- package/boilerplate/skeleton/extension/.github/workflows/backend.yml +15 -0
- package/boilerplate/skeleton/extension/.github/workflows/frontend.yml +20 -0
- package/boilerplate/skeleton/extension/.styleci.yml +14 -0
- package/boilerplate/skeleton/extension/LICENSE.md +1 -0
- package/boilerplate/skeleton/extension/README.md +7 -7
- package/boilerplate/skeleton/extension/composer.json +11 -9
- package/boilerplate/skeleton/extension/extend.php +10 -10
- package/boilerplate/skeleton/extension/js/admin.js +2 -1
- package/boilerplate/skeleton/extension/js/forum.js +2 -1
- package/boilerplate/skeleton/extension/js/package.json +13 -9
- package/boilerplate/skeleton/extension/js/src/admin/index.js +4 -2
- package/boilerplate/skeleton/extension/js/src/common/index.js +5 -0
- package/boilerplate/skeleton/extension/js/src/forum/index.js +4 -2
- package/boilerplate/skeleton/extension/js/tsconfig.json +6 -1
- package/boilerplate/skeleton/extension/locale/en.yml +1 -1
- package/boilerplate/stubs/migration.php +1 -1
- package/lib/base-command.d.ts +27 -6
- package/lib/base-command.js +131 -41
- package/lib/boilersmith/exposed-param-manager.d.ts +8 -0
- package/lib/boilersmith/exposed-param-manager.js +31 -0
- package/lib/boilersmith/io.d.ts +50 -0
- package/lib/boilersmith/io.js +72 -0
- package/lib/boilersmith/paths.d.ts +22 -0
- package/lib/boilersmith/paths.js +29 -0
- package/lib/boilersmith/scaffolding/audit-step-factory.d.ts +5 -0
- package/lib/boilersmith/scaffolding/audit-step-factory.js +54 -0
- package/lib/boilersmith/scaffolding/infra-step-factory.d.ts +5 -0
- package/lib/boilersmith/scaffolding/infra-step-factory.js +34 -0
- package/lib/boilersmith/scaffolding/init-step-factory.d.ts +5 -0
- package/lib/boilersmith/scaffolding/init-step-factory.js +34 -0
- package/lib/boilersmith/scaffolding/module.d.ts +68 -0
- package/lib/boilersmith/scaffolding/module.js +111 -0
- package/lib/boilersmith/scaffolding/scaffolder.d.ts +32 -0
- package/lib/boilersmith/scaffolding/scaffolder.js +203 -0
- package/lib/boilersmith/scaffolding/template-param.d.ts +23 -0
- package/lib/boilersmith/scaffolding/template-param.js +46 -0
- package/lib/boilersmith/step-manager.d.ts +85 -0
- package/lib/boilersmith/step-manager.js +234 -0
- package/lib/boilersmith/steps/stub-base.d.ts +53 -0
- package/lib/boilersmith/steps/stub-base.js +54 -0
- package/lib/{utils → boilersmith/utils}/clone-and-fill.d.ts +0 -0
- package/lib/{utils → boilersmith/utils}/clone-and-fill.js +2 -2
- package/lib/boilersmith/utils/cond-format.d.ts +1 -0
- package/lib/boilersmith/utils/cond-format.js +8 -0
- package/lib/boilersmith/utils/json-leaf-paths.d.ts +7 -0
- package/lib/boilersmith/utils/json-leaf-paths.js +17 -0
- package/lib/boilersmith/utils/read-tpl.d.ts +2 -0
- package/lib/boilersmith/utils/read-tpl.js +10 -0
- package/lib/boilersmith/utils/rename-keys.d.ts +1 -0
- package/lib/boilersmith/utils/rename-keys.js +7 -0
- package/lib/commands/audit/infra.d.ts +16 -0
- package/lib/commands/audit/infra.js +27 -0
- package/lib/commands/infra.d.ts +20 -0
- package/lib/commands/infra.js +55 -0
- package/lib/commands/init.d.ts +4 -3
- package/lib/commands/init.js +8 -6
- package/lib/commands/make/backend/api-controller.d.ts +4 -3
- package/lib/commands/make/backend/api-controller.js +3 -2
- package/lib/commands/make/backend/api-serializer-attributes.d.ts +4 -3
- package/lib/commands/make/backend/api-serializer-attributes.js +1 -1
- package/lib/commands/make/backend/api-serializer.d.ts +4 -3
- package/lib/commands/make/backend/api-serializer.js +3 -2
- package/lib/commands/make/backend/command.d.ts +4 -3
- package/lib/commands/make/backend/command.js +3 -2
- package/lib/commands/make/backend/event-listener.d.ts +4 -3
- package/lib/commands/make/backend/event-listener.js +3 -2
- package/lib/commands/make/backend/handler.d.ts +4 -3
- package/lib/commands/make/backend/handler.js +4 -3
- package/lib/commands/make/backend/integration-test.d.ts +4 -3
- package/lib/commands/make/backend/integration-test.js +3 -2
- package/lib/commands/make/backend/job.d.ts +4 -3
- package/lib/commands/make/backend/job.js +3 -2
- package/lib/commands/make/backend/migration.d.ts +4 -3
- package/lib/commands/make/backend/migration.js +3 -2
- package/lib/commands/make/backend/model.d.ts +4 -3
- package/lib/commands/make/backend/model.js +22 -21
- package/lib/commands/make/backend/policy.d.ts +4 -3
- package/lib/commands/make/backend/policy.js +3 -2
- package/lib/commands/make/backend/repository.d.ts +4 -3
- package/lib/commands/make/backend/repository.js +3 -2
- package/lib/commands/make/backend/route.d.ts +4 -3
- package/lib/commands/make/backend/route.js +1 -1
- package/lib/commands/make/backend/service-provider.d.ts +4 -3
- package/lib/commands/make/backend/service-provider.js +3 -2
- package/lib/commands/make/backend/validator.d.ts +4 -3
- package/lib/commands/make/backend/validator.js +3 -2
- package/lib/commands/make/frontend/component.d.ts +4 -3
- package/lib/commands/make/frontend/component.js +3 -2
- package/lib/commands/make/frontend/modal.d.ts +4 -3
- package/lib/commands/make/frontend/modal.js +3 -2
- package/lib/commands/make/frontend/model.d.ts +4 -3
- package/lib/commands/make/frontend/model.js +3 -2
- package/lib/commands/update/js-imports.d.ts +4 -3
- package/lib/commands/update/js-imports.js +1 -1
- package/lib/help.d.ts +5 -6
- package/lib/help.js +5 -4
- package/lib/index.d.ts +1 -1
- package/lib/index.js +3 -2
- package/lib/providers/index.d.ts +5 -0
- package/lib/providers/index.js +2 -0
- package/lib/{provider → providers}/php-provider.d.ts +0 -0
- package/lib/{provider → providers}/php-provider.js +2 -2
- package/lib/steps/extenders/api-serializer.js +2 -3
- package/lib/steps/extenders/base.d.ts +10 -10
- package/lib/steps/extenders/base.js +11 -11
- package/lib/steps/extenders/console-command.js +2 -3
- package/lib/steps/extenders/event.js +2 -3
- package/lib/steps/extenders/policy.js +2 -3
- package/lib/steps/extenders/route.js +2 -3
- package/lib/steps/extenders/service-provider.js +2 -3
- package/lib/steps/gen-ext-scaffolder.d.ts +6 -0
- package/lib/steps/gen-ext-scaffolder.js +508 -0
- package/lib/steps/js/base.d.ts +9 -9
- package/lib/steps/js/base.js +11 -11
- package/lib/steps/js/model.d.ts +5 -5
- package/lib/steps/js/model.js +8 -13
- package/lib/steps/misc/composer.d.ts +5 -6
- package/lib/steps/misc/composer.js +3 -3
- package/lib/steps/misc/git.d.ts +11 -0
- package/lib/steps/misc/git.js +20 -0
- package/lib/steps/misc/yarn.d.ts +5 -6
- package/lib/steps/misc/yarn.js +3 -3
- package/lib/steps/stubs/backend/api-controller.d.ts +1 -8
- package/lib/steps/stubs/backend/api-controller.js +2 -3
- package/lib/steps/stubs/backend/api-serializer.d.ts +4 -9
- package/lib/steps/stubs/backend/api-serializer.js +4 -4
- package/lib/steps/stubs/backend/command.d.ts +0 -5
- package/lib/steps/stubs/backend/command.js +1 -1
- package/lib/steps/stubs/backend/event-listener.d.ts +0 -5
- package/lib/steps/stubs/backend/event-listener.js +1 -1
- package/lib/steps/stubs/backend/handler-command.js +1 -1
- package/lib/steps/stubs/backend/handler.js +1 -1
- package/lib/steps/stubs/backend/migration.d.ts +4 -5
- package/lib/steps/stubs/backend/migration.js +8 -8
- package/lib/steps/stubs/backend/model.d.ts +4 -4
- package/lib/steps/stubs/backend/model.js +4 -4
- package/lib/steps/stubs/backend/policy.d.ts +0 -5
- package/lib/steps/stubs/backend/policy.js +1 -1
- package/lib/steps/stubs/backend/repository.d.ts +0 -5
- package/lib/steps/stubs/backend/repository.js +1 -1
- package/lib/steps/stubs/flarum-base.d.ts +9 -0
- package/lib/steps/stubs/flarum-base.js +10 -0
- package/lib/steps/stubs/frontend/component.js +0 -1
- package/lib/steps/stubs/frontend/modal.js +0 -1
- package/lib/steps/stubs/frontend/model.d.ts +4 -4
- package/lib/steps/stubs/frontend/model.js +3 -3
- package/lib/steps/stubs/js-base.d.ts +6 -7
- package/lib/steps/stubs/js-base.js +11 -16
- package/lib/steps/stubs/php-base.d.ts +7 -8
- package/lib/steps/stubs/php-base.js +12 -20
- package/lib/steps/update/js-imports.d.ts +5 -6
- package/lib/steps/update/js-imports.js +13 -17
- package/lib/utils/composer.d.ts +64 -0
- package/lib/utils/composer.js +8 -0
- package/lib/utils/migration.js +3 -3
- package/lib/utils/model-name.js +6 -6
- package/lib/utils/validation.d.ts +10 -7
- package/lib/utils/validation.js +9 -6
- package/oclif.manifest.json +1 -1
- package/package.json +53 -31
- package/php-subsystem/src/NodeVisitors/AddExtender.php +2 -1
- package/boilerplate/skeleton/extension/.github/workflows/build.yml +0 -32
- package/boilerplate/skeleton/extension/.github/workflows/lint.yml +0 -32
- package/boilerplate/skeleton/extension/.github/workflows/test.yml +0 -78
- package/lib/commands/infra/backend-testing.d.ts +0 -14
- package/lib/commands/infra/backend-testing.js +0 -26
- package/lib/provider/param-provider.d.ts +0 -15
- package/lib/provider/param-provider.js +0 -39
- package/lib/provider/path-provider.d.ts +0 -19
- package/lib/provider/path-provider.js +0 -24
- package/lib/steps/infra/backend-testing.d.ts +0 -8
- package/lib/steps/infra/backend-testing.js +0 -22
- package/lib/steps/infra/base.d.ts +0 -20
- package/lib/steps/infra/base.js +0 -36
- package/lib/steps/init/extension-skeleton.d.ts +0 -12
- package/lib/steps/init/extension-skeleton.js +0 -142
- package/lib/steps/step-manager.d.ts +0 -71
- package/lib/steps/step-manager.js +0 -173
- package/lib/steps/stubs/base.d.ts +0 -49
- package/lib/steps/stubs/base.js +0 -58
- package/lib/utils/extension-metadata.d.ts +0 -2
- package/lib/utils/extension-metadata.js +0 -21
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
export declare class ExposedParamManager {
|
|
2
|
+
protected stepsRan: Set<string>;
|
|
3
|
+
protected exposedParams: Map<string, unknown>;
|
|
4
|
+
stepRan(stepName: string, packagePath?: string): boolean;
|
|
5
|
+
has(stepName: string, paramName: string, packagePath?: string): boolean;
|
|
6
|
+
get<T = unknown>(stepName: string, paramName: string, packagePath?: string): T;
|
|
7
|
+
add(stepName: string, params: Record<string, unknown>, packagePath?: string): void;
|
|
8
|
+
}
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.ExposedParamManager = void 0;
|
|
4
|
+
function ranKey(stepName, packagePath = '') {
|
|
5
|
+
return JSON.stringify([stepName, packagePath]);
|
|
6
|
+
}
|
|
7
|
+
function paramKey(stepName, paramName, packagePath = '') {
|
|
8
|
+
return JSON.stringify([stepName, paramName, packagePath]);
|
|
9
|
+
}
|
|
10
|
+
class ExposedParamManager {
|
|
11
|
+
constructor() {
|
|
12
|
+
this.stepsRan = new Set();
|
|
13
|
+
this.exposedParams = new Map();
|
|
14
|
+
}
|
|
15
|
+
stepRan(stepName, packagePath) {
|
|
16
|
+
return this.stepsRan.has(ranKey(stepName, packagePath));
|
|
17
|
+
}
|
|
18
|
+
has(stepName, paramName, packagePath) {
|
|
19
|
+
return this.exposedParams.has(paramKey(stepName, paramName, packagePath));
|
|
20
|
+
}
|
|
21
|
+
get(stepName, paramName, packagePath) {
|
|
22
|
+
return this.exposedParams.get(paramKey(stepName, paramName, packagePath));
|
|
23
|
+
}
|
|
24
|
+
add(stepName, params, packagePath) {
|
|
25
|
+
this.stepsRan.add(ranKey(stepName, packagePath));
|
|
26
|
+
Object.entries(params).forEach(([paramName, value]) => {
|
|
27
|
+
this.exposedParams.set(paramKey(stepName, paramName, packagePath), value);
|
|
28
|
+
});
|
|
29
|
+
}
|
|
30
|
+
}
|
|
31
|
+
exports.ExposedParamManager = ExposedParamManager;
|
|
@@ -0,0 +1,50 @@
|
|
|
1
|
+
import { Options, PromptObject } from 'prompts';
|
|
2
|
+
export declare type ParamDef<N extends string = string> = Omit<PromptObject<N>, 'name'> & {
|
|
3
|
+
name: N;
|
|
4
|
+
};
|
|
5
|
+
export declare type Message = {
|
|
6
|
+
type: 'info' | 'warning' | 'error';
|
|
7
|
+
message: string;
|
|
8
|
+
};
|
|
9
|
+
export interface IO {
|
|
10
|
+
supportsAnsiColor: boolean;
|
|
11
|
+
/**
|
|
12
|
+
* Prompt the user for some input data.
|
|
13
|
+
*/
|
|
14
|
+
getParam<T>(param: ParamDef): Promise<T>;
|
|
15
|
+
/**
|
|
16
|
+
* Check if some data has already been prompted for.
|
|
17
|
+
*/
|
|
18
|
+
hasCached(name: string): boolean;
|
|
19
|
+
/**
|
|
20
|
+
* Get all cached params.
|
|
21
|
+
*/
|
|
22
|
+
cached(): Record<string, unknown>;
|
|
23
|
+
info(message: string, immediate: boolean): void;
|
|
24
|
+
warning(message: string, immediate: boolean): void;
|
|
25
|
+
error(message: string, immediate: boolean): void;
|
|
26
|
+
/**
|
|
27
|
+
* Get all messages that have been logged non-immediately.
|
|
28
|
+
*/
|
|
29
|
+
getOutput(): Message[];
|
|
30
|
+
newInstance(cache: Record<string, unknown>, messages: Message[]): IO;
|
|
31
|
+
}
|
|
32
|
+
export declare const PROMPTS_OPTIONS: Options;
|
|
33
|
+
export declare class PromptsIO implements IO {
|
|
34
|
+
supportsAnsiColor: boolean;
|
|
35
|
+
private cache;
|
|
36
|
+
private messages;
|
|
37
|
+
constructor(initial?: Record<string, unknown>, messages?: Message[]);
|
|
38
|
+
getParam<T>(paramDef: ParamDef): Promise<T>;
|
|
39
|
+
hasCached(name: string): boolean;
|
|
40
|
+
/**
|
|
41
|
+
* @internal
|
|
42
|
+
*/
|
|
43
|
+
cached(): Record<string, unknown>;
|
|
44
|
+
info(message: string, immediate: boolean): void;
|
|
45
|
+
warning(message: string, immediate: boolean): void;
|
|
46
|
+
error(message: string, immediate: false): void;
|
|
47
|
+
error(message: string, immediate: true): void;
|
|
48
|
+
getOutput(): Message[];
|
|
49
|
+
newInstance(cache: Record<string, unknown>, messages: Message[]): PromptsIO;
|
|
50
|
+
}
|
|
@@ -0,0 +1,72 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.PromptsIO = exports.PROMPTS_OPTIONS = void 0;
|
|
4
|
+
const tslib_1 = require("tslib");
|
|
5
|
+
const prompts_1 = (0, tslib_1.__importDefault)(require("prompts"));
|
|
6
|
+
const errors_1 = require("@oclif/errors");
|
|
7
|
+
const chalk_1 = (0, tslib_1.__importDefault)(require("chalk"));
|
|
8
|
+
exports.PROMPTS_OPTIONS = { onCancel: () => (0, errors_1.exit)() };
|
|
9
|
+
class PromptsIO {
|
|
10
|
+
constructor(initial = {}, messages = []) {
|
|
11
|
+
this.supportsAnsiColor = true;
|
|
12
|
+
this.cache = new Map();
|
|
13
|
+
this.messages = [];
|
|
14
|
+
this.cache = new Map(Object.entries(initial));
|
|
15
|
+
this.messages = messages;
|
|
16
|
+
}
|
|
17
|
+
async getParam(paramDef) {
|
|
18
|
+
const paramName = paramDef.name;
|
|
19
|
+
if (this.cache.has(paramName)) {
|
|
20
|
+
return this.cache.get(paramName);
|
|
21
|
+
}
|
|
22
|
+
const res = (await (0, prompts_1.default)(paramDef, exports.PROMPTS_OPTIONS));
|
|
23
|
+
const resValue = res[paramName];
|
|
24
|
+
this.cache.set(paramName, resValue);
|
|
25
|
+
return resValue;
|
|
26
|
+
}
|
|
27
|
+
hasCached(name) {
|
|
28
|
+
return this.cache.has(name);
|
|
29
|
+
}
|
|
30
|
+
/**
|
|
31
|
+
* @internal
|
|
32
|
+
*/
|
|
33
|
+
cached() {
|
|
34
|
+
return [...this.cache].reduce((obj, [key, value]) => {
|
|
35
|
+
obj[key] = value;
|
|
36
|
+
return obj;
|
|
37
|
+
}, {});
|
|
38
|
+
}
|
|
39
|
+
info(message, immediate) {
|
|
40
|
+
if (immediate) {
|
|
41
|
+
console.log(message);
|
|
42
|
+
}
|
|
43
|
+
else {
|
|
44
|
+
this.messages.push({ type: 'info', message });
|
|
45
|
+
}
|
|
46
|
+
}
|
|
47
|
+
warning(message, immediate) {
|
|
48
|
+
const formatted = `${chalk_1.default.yellow('Warning:')} ${message}`;
|
|
49
|
+
if (immediate) {
|
|
50
|
+
console.log(formatted);
|
|
51
|
+
}
|
|
52
|
+
else {
|
|
53
|
+
this.messages.push({ type: 'warning', message: formatted });
|
|
54
|
+
}
|
|
55
|
+
}
|
|
56
|
+
error(message, immediate) {
|
|
57
|
+
const formatted = `${chalk_1.default.red('Error:')} ${message}`;
|
|
58
|
+
if (immediate) {
|
|
59
|
+
throw new Error(message);
|
|
60
|
+
}
|
|
61
|
+
else {
|
|
62
|
+
this.messages.push({ type: 'error', message: formatted });
|
|
63
|
+
}
|
|
64
|
+
}
|
|
65
|
+
getOutput() {
|
|
66
|
+
return this.messages;
|
|
67
|
+
}
|
|
68
|
+
newInstance(cache, messages) {
|
|
69
|
+
return new PromptsIO(cache, messages);
|
|
70
|
+
}
|
|
71
|
+
}
|
|
72
|
+
exports.PromptsIO = PromptsIO;
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
export interface Paths {
|
|
2
|
+
cwd(...path: string[]): string;
|
|
3
|
+
package(...path: string[]): string;
|
|
4
|
+
requestedDir(...path: string[]): string | null;
|
|
5
|
+
monorepo(...path: string[]): string | null;
|
|
6
|
+
onMonorepoSub(packagePath: string): Paths;
|
|
7
|
+
}
|
|
8
|
+
declare type InternalPaths = {
|
|
9
|
+
package: string;
|
|
10
|
+
monorepo?: string | null;
|
|
11
|
+
requestedDir?: string | null;
|
|
12
|
+
};
|
|
13
|
+
export declare class NodePaths implements Paths {
|
|
14
|
+
protected paths: InternalPaths;
|
|
15
|
+
constructor(paths: InternalPaths);
|
|
16
|
+
cwd(...path: string[]): string;
|
|
17
|
+
package(...path: string[]): string;
|
|
18
|
+
requestedDir(...path: string[]): string | null;
|
|
19
|
+
monorepo(...path: string[]): string | null;
|
|
20
|
+
onMonorepoSub(packagePath: string): NodePaths;
|
|
21
|
+
}
|
|
22
|
+
export {};
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.NodePaths = void 0;
|
|
4
|
+
const node_path_1 = require("node:path");
|
|
5
|
+
class NodePaths {
|
|
6
|
+
constructor(paths) {
|
|
7
|
+
this.paths = paths;
|
|
8
|
+
}
|
|
9
|
+
cwd(...path) {
|
|
10
|
+
return (0, node_path_1.resolve)(process.cwd(), ...path);
|
|
11
|
+
}
|
|
12
|
+
package(...path) {
|
|
13
|
+
return (0, node_path_1.resolve)(this.paths.package, ...path);
|
|
14
|
+
}
|
|
15
|
+
requestedDir(...path) {
|
|
16
|
+
if (!this.paths.requestedDir)
|
|
17
|
+
return null;
|
|
18
|
+
return (0, node_path_1.resolve)(this.paths.requestedDir, ...path);
|
|
19
|
+
}
|
|
20
|
+
monorepo(...path) {
|
|
21
|
+
if (!this.paths.monorepo)
|
|
22
|
+
return null;
|
|
23
|
+
return (0, node_path_1.resolve)(this.paths.monorepo, ...path);
|
|
24
|
+
}
|
|
25
|
+
onMonorepoSub(packagePath) {
|
|
26
|
+
return new NodePaths(Object.assign(Object.assign({}, this.paths), { monorepo: this.paths.package, package: packagePath }));
|
|
27
|
+
}
|
|
28
|
+
}
|
|
29
|
+
exports.NodePaths = NodePaths;
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
import { DefaultProviders, Step } from '../step-manager';
|
|
2
|
+
import { Module, ModuleStatusCache } from './module';
|
|
3
|
+
import { TemplateParam } from './template-param';
|
|
4
|
+
import { ExcludeScaffoldingFunc } from './scaffolder';
|
|
5
|
+
export declare function auditStepFactory<MN extends string, Providers extends DefaultProviders>(dry: boolean, scaffoldDir: string, modules: Module<MN>[], templateParams: TemplateParam[], excludeScaffoldingFunc?: ExcludeScaffoldingFunc, moduleStatusCache?: ModuleStatusCache<MN>): Step<Providers>;
|
|
@@ -0,0 +1,54 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.auditStepFactory = void 0;
|
|
4
|
+
const tslib_1 = require("tslib");
|
|
5
|
+
const mem_fs_1 = require("mem-fs");
|
|
6
|
+
const rename_keys_1 = require("../utils/rename-keys");
|
|
7
|
+
const module_1 = require("./module");
|
|
8
|
+
const template_param_1 = require("./template-param");
|
|
9
|
+
const cond_format_1 = require("boilersmith/utils/cond-format");
|
|
10
|
+
const chalk_1 = (0, tslib_1.__importDefault)(require("chalk"));
|
|
11
|
+
const node_fs_1 = require("node:fs");
|
|
12
|
+
function auditStepFactory(dry, scaffoldDir, modules, templateParams, excludeScaffoldingFunc, moduleStatusCache) {
|
|
13
|
+
let modulesEnabled;
|
|
14
|
+
return {
|
|
15
|
+
type: 'Audit for outdated infrastructure files or config.',
|
|
16
|
+
composable: true,
|
|
17
|
+
async run(_fs, paths, io, _providers) {
|
|
18
|
+
const paramVals = await (0, template_param_1.currParamValues)(templateParams, _fs, paths, io);
|
|
19
|
+
modulesEnabled = await (0, module_1.currModulesEnabled)(modules, _fs, paths, moduleStatusCache);
|
|
20
|
+
const actionableModules = modules.filter(m => m.updatable && modulesEnabled[m.name] && (!m.togglable || !m.dependsOn.some(dep => !modulesEnabled[dep])));
|
|
21
|
+
io.info((0, cond_format_1.condFormat)(io.supportsAnsiColor, m => chalk_1.default.yellow(chalk_1.default.bold(chalk_1.default.underline(m))), `Auditing infrastructure for ${actionableModules.length} enabled modules:`), true);
|
|
22
|
+
for (const m of modules) {
|
|
23
|
+
if (actionableModules.includes(m)) {
|
|
24
|
+
io.info((0, cond_format_1.condFormat)(io.supportsAnsiColor, m => chalk_1.default.dim(chalk_1.default.green(m)), `✓ ${m.name}: ${m.shortDescription}`), true);
|
|
25
|
+
}
|
|
26
|
+
else if (m.updatable) {
|
|
27
|
+
io.info((0, cond_format_1.condFormat)(io.supportsAnsiColor, m => chalk_1.default.dim(chalk_1.default.red(m)), `𐄂 ${m.name}: ${m.shortDescription} (disabled)`), true);
|
|
28
|
+
}
|
|
29
|
+
}
|
|
30
|
+
for (const m of actionableModules) {
|
|
31
|
+
const fs = dry ? (0, mem_fs_1.create)() : _fs;
|
|
32
|
+
const excludeScaffolding = excludeScaffoldingFunc ? excludeScaffoldingFunc(fs, paths) : [];
|
|
33
|
+
(0, module_1.applyModule)(m, modulesEnabled, paramVals, scaffoldDir, fs, paths, excludeScaffolding, true);
|
|
34
|
+
if (dry) {
|
|
35
|
+
const filesWithChanges = fs
|
|
36
|
+
.all()
|
|
37
|
+
.filter(f => f.state && f.state !== 'deleted')
|
|
38
|
+
.filter(f => { var _a; return !(0, node_fs_1.existsSync)(f.path) || (0, node_fs_1.readFileSync)(f.path, 'utf8').toString() !== ((_a = f.contents) === null || _a === void 0 ? void 0 : _a.toString()); });
|
|
39
|
+
if (filesWithChanges.length > 0) {
|
|
40
|
+
io.error(`Module ${m.name} has ${filesWithChanges.length} changed files: ${filesWithChanges
|
|
41
|
+
.map(f => f.path.replace(paths.package() + '/', ''))
|
|
42
|
+
.join(', ')}`, false);
|
|
43
|
+
}
|
|
44
|
+
}
|
|
45
|
+
}
|
|
46
|
+
return _fs;
|
|
47
|
+
},
|
|
48
|
+
exposes: modules.map(m => `modules.${m.name}`),
|
|
49
|
+
getExposed(_paths, _paramProvider) {
|
|
50
|
+
return (0, rename_keys_1.renameKeys)(modulesEnabled, k => `modules.${k}`);
|
|
51
|
+
},
|
|
52
|
+
};
|
|
53
|
+
}
|
|
54
|
+
exports.auditStepFactory = auditStepFactory;
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
import { DefaultProviders, Step } from '../step-manager';
|
|
2
|
+
import { Module, ModuleStatusCache } from './module';
|
|
3
|
+
import { TemplateParam } from './template-param';
|
|
4
|
+
import { ExcludeScaffoldingFunc } from './scaffolder';
|
|
5
|
+
export declare function infraStepFactory<MN extends string, Providers extends DefaultProviders>(scaffoldDir: string, moduleName: string, modules: Module<MN>[], templateParams: TemplateParam[], excludeScaffoldingFunc?: ExcludeScaffoldingFunc, moduleStatusCache?: ModuleStatusCache<MN>): Step<Providers>;
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.infraStepFactory = void 0;
|
|
4
|
+
const module_1 = require("./module");
|
|
5
|
+
const template_param_1 = require("./template-param");
|
|
6
|
+
function infraStepFactory(scaffoldDir, moduleName, modules, templateParams, excludeScaffoldingFunc, moduleStatusCache) {
|
|
7
|
+
const module = modules.find(m => m.name === moduleName);
|
|
8
|
+
if (!module) {
|
|
9
|
+
throw new Error(`Module ${moduleName} not found`);
|
|
10
|
+
}
|
|
11
|
+
return {
|
|
12
|
+
type: module.shortDescription,
|
|
13
|
+
composable: true,
|
|
14
|
+
async run(fs, paths, io, _providers) {
|
|
15
|
+
const paramVals = await (0, template_param_1.currParamValues)(templateParams, fs, paths, io);
|
|
16
|
+
const modulesEnabled = await (0, module_1.currModulesEnabled)(modules, fs, paths, moduleStatusCache);
|
|
17
|
+
if (!module.updatable) {
|
|
18
|
+
io.error(`${module.name} is not updatable.`, true);
|
|
19
|
+
}
|
|
20
|
+
const excludeScaffolding = excludeScaffoldingFunc ? excludeScaffoldingFunc(fs, paths) : [];
|
|
21
|
+
const initializing = !modulesEnabled[module.name];
|
|
22
|
+
(0, module_1.applyModule)(module, modulesEnabled, paramVals, scaffoldDir, fs, paths, excludeScaffolding, initializing);
|
|
23
|
+
if (moduleStatusCache) {
|
|
24
|
+
(0, module_1.setModuleValue)(module, true, fs, paths, moduleStatusCache);
|
|
25
|
+
}
|
|
26
|
+
return fs;
|
|
27
|
+
},
|
|
28
|
+
exposes: [],
|
|
29
|
+
getExposed(_paths, _paramProvider) {
|
|
30
|
+
return {};
|
|
31
|
+
},
|
|
32
|
+
};
|
|
33
|
+
}
|
|
34
|
+
exports.infraStepFactory = infraStepFactory;
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
import { DefaultProviders, Step } from '../step-manager';
|
|
2
|
+
import { Module, ModuleStatusCache } from './module';
|
|
3
|
+
import { TemplateParam } from './template-param';
|
|
4
|
+
import { ExcludeScaffoldingFunc } from './scaffolder';
|
|
5
|
+
export declare function initStepFactory<MN extends string, Providers extends DefaultProviders>(scaffoldDir: string, modules: Module<MN>[], templateParams: TemplateParam[], excludeScaffoldingFunc?: ExcludeScaffoldingFunc, moduleStatusCache?: ModuleStatusCache<MN>): Step<Providers>;
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.initStepFactory = void 0;
|
|
4
|
+
const rename_keys_1 = require("../utils/rename-keys");
|
|
5
|
+
const module_1 = require("./module");
|
|
6
|
+
const template_param_1 = require("./template-param");
|
|
7
|
+
function initStepFactory(scaffoldDir, modules, templateParams, excludeScaffoldingFunc, moduleStatusCache) {
|
|
8
|
+
let modulesEnabled;
|
|
9
|
+
return {
|
|
10
|
+
type: 'Generate package skeleton',
|
|
11
|
+
composable: true,
|
|
12
|
+
async run(fs, paths, io, _providers) {
|
|
13
|
+
const paramVals = await (0, template_param_1.promptParamValues)(templateParams, paths, io);
|
|
14
|
+
modulesEnabled = await (0, module_1.promptModulesEnabled)(modules, io);
|
|
15
|
+
const excludeScaffolding = excludeScaffoldingFunc ? excludeScaffoldingFunc(fs, paths) : [];
|
|
16
|
+
for (const m of modules) {
|
|
17
|
+
if (modulesEnabled[m.name] && (!m.togglable || !m.dependsOn.some(dep => !modulesEnabled[dep]))) {
|
|
18
|
+
(0, module_1.applyModule)(m, modulesEnabled, paramVals, scaffoldDir, fs, paths, excludeScaffolding, true);
|
|
19
|
+
}
|
|
20
|
+
}
|
|
21
|
+
if (moduleStatusCache) {
|
|
22
|
+
modules.forEach(m => {
|
|
23
|
+
(0, module_1.setModuleValue)(m, modulesEnabled[m.name], fs, paths, moduleStatusCache);
|
|
24
|
+
});
|
|
25
|
+
}
|
|
26
|
+
return fs;
|
|
27
|
+
},
|
|
28
|
+
exposes: modules.map(m => `modules.${m.name}`),
|
|
29
|
+
getExposed(_paths, _paramProvider) {
|
|
30
|
+
return (0, rename_keys_1.renameKeys)(modulesEnabled, k => `modules.${k}`);
|
|
31
|
+
},
|
|
32
|
+
};
|
|
33
|
+
}
|
|
34
|
+
exports.initStepFactory = initStepFactory;
|
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
import { Store } from 'mem-fs';
|
|
2
|
+
import { IO } from 'boilersmith/io';
|
|
3
|
+
import { Paths } from 'boilersmith/paths';
|
|
4
|
+
interface FileOwnership {
|
|
5
|
+
/**
|
|
6
|
+
* The path to the file
|
|
7
|
+
*/
|
|
8
|
+
path: string;
|
|
9
|
+
/**
|
|
10
|
+
* If any of the needed modules aren't enabled, the file won't be updated.
|
|
11
|
+
*/
|
|
12
|
+
needsOtherModules?: string[];
|
|
13
|
+
/**
|
|
14
|
+
* If in a monorepo, should the file be placed relative to the monorepo root?
|
|
15
|
+
*/
|
|
16
|
+
monorepoPath?: string;
|
|
17
|
+
}
|
|
18
|
+
interface CommonModule<N extends string> {
|
|
19
|
+
name: N;
|
|
20
|
+
shortDescription: string;
|
|
21
|
+
longDescription?: string;
|
|
22
|
+
/**
|
|
23
|
+
* Whether files belonging to this module should be kept up to date.
|
|
24
|
+
*/
|
|
25
|
+
updatable: boolean;
|
|
26
|
+
/**
|
|
27
|
+
* A list of scaffolding files managed by this module.
|
|
28
|
+
*/
|
|
29
|
+
filesToReplace: (string | FileOwnership)[];
|
|
30
|
+
/**
|
|
31
|
+
* A map of names of JSON files to keys which should be deep-merged from the scaffolding.
|
|
32
|
+
*/
|
|
33
|
+
jsonToAugment: Record<string, string[]>;
|
|
34
|
+
/**
|
|
35
|
+
* An array of names of template params needed by this module.
|
|
36
|
+
*/
|
|
37
|
+
needsTemplateParams: string[];
|
|
38
|
+
}
|
|
39
|
+
interface UntoggleableModule<N extends string> extends CommonModule<N> {
|
|
40
|
+
/**
|
|
41
|
+
* Whether this module can be enabled/disabled.
|
|
42
|
+
*/
|
|
43
|
+
togglable: false;
|
|
44
|
+
}
|
|
45
|
+
interface TogglableModule<N extends string> extends CommonModule<N> {
|
|
46
|
+
/**
|
|
47
|
+
* Whether this module can be enabled/disabled.
|
|
48
|
+
*/
|
|
49
|
+
togglable: true;
|
|
50
|
+
/**
|
|
51
|
+
* Whether this module is enabled or disabled by default.
|
|
52
|
+
*/
|
|
53
|
+
defaultEnabled: boolean;
|
|
54
|
+
/**
|
|
55
|
+
* Can only be enabled if these other modules are enabled.
|
|
56
|
+
*/
|
|
57
|
+
dependsOn: string[];
|
|
58
|
+
}
|
|
59
|
+
export declare type Module<N extends string = string> = UntoggleableModule<N> | TogglableModule<N>;
|
|
60
|
+
export declare type ModuleStatusCache<N extends string> = {
|
|
61
|
+
get: (module: Module<N>, fs: Store, paths: Paths) => Promise<boolean | undefined>;
|
|
62
|
+
set: (module: Module<N>, val: boolean, fs: Store, paths: Paths) => Promise<void>;
|
|
63
|
+
};
|
|
64
|
+
export declare function promptModulesEnabled<N extends string>(modules: Module<N>[], io: IO): Promise<Record<N, boolean>>;
|
|
65
|
+
export declare function currModulesEnabled<N extends string>(modules: Module<N>[], fs: Store, paths: Paths, cache?: ModuleStatusCache<N>): Promise<Record<N, boolean>>;
|
|
66
|
+
export declare function setModuleValue<MN extends string>(module: Module<MN>, enabled: boolean, fs: Store, paths: Paths, cache: ModuleStatusCache<MN>): Promise<void>;
|
|
67
|
+
export declare function applyModule<MN extends string, TN extends string>(module: Module<MN>, modulesEnabled: Record<string, boolean>, paramVals: Record<TN, unknown>, scaffoldDir: string, fs: Store, paths: Paths, excludeFiles?: string[], isInitial?: boolean): Promise<Store>;
|
|
68
|
+
export {};
|
|
@@ -0,0 +1,111 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.applyModule = exports.setModuleValue = exports.currModulesEnabled = exports.promptModulesEnabled = void 0;
|
|
4
|
+
const tslib_1 = require("tslib");
|
|
5
|
+
const chalk_1 = (0, tslib_1.__importDefault)(require("chalk"));
|
|
6
|
+
const mem_fs_editor_1 = require("mem-fs-editor");
|
|
7
|
+
const node_path_1 = require("node:path");
|
|
8
|
+
const pick_deep_1 = (0, tslib_1.__importDefault)(require("pick-deep"));
|
|
9
|
+
const read_tpl_1 = require("boilersmith/utils/read-tpl");
|
|
10
|
+
const clone_and_fill_1 = require("boilersmith/utils/clone-and-fill");
|
|
11
|
+
const rename_keys_1 = require("boilersmith/utils/rename-keys");
|
|
12
|
+
const cond_format_1 = require("boilersmith/utils/cond-format");
|
|
13
|
+
async function promptModulesEnabled(modules, io) {
|
|
14
|
+
const modulesEnabled = {};
|
|
15
|
+
const advanced = await io.getParam({
|
|
16
|
+
name: 'advancedInstallation',
|
|
17
|
+
type: 'confirm',
|
|
18
|
+
initial: false,
|
|
19
|
+
message: `Advanced Initialization ${(0, cond_format_1.condFormat)(io.supportsAnsiColor, chalk_1.default.dim, '(fine-tune which features are enabled)')}`,
|
|
20
|
+
});
|
|
21
|
+
for (const m of modules) {
|
|
22
|
+
const missingDeps = !m.togglable || m.dependsOn.some(dep => !modulesEnabled[dep]);
|
|
23
|
+
if (!m.togglable) {
|
|
24
|
+
modulesEnabled[m.name] = true;
|
|
25
|
+
}
|
|
26
|
+
else if (missingDeps) {
|
|
27
|
+
modulesEnabled[m.name] = false;
|
|
28
|
+
}
|
|
29
|
+
else if (advanced) {
|
|
30
|
+
// eslint-disable-next-line no-await-in-loop
|
|
31
|
+
modulesEnabled[m.name] = await io.getParam({
|
|
32
|
+
name: `modules.${m.name}`,
|
|
33
|
+
type: 'confirm',
|
|
34
|
+
initial: m.defaultEnabled,
|
|
35
|
+
message: m.shortDescription + (m.longDescription ? (0, cond_format_1.condFormat)(io.supportsAnsiColor, chalk_1.default.dim, ` (${m.longDescription})`) : ''),
|
|
36
|
+
});
|
|
37
|
+
}
|
|
38
|
+
else {
|
|
39
|
+
modulesEnabled[m.name] = m.defaultEnabled;
|
|
40
|
+
}
|
|
41
|
+
}
|
|
42
|
+
return modulesEnabled;
|
|
43
|
+
}
|
|
44
|
+
exports.promptModulesEnabled = promptModulesEnabled;
|
|
45
|
+
async function currModulesEnabled(modules, fs, paths, cache) {
|
|
46
|
+
const modulesEnabled = {};
|
|
47
|
+
for (const m of modules) {
|
|
48
|
+
if (m.togglable) {
|
|
49
|
+
// eslint-disable-next-line no-await-in-loop
|
|
50
|
+
const cacheVal = await (cache === null || cache === void 0 ? void 0 : cache.get(m, fs, paths));
|
|
51
|
+
modulesEnabled[m.name] = cacheVal !== null && cacheVal !== void 0 ? cacheVal : m.defaultEnabled;
|
|
52
|
+
}
|
|
53
|
+
else {
|
|
54
|
+
modulesEnabled[m.name] = true;
|
|
55
|
+
}
|
|
56
|
+
}
|
|
57
|
+
return modulesEnabled;
|
|
58
|
+
}
|
|
59
|
+
exports.currModulesEnabled = currModulesEnabled;
|
|
60
|
+
async function setModuleValue(module, enabled, fs, paths, cache) {
|
|
61
|
+
if (module.togglable) {
|
|
62
|
+
cache.set(module, enabled, fs, paths);
|
|
63
|
+
}
|
|
64
|
+
}
|
|
65
|
+
exports.setModuleValue = setModuleValue;
|
|
66
|
+
// eslint-disable-next-line max-params
|
|
67
|
+
async function applyModule(module, modulesEnabled, paramVals, scaffoldDir, fs, paths, excludeFiles = [], isInitial = false) {
|
|
68
|
+
var _a;
|
|
69
|
+
const fsEditor = (0, mem_fs_editor_1.create)(fs);
|
|
70
|
+
// Validate that module can be enabled
|
|
71
|
+
if (!(modulesEnabled === null || modulesEnabled === void 0 ? void 0 : modulesEnabled[module.name])) {
|
|
72
|
+
throw new Error(`Could not apply module "${module.name}", because it is not enabled in the provided module statuses.`);
|
|
73
|
+
}
|
|
74
|
+
// Validate that dependencies are enabled
|
|
75
|
+
const missingDeps = module.togglable ? module.dependsOn.filter(dep => !modulesEnabled[dep]) : [];
|
|
76
|
+
if (missingDeps.length > 0) {
|
|
77
|
+
throw new Error(`Could not apply module "${module.name}", because the following dependency modules are missing: "${missingDeps.join(', ')}".`);
|
|
78
|
+
}
|
|
79
|
+
// Validate that all needed params are present
|
|
80
|
+
const missingParams = module.needsTemplateParams.filter(p => !(p in paramVals));
|
|
81
|
+
if (missingParams.length > 0) {
|
|
82
|
+
throw new Error(`Could not apply module "${module.name}", because the following params are missing: "${missingParams.join(', ')}".`);
|
|
83
|
+
}
|
|
84
|
+
if (!isInitial && !module.updatable) {
|
|
85
|
+
throw new Error(`Cannot update module "${module.name}", as it is not updatable, and has already been initialized.`);
|
|
86
|
+
}
|
|
87
|
+
const tplData = {
|
|
88
|
+
params: paramVals,
|
|
89
|
+
modules: modulesEnabled,
|
|
90
|
+
};
|
|
91
|
+
const tplDataFlat = Object.assign(Object.assign({}, (0, rename_keys_1.renameKeys)(tplData.modules, k => `modules.${k}`)), (0, rename_keys_1.renameKeys)(tplData.params, k => `params.${k}`));
|
|
92
|
+
for (const file of module.filesToReplace) {
|
|
93
|
+
const path = typeof file === 'string' ? file : file.path;
|
|
94
|
+
const needsOtherModules = typeof file === 'string' ? [] : (_a = file.needsOtherModules) !== null && _a !== void 0 ? _a : [];
|
|
95
|
+
if (!excludeFiles.includes(path) && !needsOtherModules.some(dep => !modulesEnabled[dep])) {
|
|
96
|
+
const copyToIfMonorepo = typeof file !== 'string' && file.monorepoPath ? paths.monorepo((0, clone_and_fill_1.cloneAndFill)(file.monorepoPath, tplDataFlat)) : undefined;
|
|
97
|
+
const copyTo = copyToIfMonorepo !== null && copyToIfMonorepo !== void 0 ? copyToIfMonorepo : paths.package(path);
|
|
98
|
+
fsEditor.copyTpl((0, node_path_1.resolve)(scaffoldDir, path), copyTo, tplData);
|
|
99
|
+
}
|
|
100
|
+
}
|
|
101
|
+
const jsonPaths = (0, clone_and_fill_1.cloneAndFill)(module.jsonToAugment, tplDataFlat);
|
|
102
|
+
for (const jsonPath of Object.keys(jsonPaths)) {
|
|
103
|
+
const scaffoldContents = (0, read_tpl_1.readTpl)((0, node_path_1.resolve)(scaffoldDir, jsonPath), tplData);
|
|
104
|
+
const scaffoldContentsJson = JSON.parse(scaffoldContents);
|
|
105
|
+
const fieldsToAugment = jsonPaths[jsonPath];
|
|
106
|
+
const relevant = (0, pick_deep_1.default)(scaffoldContentsJson, fieldsToAugment);
|
|
107
|
+
fsEditor.extendJSON(paths.package(jsonPath), relevant, undefined, 4);
|
|
108
|
+
}
|
|
109
|
+
return fs;
|
|
110
|
+
}
|
|
111
|
+
exports.applyModule = applyModule;
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
import { Store } from 'mem-fs';
|
|
2
|
+
import { Paths } from '../paths';
|
|
3
|
+
import { DefaultProviders, Step } from '../step-manager';
|
|
4
|
+
import { Module, ModuleStatusCache } from './module';
|
|
5
|
+
import { TemplateParam } from './template-param';
|
|
6
|
+
import { IO } from 'boilersmith/io';
|
|
7
|
+
export declare type ExcludeScaffoldingFunc = (fs: Store, paths: Paths) => string[];
|
|
8
|
+
export declare class Scaffolder<TN extends string = string, MN extends string = string> {
|
|
9
|
+
private templateParams;
|
|
10
|
+
private modules;
|
|
11
|
+
private scaffoldDir;
|
|
12
|
+
private moduleStatusCache?;
|
|
13
|
+
private excludeScaffoldingFunc?;
|
|
14
|
+
constructor(scaffoldDir: string);
|
|
15
|
+
constructor(scaffoldDir: string, moduleStatusCache: ModuleStatusCache<MN>);
|
|
16
|
+
constructor(scaffoldDir: string, moduleStatusCache: ModuleStatusCache<MN>, excludeScaffoldingFuncs: ExcludeScaffoldingFunc);
|
|
17
|
+
registerModule(module: Module<MN>): this;
|
|
18
|
+
registerTemplateParam<T>(templateParam: TemplateParam<T, TN>): this;
|
|
19
|
+
genInitStep<Providers extends DefaultProviders>(): Step<Providers>;
|
|
20
|
+
genInfraStep<Providers extends DefaultProviders>(module: string): Step<Providers>;
|
|
21
|
+
genAuditStep<Providers extends DefaultProviders>(dry?: boolean): Step<Providers>;
|
|
22
|
+
templateParamVal<T>(param: TN, fs: Store, paths: Paths, io: IO): Promise<T>;
|
|
23
|
+
templateParamVals(fs: Store, paths: Paths, io: IO): Promise<Record<TN, unknown>>;
|
|
24
|
+
modulesEnabled(fs: Store, paths: Paths): Promise<Record<MN, boolean>>;
|
|
25
|
+
moduleFiles(moduleName: MN): string[];
|
|
26
|
+
/**
|
|
27
|
+
* Confirm that all files and configuration keys in the scaffolding dir
|
|
28
|
+
* are owned by at least one module, and that no modules own nonexistent
|
|
29
|
+
* files or configuration keys.
|
|
30
|
+
*/
|
|
31
|
+
validate(): Promise<void>;
|
|
32
|
+
}
|