@lumenflow/cli 3.17.5 → 3.17.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/dist/init-docs-scaffolder.js +96 -0
- package/dist/init-docs-scaffolder.js.map +1 -0
- package/dist/init-package-config.js +135 -0
- package/dist/init-package-config.js.map +1 -0
- package/dist/init-safety-scripts.js +129 -0
- package/dist/init-safety-scripts.js.map +1 -0
- package/dist/init.js +13 -302
- package/dist/init.js.map +1 -1
- package/dist/onboarding-template-paths.js +0 -1
- package/dist/onboarding-template-paths.js.map +1 -1
- package/dist/wu-done.js +389 -423
- package/dist/wu-done.js.map +1 -1
- package/package.json +8 -8
- package/packs/sidekick/.turbo/turbo-build.log +1 -1
- package/packs/sidekick/package.json +1 -1
- package/packs/sidekick/vitest.config.ts +11 -0
- package/packs/software-delivery/.turbo/turbo-build.log +1 -1
- package/packs/software-delivery/package.json +1 -1
- package/packs/software-delivery/vitest.config.ts +11 -0
- package/templates/core/LUMENFLOW.md.template +2 -2
- package/templates/core/ai/onboarding/wu-sizing-guide.md.template +0 -84
|
@@ -0,0 +1,96 @@
|
|
|
1
|
+
// Copyright (c) 2026 Hellmai Ltd
|
|
2
|
+
// SPDX-License-Identifier: AGPL-3.0-only
|
|
3
|
+
/**
|
|
4
|
+
* @file init-docs-scaffolder.ts
|
|
5
|
+
* WU-2399: Extracted from init.ts -- documentation generation and framework overlay logic.
|
|
6
|
+
*
|
|
7
|
+
* Responsible for:
|
|
8
|
+
* - Full docs scaffolding (WU dirs, templates, backlog, status)
|
|
9
|
+
* - Agent onboarding docs
|
|
10
|
+
* - Claude skills
|
|
11
|
+
* - Framework overlay files
|
|
12
|
+
*/
|
|
13
|
+
import * as path from 'node:path';
|
|
14
|
+
import { createError, ErrorCodes } from '@lumenflow/core';
|
|
15
|
+
import { processTemplate, loadTemplate, createFile, createDirectory } from './init-scaffolding.js';
|
|
16
|
+
import { BACKLOG_TEMPLATE, STATUS_TEMPLATE, WU_TEMPLATE_YAML, FRAMEWORK_HINT_TEMPLATE, FRAMEWORK_OVERLAY_TEMPLATE, WU_LIFECYCLE_SKILL_TEMPLATE, WORKTREE_DISCIPLINE_SKILL_TEMPLATE, LUMENFLOW_GATES_SKILL_TEMPLATE, } from './init-templates.js';
|
|
17
|
+
import { SCAFFOLDED_ONBOARDING_TEMPLATE_PATHS } from './onboarding-template-paths.js';
|
|
18
|
+
/**
|
|
19
|
+
* Normalize a framework name into display + slug
|
|
20
|
+
*/
|
|
21
|
+
export function normalizeFrameworkName(framework) {
|
|
22
|
+
const name = framework.trim();
|
|
23
|
+
const slug = name
|
|
24
|
+
.toLowerCase()
|
|
25
|
+
.replace(/[^a-z0-9_-]+/g, '-')
|
|
26
|
+
// Remove leading dashes and trailing dashes separately (explicit precedence)
|
|
27
|
+
.replace(/^-+/, '')
|
|
28
|
+
.replace(/-+$/, '');
|
|
29
|
+
if (!slug) {
|
|
30
|
+
throw createError(ErrorCodes.INVALID_ARGUMENT, `Invalid framework name: "${framework}"`);
|
|
31
|
+
}
|
|
32
|
+
return { name, slug };
|
|
33
|
+
}
|
|
34
|
+
/**
|
|
35
|
+
* WU-1083: Scaffold agent onboarding documentation
|
|
36
|
+
* WU-1300: Added starting-prompt.md
|
|
37
|
+
* WU-1309: Added onboarding docs scaffold with dynamic docs path resolution
|
|
38
|
+
*/
|
|
39
|
+
export async function scaffoldAgentOnboardingDocs(targetDir, options, result, tokens) {
|
|
40
|
+
// WU-1309: Use dynamic onboarding path from tokens
|
|
41
|
+
const onboardingDir = path.join(targetDir, tokens.DOCS_ONBOARDING_PATH);
|
|
42
|
+
await createDirectory(onboardingDir, result, targetDir);
|
|
43
|
+
for (const [outputFile, templatePath] of Object.entries(SCAFFOLDED_ONBOARDING_TEMPLATE_PATHS)) {
|
|
44
|
+
await createFile(path.join(onboardingDir, outputFile), processTemplate(loadTemplate(templatePath), tokens), options.force, result, targetDir);
|
|
45
|
+
}
|
|
46
|
+
}
|
|
47
|
+
/**
|
|
48
|
+
* WU-1083: Scaffold Claude skills
|
|
49
|
+
*/
|
|
50
|
+
export async function scaffoldClaudeSkills(targetDir, options, result, tokens) {
|
|
51
|
+
const skillsDir = path.join(targetDir, '.claude', 'skills');
|
|
52
|
+
// wu-lifecycle skill
|
|
53
|
+
const wuLifecycleDir = path.join(skillsDir, 'wu-lifecycle');
|
|
54
|
+
await createDirectory(wuLifecycleDir, result, targetDir);
|
|
55
|
+
await createFile(path.join(wuLifecycleDir, 'SKILL.md'), processTemplate(WU_LIFECYCLE_SKILL_TEMPLATE, tokens), true, result, targetDir);
|
|
56
|
+
// worktree-discipline skill
|
|
57
|
+
const worktreeDir = path.join(skillsDir, 'worktree-discipline');
|
|
58
|
+
await createDirectory(worktreeDir, result, targetDir);
|
|
59
|
+
await createFile(path.join(worktreeDir, 'SKILL.md'), processTemplate(WORKTREE_DISCIPLINE_SKILL_TEMPLATE, tokens), true, result, targetDir);
|
|
60
|
+
// lumenflow-gates skill
|
|
61
|
+
const gatesDir = path.join(skillsDir, 'lumenflow-gates');
|
|
62
|
+
await createDirectory(gatesDir, result, targetDir);
|
|
63
|
+
await createFile(path.join(gatesDir, 'SKILL.md'), processTemplate(LUMENFLOW_GATES_SKILL_TEMPLATE, tokens), true, result, targetDir);
|
|
64
|
+
}
|
|
65
|
+
export async function scaffoldFullDocs(targetDir, options, result, tokens) {
|
|
66
|
+
// WU-1309: Use config-derived docs paths from tokens (computed in scaffoldProject)
|
|
67
|
+
const wuDir = path.join(targetDir, tokens.DOCS_WU_DIR_PATH);
|
|
68
|
+
const templatesDir = path.join(targetDir, tokens.DOCS_TEMPLATES_DIR_PATH);
|
|
69
|
+
await createDirectory(wuDir, result, targetDir);
|
|
70
|
+
await createDirectory(templatesDir, result, targetDir);
|
|
71
|
+
await createFile(path.join(wuDir, '.gitkeep'), '', options.force, result, targetDir);
|
|
72
|
+
await createFile(path.join(targetDir, tokens.DOCS_BACKLOG_PATH), BACKLOG_TEMPLATE, true, result, targetDir);
|
|
73
|
+
await createFile(path.join(targetDir, tokens.DOCS_STATUS_PATH), STATUS_TEMPLATE, true, result, targetDir);
|
|
74
|
+
await createFile(path.join(templatesDir, 'wu-template.yaml'), processTemplate(WU_TEMPLATE_YAML, tokens), true, result, targetDir);
|
|
75
|
+
// WU-1083: Scaffold agent onboarding docs with --full
|
|
76
|
+
await scaffoldAgentOnboardingDocs(targetDir, options, result, tokens);
|
|
77
|
+
}
|
|
78
|
+
/** Framework hint file name constant */
|
|
79
|
+
const FRAMEWORK_HINT_FILE = '.lumenflow.framework.yaml';
|
|
80
|
+
export async function scaffoldFrameworkOverlay(targetDir, options, result, tokens) {
|
|
81
|
+
if (!options.framework) {
|
|
82
|
+
return;
|
|
83
|
+
}
|
|
84
|
+
const { name, slug } = normalizeFrameworkName(options.framework);
|
|
85
|
+
const frameworkTokens = {
|
|
86
|
+
...tokens,
|
|
87
|
+
FRAMEWORK_NAME: name,
|
|
88
|
+
FRAMEWORK_SLUG: slug,
|
|
89
|
+
};
|
|
90
|
+
await createFile(path.join(targetDir, FRAMEWORK_HINT_FILE), processTemplate(FRAMEWORK_HINT_TEMPLATE, frameworkTokens), options.force, result, targetDir);
|
|
91
|
+
// WU-1309: Use dynamic operations path from tokens
|
|
92
|
+
const overlayDir = path.join(targetDir, tokens.DOCS_OPERATIONS_PATH, '_frameworks', slug);
|
|
93
|
+
await createDirectory(overlayDir, result, targetDir);
|
|
94
|
+
await createFile(path.join(overlayDir, 'README.md'), processTemplate(FRAMEWORK_OVERLAY_TEMPLATE, frameworkTokens), options.force, result, targetDir);
|
|
95
|
+
}
|
|
96
|
+
//# sourceMappingURL=init-docs-scaffolder.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"init-docs-scaffolder.js","sourceRoot":"","sources":["../src/init-docs-scaffolder.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,135 @@
|
|
|
1
|
+
// Copyright (c) 2026 Hellmai Ltd
|
|
2
|
+
// SPDX-License-Identifier: AGPL-3.0-only
|
|
3
|
+
/**
|
|
4
|
+
* @file init-package-config.ts
|
|
5
|
+
* WU-2399: Extracted from init.ts -- package.json scripts, prettier config,
|
|
6
|
+
* dependency injection.
|
|
7
|
+
*
|
|
8
|
+
* Responsible for:
|
|
9
|
+
* - Generating LumenFlow scripts from the public manifest
|
|
10
|
+
* - Injecting scripts into package.json
|
|
11
|
+
* - Adding devDependencies (prettier, @lumenflow/cli)
|
|
12
|
+
* - Adding gate stub scripts
|
|
13
|
+
*/
|
|
14
|
+
import * as fs from 'node:fs';
|
|
15
|
+
import * as path from 'node:path';
|
|
16
|
+
import { getPublicManifest } from './public-manifest.js';
|
|
17
|
+
import { GATE_STUB_SCRIPTS, SCRIPT_ARG_OVERRIDES } from './init-templates.js';
|
|
18
|
+
/**
|
|
19
|
+
* WU-1517: Prettier version to add to devDependencies.
|
|
20
|
+
* Uses caret range to allow minor/patch updates.
|
|
21
|
+
*/
|
|
22
|
+
export const PRETTIER_VERSION = '^3.8.0';
|
|
23
|
+
/** WU-1517: Prettier package name constant */
|
|
24
|
+
export const PRETTIER_PACKAGE_NAME = 'prettier';
|
|
25
|
+
/**
|
|
26
|
+
* WU-1963: @lumenflow/cli version to add to devDependencies.
|
|
27
|
+
* Uses caret range to allow minor/patch updates within the major version.
|
|
28
|
+
* This ensures `pnpm wu:create`, `pnpm gates`, etc. resolve after `pnpm install`.
|
|
29
|
+
*/
|
|
30
|
+
export const CLI_PACKAGE_VERSION = '^3.0.0';
|
|
31
|
+
/** WU-1963: CLI package name constant */
|
|
32
|
+
export const CLI_PACKAGE_NAME = '@lumenflow/cli';
|
|
33
|
+
/**
|
|
34
|
+
* WU-1307: LumenFlow scripts to inject into package.json
|
|
35
|
+
* WU-1342: Expanded to include essential commands
|
|
36
|
+
* WU-1433: Now derived from the public CLI manifest (WU-1432) instead of
|
|
37
|
+
* hardcoded list. Ensures all public commands are exposed and avoids drift.
|
|
38
|
+
*/
|
|
39
|
+
export function generateLumenflowScripts() {
|
|
40
|
+
const scripts = {};
|
|
41
|
+
const manifest = getPublicManifest();
|
|
42
|
+
for (const cmd of manifest) {
|
|
43
|
+
// Use override if defined, otherwise map to the binary name
|
|
44
|
+
scripts[cmd.name] = SCRIPT_ARG_OVERRIDES[cmd.name] ?? cmd.binName;
|
|
45
|
+
}
|
|
46
|
+
return scripts;
|
|
47
|
+
}
|
|
48
|
+
/**
|
|
49
|
+
* WU-1300: Inject LumenFlow scripts into package.json
|
|
50
|
+
* WU-1517: Also adds prettier devDependency
|
|
51
|
+
* WU-1518: Also adds gate stub scripts (spec:linter, lint, typecheck)
|
|
52
|
+
* WU-1747: format and format:check are now part of GATE_STUB_SCRIPTS
|
|
53
|
+
* WU-1963: Also adds @lumenflow/cli devDependency so binary scripts resolve
|
|
54
|
+
* WU-2399: Fix --force flag: when force is true, always overwrite existing values
|
|
55
|
+
* - Creates package.json if it doesn't exist
|
|
56
|
+
* - Preserves existing scripts (doesn't overwrite unless --force)
|
|
57
|
+
* - Adds missing LumenFlow scripts
|
|
58
|
+
* - Adds @lumenflow/cli to devDependencies (provides wu-create, gates, etc. binaries)
|
|
59
|
+
* - Adds prettier to devDependencies
|
|
60
|
+
* - Adds gate stub scripts for spec:linter, lint, typecheck, format, format:check
|
|
61
|
+
*/
|
|
62
|
+
export async function injectPackageJsonScripts(targetDir, options, result) {
|
|
63
|
+
const packageJsonPath = path.join(targetDir, 'package.json');
|
|
64
|
+
let packageJson;
|
|
65
|
+
if (fs.existsSync(packageJsonPath)) {
|
|
66
|
+
// Read existing package.json
|
|
67
|
+
const content = fs.readFileSync(packageJsonPath, 'utf-8');
|
|
68
|
+
packageJson = JSON.parse(content);
|
|
69
|
+
}
|
|
70
|
+
else {
|
|
71
|
+
// Create minimal package.json
|
|
72
|
+
packageJson = {
|
|
73
|
+
name: path.basename(targetDir),
|
|
74
|
+
version: '0.0.1',
|
|
75
|
+
private: true,
|
|
76
|
+
};
|
|
77
|
+
}
|
|
78
|
+
// Ensure scripts object exists
|
|
79
|
+
if (!packageJson.scripts || typeof packageJson.scripts !== 'object') {
|
|
80
|
+
packageJson.scripts = {};
|
|
81
|
+
}
|
|
82
|
+
const scripts = packageJson.scripts;
|
|
83
|
+
let modified = false;
|
|
84
|
+
// WU-1433: Derive scripts from public manifest (not hardcoded)
|
|
85
|
+
// WU-2399: Fix --force flag: when force is true, always overwrite existing scripts
|
|
86
|
+
const lumenflowScripts = generateLumenflowScripts();
|
|
87
|
+
for (const [scriptName, scriptCommand] of Object.entries(lumenflowScripts)) {
|
|
88
|
+
if (options.force || !(scriptName in scripts)) {
|
|
89
|
+
scripts[scriptName] = scriptCommand;
|
|
90
|
+
modified = true;
|
|
91
|
+
}
|
|
92
|
+
}
|
|
93
|
+
// WU-1518: Add gate stub scripts (spec:linter, lint, typecheck, format, format:check)
|
|
94
|
+
// WU-1747: format and format:check are now part of GATE_STUB_SCRIPTS with
|
|
95
|
+
// auto-detection of prettier availability, so they pass immediately after init.
|
|
96
|
+
// These stubs let `pnpm gates` pass on a fresh project without manual script additions.
|
|
97
|
+
// Projects replace them with real tooling when ready.
|
|
98
|
+
for (const [scriptName, scriptCommand] of Object.entries(GATE_STUB_SCRIPTS)) {
|
|
99
|
+
if (options.force) {
|
|
100
|
+
scripts[scriptName] = scriptCommand;
|
|
101
|
+
modified = true;
|
|
102
|
+
}
|
|
103
|
+
else if (!(scriptName in scripts)) {
|
|
104
|
+
scripts[scriptName] = scriptCommand;
|
|
105
|
+
modified = true;
|
|
106
|
+
}
|
|
107
|
+
}
|
|
108
|
+
// Ensure devDependencies object exists
|
|
109
|
+
if (!packageJson.devDependencies || typeof packageJson.devDependencies !== 'object') {
|
|
110
|
+
packageJson.devDependencies = {};
|
|
111
|
+
}
|
|
112
|
+
const devDeps = packageJson.devDependencies;
|
|
113
|
+
// WU-1963: Add @lumenflow/cli to devDependencies so binary scripts resolve after pnpm install
|
|
114
|
+
if (options.force || !(CLI_PACKAGE_NAME in devDeps)) {
|
|
115
|
+
if (options.force && CLI_PACKAGE_NAME in devDeps) {
|
|
116
|
+
devDeps[CLI_PACKAGE_NAME] = CLI_PACKAGE_VERSION;
|
|
117
|
+
modified = true;
|
|
118
|
+
}
|
|
119
|
+
else if (!(CLI_PACKAGE_NAME in devDeps)) {
|
|
120
|
+
devDeps[CLI_PACKAGE_NAME] = CLI_PACKAGE_VERSION;
|
|
121
|
+
modified = true;
|
|
122
|
+
}
|
|
123
|
+
}
|
|
124
|
+
// WU-1517: Add prettier to devDependencies
|
|
125
|
+
// WU-2399: Fix --force flag: when force is true, always overwrite existing version
|
|
126
|
+
if (options.force || !(PRETTIER_PACKAGE_NAME in devDeps)) {
|
|
127
|
+
devDeps[PRETTIER_PACKAGE_NAME] = PRETTIER_VERSION;
|
|
128
|
+
modified = true;
|
|
129
|
+
}
|
|
130
|
+
if (modified) {
|
|
131
|
+
fs.writeFileSync(packageJsonPath, JSON.stringify(packageJson, null, 2) + '\n');
|
|
132
|
+
result.created.push('package.json (scripts updated)');
|
|
133
|
+
}
|
|
134
|
+
}
|
|
135
|
+
//# sourceMappingURL=init-package-config.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"init-package-config.js","sourceRoot":"","sources":["../src/init-package-config.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,129 @@
|
|
|
1
|
+
// Copyright (c) 2026 Hellmai Ltd
|
|
2
|
+
// SPDX-License-Identifier: AGPL-3.0-only
|
|
3
|
+
/**
|
|
4
|
+
* @file init-safety-scripts.ts
|
|
5
|
+
* WU-2399: Extracted from init.ts -- husky/git hooks, pre-commit setup,
|
|
6
|
+
* gitignore/prettierignore scaffolding.
|
|
7
|
+
*
|
|
8
|
+
* Responsible for:
|
|
9
|
+
* - Scaffolding .gitignore with LumenFlow exclusions
|
|
10
|
+
* - Scaffolding .prettierignore
|
|
11
|
+
* - Scaffolding scripts/safe-git wrapper
|
|
12
|
+
* - Scaffolding .husky/pre-commit hook
|
|
13
|
+
*/
|
|
14
|
+
import * as fs from 'node:fs';
|
|
15
|
+
import * as path from 'node:path';
|
|
16
|
+
import { createFile, createExecutableScript, loadTemplate } from './init-scaffolding.js';
|
|
17
|
+
import { GITIGNORE_TEMPLATE, REQUIRED_GITIGNORE_EXCLUSIONS, PRETTIERIGNORE_TEMPLATE, SAFE_GIT_TEMPLATE, PRE_COMMIT_TEMPLATE, } from './init-templates.js';
|
|
18
|
+
/** Gitignore file name constant to avoid duplicate string lint error */
|
|
19
|
+
const GITIGNORE_FILE_NAME = '.gitignore';
|
|
20
|
+
/** Prettierignore file name constant to avoid duplicate string lint error */
|
|
21
|
+
const PRETTIERIGNORE_FILE_NAME = '.prettierignore';
|
|
22
|
+
/** WU-1408: Safety script path constants */
|
|
23
|
+
const SCRIPTS_DIR = 'scripts';
|
|
24
|
+
const SAFE_GIT_FILE = 'safe-git';
|
|
25
|
+
const HUSKY_DIR = '.husky';
|
|
26
|
+
const PRE_COMMIT_FILE = 'pre-commit';
|
|
27
|
+
const SAFE_GIT_TEMPLATE_PATH = 'core/scripts/safe-git.template';
|
|
28
|
+
const PRE_COMMIT_TEMPLATE_PATH = 'core/.husky/pre-commit.template';
|
|
29
|
+
/**
|
|
30
|
+
* WU-1171: Determine file mode from options
|
|
31
|
+
*/
|
|
32
|
+
export function getFileMode(options) {
|
|
33
|
+
if (options.force) {
|
|
34
|
+
return 'force';
|
|
35
|
+
}
|
|
36
|
+
if (options.merge) {
|
|
37
|
+
return 'merge';
|
|
38
|
+
}
|
|
39
|
+
return 'skip';
|
|
40
|
+
}
|
|
41
|
+
/**
|
|
42
|
+
* WU-1342: Scaffold .gitignore file with LumenFlow exclusions
|
|
43
|
+
* Supports merge mode to add exclusions to existing .gitignore
|
|
44
|
+
* WU-2399: Fixed gitignore matching to parse lines and ignore comments
|
|
45
|
+
*/
|
|
46
|
+
export async function scaffoldGitignore(targetDir, options, result) {
|
|
47
|
+
const gitignorePath = path.join(targetDir, GITIGNORE_FILE_NAME);
|
|
48
|
+
const fileMode = getFileMode(options);
|
|
49
|
+
// WU-1965: Auto-merge lumenflow entries when .gitignore exists, regardless of mode.
|
|
50
|
+
// Previously only merge mode triggered merging; skip mode would skip the entire file,
|
|
51
|
+
// risking accidental commits of .lumenflow/telemetry, worktrees, etc.
|
|
52
|
+
if ((fileMode === 'merge' || fileMode === 'skip') && fs.existsSync(gitignorePath)) {
|
|
53
|
+
// Merge mode or skip mode with existing file: append LumenFlow exclusions if not already present
|
|
54
|
+
const existingContent = fs.readFileSync(gitignorePath, 'utf-8');
|
|
55
|
+
const linesToAdd = [];
|
|
56
|
+
// WU-2399: Parse gitignore lines properly -- strip comments and blank lines,
|
|
57
|
+
// compare against trimmed non-comment lines only. The old `existingContent.includes(pattern)`
|
|
58
|
+
// would false-positive match comments like "# ignore node_modules".
|
|
59
|
+
const existingNonCommentLines = new Set(existingContent
|
|
60
|
+
.split('\n')
|
|
61
|
+
.map((l) => l.trim())
|
|
62
|
+
.filter((l) => l.length > 0 && !l.startsWith('#')));
|
|
63
|
+
// WU-1969: Use shared constant so merge path and full template cannot drift
|
|
64
|
+
for (const { pattern, line } of REQUIRED_GITIGNORE_EXCLUSIONS) {
|
|
65
|
+
if (!existingNonCommentLines.has(pattern) && !existingNonCommentLines.has(line)) {
|
|
66
|
+
linesToAdd.push(line);
|
|
67
|
+
}
|
|
68
|
+
}
|
|
69
|
+
if (linesToAdd.length > 0) {
|
|
70
|
+
const separator = existingContent.endsWith('\n') ? '' : '\n';
|
|
71
|
+
const lumenflowBlock = `${separator}
|
|
72
|
+
# LumenFlow (auto-added)
|
|
73
|
+
${linesToAdd.join('\n')}
|
|
74
|
+
`;
|
|
75
|
+
fs.writeFileSync(gitignorePath, existingContent + lumenflowBlock);
|
|
76
|
+
result.merged = result.merged ?? [];
|
|
77
|
+
result.merged.push(GITIGNORE_FILE_NAME);
|
|
78
|
+
}
|
|
79
|
+
else {
|
|
80
|
+
result.skipped.push(GITIGNORE_FILE_NAME);
|
|
81
|
+
}
|
|
82
|
+
return;
|
|
83
|
+
}
|
|
84
|
+
// Force mode or file doesn't exist: write full template
|
|
85
|
+
await createFile(gitignorePath, GITIGNORE_TEMPLATE, fileMode, result, targetDir);
|
|
86
|
+
}
|
|
87
|
+
/**
|
|
88
|
+
* WU-1517: Scaffold .prettierignore file with sane defaults
|
|
89
|
+
* This is a core file scaffolded in all modes (full and minimal)
|
|
90
|
+
* because it's required for format:check gate to pass.
|
|
91
|
+
*/
|
|
92
|
+
export async function scaffoldPrettierignore(targetDir, options, result) {
|
|
93
|
+
const prettierignorePath = path.join(targetDir, PRETTIERIGNORE_FILE_NAME);
|
|
94
|
+
const fileMode = getFileMode(options);
|
|
95
|
+
await createFile(prettierignorePath, PRETTIERIGNORE_TEMPLATE, fileMode, result, targetDir);
|
|
96
|
+
}
|
|
97
|
+
/**
|
|
98
|
+
* WU-1408: Scaffold safety scripts (safe-git wrapper and pre-commit hook)
|
|
99
|
+
* These are core safety components needed for LumenFlow enforcement:
|
|
100
|
+
* - scripts/safe-git: Blocks dangerous git operations (e.g., manual worktree remove)
|
|
101
|
+
* - .husky/pre-commit: Blocks direct commits to main/master, enforces WU workflow
|
|
102
|
+
*
|
|
103
|
+
* Both scripts are scaffolded in all modes (full and minimal) because they are
|
|
104
|
+
* required for lumenflow-doctor to pass.
|
|
105
|
+
*/
|
|
106
|
+
export async function scaffoldSafetyScripts(targetDir, options, result) {
|
|
107
|
+
const fileMode = getFileMode(options);
|
|
108
|
+
// Scaffold scripts/safe-git
|
|
109
|
+
const safeGitPath = path.join(targetDir, SCRIPTS_DIR, SAFE_GIT_FILE);
|
|
110
|
+
try {
|
|
111
|
+
const safeGitTemplate = loadTemplate(SAFE_GIT_TEMPLATE_PATH);
|
|
112
|
+
await createExecutableScript(safeGitPath, safeGitTemplate, fileMode, result, targetDir);
|
|
113
|
+
}
|
|
114
|
+
catch {
|
|
115
|
+
// Fallback to hardcoded template if template file not found
|
|
116
|
+
await createExecutableScript(safeGitPath, SAFE_GIT_TEMPLATE, fileMode, result, targetDir);
|
|
117
|
+
}
|
|
118
|
+
// Scaffold .husky/pre-commit
|
|
119
|
+
const preCommitPath = path.join(targetDir, HUSKY_DIR, PRE_COMMIT_FILE);
|
|
120
|
+
try {
|
|
121
|
+
const preCommitTemplate = loadTemplate(PRE_COMMIT_TEMPLATE_PATH);
|
|
122
|
+
await createExecutableScript(preCommitPath, preCommitTemplate, fileMode, result, targetDir);
|
|
123
|
+
}
|
|
124
|
+
catch {
|
|
125
|
+
// Fallback to hardcoded template if template file not found
|
|
126
|
+
await createExecutableScript(preCommitPath, PRE_COMMIT_TEMPLATE, fileMode, result, targetDir);
|
|
127
|
+
}
|
|
128
|
+
}
|
|
129
|
+
//# sourceMappingURL=init-safety-scripts.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"init-safety-scripts.js","sourceRoot":"","sources":["../src/init-safety-scripts.ts"],"names":[],"mappings":"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"}
|