context-forge
Version:
AI orchestration platform with autonomous teams, enhancement planning, migration tools, 25+ slash commands, checkpoints & hooks. Multi-IDE: Claude, Cursor, Windsurf, Cline, Copilot
102 lines ⢠4.84 kB
JavaScript
;
var __importDefault = (this && this.__importDefault) || function (mod) {
return (mod && mod.__esModule) ? mod : { "default": mod };
};
Object.defineProperty(exports, "__esModule", { value: true });
exports.copyHooksCommand = void 0;
const commander_1 = require("commander");
const chalk_1 = __importDefault(require("chalk"));
const ora_1 = __importDefault(require("ora"));
const path_1 = __importDefault(require("path"));
const inquirer_1 = __importDefault(require("inquirer"));
const hooks_1 = require("../../generators/hooks");
const fs_extra_1 = __importDefault(require("fs-extra"));
exports.copyHooksCommand = new commander_1.Command('copy-hooks')
.description('Copy Claude Code hooks from an external repository')
.option('-s, --source <path>', 'source repository path')
.option('-t, --target <path>', 'target directory (default: current directory)', '.')
.option('-a, --all', 'copy all hooks without prompting')
.action(async (options) => {
console.log(chalk_1.default.blue.bold('\nđŞ Copy Claude Code Hooks\n'));
const spinner = (0, ora_1.default)();
try {
let sourcePath = options.source;
// If no source provided, prompt for it
if (!sourcePath) {
const { repoPath } = await inquirer_1.default.prompt([
{
type: 'input',
name: 'repoPath',
message: 'Path to hooks repository:',
default: '../claude-hooks-repo',
validate: async (input) => {
const exists = await fs_extra_1.default.pathExists(input);
return exists || 'Repository path does not exist';
},
},
]);
sourcePath = repoPath;
}
const targetPath = path_1.default.resolve(options.target);
const hooksRepoPath = path_1.default.resolve(sourcePath);
// Validate source repository
spinner.start('Validating hooks repository...');
const hooksDir = path_1.default.join(hooksRepoPath, 'hooks');
if (!(await fs_extra_1.default.pathExists(hooksDir))) {
spinner.fail('Hooks directory not found in repository');
console.log(chalk_1.default.red(`Expected hooks directory at: ${hooksDir}`));
return;
}
const availableHooks = await fs_extra_1.default.readdir(hooksDir);
spinner.succeed(`Found ${availableHooks.length} hooks in repository`);
let selectedHooks = [];
if (options.all) {
selectedHooks = availableHooks;
}
else {
// Let user select which hooks to copy
const { hooks } = await inquirer_1.default.prompt([
{
type: 'checkbox',
name: 'hooks',
message: 'Select hooks to copy:',
choices: availableHooks.map((hook) => ({
name: hook,
value: hook,
checked: true, // Default to all selected
})),
},
]);
selectedHooks = hooks;
}
if (selectedHooks.length === 0) {
console.log(chalk_1.default.yellow('No hooks selected. Exiting.'));
return;
}
// Copy selected hooks
spinner.start(`Copying ${selectedHooks.length} hooks...`);
await (0, hooks_1.copyHooksFromRepo)(hooksRepoPath, targetPath, selectedHooks);
spinner.succeed('Hooks copied successfully');
// Display success message
console.log(chalk_1.default.green.bold('\n⨠Hooks installation complete!\n'));
console.log(chalk_1.default.white('Copied hooks:'));
selectedHooks.forEach((hook) => {
console.log(chalk_1.default.gray(` ⢠${hook}`));
});
console.log(chalk_1.default.blue.bold('\nđŻ Next steps:\n'));
console.log(chalk_1.default.white('1. Review hooks in .claude/hooks/'));
console.log(chalk_1.default.white('2. Customize hooks for your project'));
console.log(chalk_1.default.white('3. Ensure Claude Code has hooks enabled'));
console.log(chalk_1.default.white('4. Test hooks by running development commands\n'));
// Show hook status
const targetHooksPath = path_1.default.join(targetPath, '.claude', 'hooks');
const installedHooks = await fs_extra_1.default.readdir(targetHooksPath);
console.log(chalk_1.default.cyan(`đ Hooks directory: ${targetHooksPath}`));
console.log(chalk_1.default.cyan(`đ Total hooks installed: ${installedHooks.length}`));
}
catch (error) {
spinner.fail('Failed to copy hooks');
throw error;
}
});
//# sourceMappingURL=copy-hooks.js.map