tree-cli-tool
Version:
A powerful command-line tool to display directory tree structure with various configuration options and output formats
234 lines • 9.25 kB
JavaScript
;
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
if (k2 === undefined) k2 = k;
var desc = Object.getOwnPropertyDescriptor(m, k);
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
desc = { enumerable: true, get: function() { return m[k]; } };
}
Object.defineProperty(o, k2, desc);
}) : (function(o, m, k, k2) {
if (k2 === undefined) k2 = k;
o[k2] = m[k];
}));
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
Object.defineProperty(o, "default", { enumerable: true, value: v });
}) : function(o, v) {
o["default"] = v;
});
var __importStar = (this && this.__importStar) || (function () {
var ownKeys = function(o) {
ownKeys = Object.getOwnPropertyNames || function (o) {
var ar = [];
for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
return ar;
};
return ownKeys(o);
};
return function (mod) {
if (mod && mod.__esModule) return mod;
var result = {};
if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
__setModuleDefault(result, mod);
return result;
};
})();
Object.defineProperty(exports, "__esModule", { value: true });
const commander_1 = require("commander");
const path = __importStar(require("path"));
const fs = __importStar(require("fs"));
const tree_builder_1 = require("./tree-builder");
const formatters_1 = require("./formatters");
const program = new commander_1.Command();
program
.name('tree-cli')
.description('A powerful command-line tool to display directory tree structure')
.version('1.0.0')
.argument('[path]', 'Target directory path', '.')
.option('-d, --max-depth <number>', 'Maximum depth of the tree', '-1')
.option('-f, --format <type>', 'Output format (text|json|markdown)', 'text')
.option('-e, --exclude <patterns...>', 'Additional exclude patterns', [])
.option('-s, --show-size', 'Show file sizes', false)
.option('--show-date', 'Show modification dates', false)
.option('-a, --show-hidden', 'Show hidden files and directories', false)
.option('-D, --dirs-only', 'Show only directories', false)
.option('--no-color', 'Disable colored output')
.option('-o, --output <file>', 'Output to file instead of stdout')
.action(async (targetPath, options) => {
try {
// 验证目标路径
const resolvedPath = path.resolve(targetPath);
if (!fs.existsSync(resolvedPath)) {
console.error(`Error: Path "${resolvedPath}" does not exist.`);
process.exit(1);
}
const stat = fs.statSync(resolvedPath);
if (!stat.isDirectory()) {
console.error(`Error: Path "${resolvedPath}" is not a directory.`);
process.exit(1);
}
// 构建配置选项
const treeOptions = {
path: resolvedPath,
maxDepth: parseInt(options.maxDepth),
format: options.format,
exclude: options.exclude || [],
includeTypes: options.includeTypes || [],
excludeTypes: options.excludeTypes || [],
ignorePattern: options.ignorePattern
? new RegExp(options.ignorePattern)
: undefined,
showHidden: options.showHidden,
showSize: options.showSize,
showDate: options.showDate,
dirsOnly: options.dirsOnly,
colorize: options.color,
};
// 验证格式选项
if (!['text', 'json', 'markdown'].includes(treeOptions.format)) {
console.error(`Error: Invalid format "${treeOptions.format}". Supported formats: text, json, markdown`);
process.exit(1);
}
// 构建目录树
console.error('Building directory tree...');
const treeBuilder = new tree_builder_1.TreeBuilder(treeOptions);
const { tree, stats } = await treeBuilder.buildTree();
// 格式化输出
const formatter = (0, formatters_1.createFormatter)(treeOptions);
const output = formatter.format(tree, stats);
// 输出结果
if (options.output) {
fs.writeFileSync(options.output, output);
console.error(`Tree structure saved to: ${options.output}`);
}
else {
console.log(output);
}
}
catch (error) {
console.error(`Error: ${error instanceof Error ? error.message : 'Unknown error occurred'}`);
process.exit(1);
}
});
// 添加一些预设命令
program
.command('quick')
.description('Quick tree view with common settings')
.argument('[path]', 'Target directory path', '.')
.option('-d, --max-depth <number>', 'Maximum depth', '3')
.option('-f, --format <type>', 'Output format (text|json|markdown)', 'text')
.option('-e, --exclude <patterns...>', 'Additional exclude patterns', [])
.option('-s, --show-size', 'Show file sizes', false)
.option('--show-date', 'Show modification dates', false)
.option('-a, --show-hidden', 'Show hidden files and directories', false)
.option('-D, --dirs-only', 'Show only directories', false)
.option('--no-color', 'Disable colored output')
.option('-o, --output <file>', 'Output to file instead of stdout')
.action(async (targetPath) => {
const options = program.opts();
const defaultExcludes = [
'node_modules',
'.git',
'dist',
'build',
'.next',
'.nuxt',
];
const quickOptions = {
path: path.resolve(targetPath),
maxDepth: parseInt(options.maxDepth),
format: options.format,
exclude: [...defaultExcludes, ...(options.exclude || [])],
includeTypes: [],
excludeTypes: [],
showHidden: options.showHidden,
showSize: options.showSize,
showDate: options.showDate,
dirsOnly: options.dirsOnly,
colorize: options.color,
};
try {
const treeBuilder = new tree_builder_1.TreeBuilder(quickOptions);
const { tree, stats } = await treeBuilder.buildTree();
const formatter = (0, formatters_1.createFormatter)(quickOptions);
const output = formatter.format(tree, stats);
// 输出结果
if (options.output) {
fs.writeFileSync(options.output, output);
console.error(`Tree structure saved to: ${options.output}`);
}
else {
console.log(output);
}
}
catch (error) {
console.error(`Error: ${error instanceof Error ? error.message : 'Unknown error occurred'}`);
process.exit(1);
}
});
program
.command('dev')
.description('Development-focused tree view (excludes common build/cache directories)')
.argument('[path]', 'Target directory path', '.')
.option('-d, --max-depth <number>', 'Maximum depth')
.option('-f, --format <type>', 'Output format (text|json|markdown)')
.option('-e, --exclude <patterns...>', 'Additional exclude patterns')
.option('-s, --show-size', 'Show file sizes')
.option('--show-date', 'Show modification dates')
.option('-a, --show-hidden', 'Show hidden files and directories')
.option('-D, --dirs-only', 'Show only directories')
.option('--no-color', 'Disable colored output')
.option('-o, --output <file>', 'Output to file instead of stdout')
.action(async (targetPath) => {
const options = program.opts();
const defaultExcludes = [
'node_modules',
'.git',
'dist',
'build',
'.next',
'.nuxt',
'coverage',
'.nyc_output',
'.cache',
'tmp',
'temp',
'*.log',
'.DS_Store',
'Thumbs.db',
];
const devOptions = {
path: path.resolve(targetPath),
maxDepth: options.maxDepth ? parseInt(options.maxDepth) : 4,
format: options.format || 'text',
exclude: [...defaultExcludes, ...(options.exclude || [])],
includeTypes: [],
excludeTypes: [],
showHidden: options.showHidden || false,
showSize: options.showSize || false,
showDate: options.showDate || false,
dirsOnly: options.dirsOnly || false,
colorize: !options.noColor,
};
try {
const treeBuilder = new tree_builder_1.TreeBuilder(devOptions);
const { tree, stats } = await treeBuilder.buildTree();
const formatter = (0, formatters_1.createFormatter)(devOptions);
const output = formatter.format(tree, stats);
// 输出结果
if (options.output) {
fs.writeFileSync(options.output, output);
console.error(`Tree structure saved to: ${options.output}`);
}
else {
console.log(output);
}
}
catch (error) {
console.error(`Error: ${error instanceof Error ? error.message : 'Unknown error occurred'}`);
process.exit(1);
}
});
// 解析命令行参数
program.parse();
//# sourceMappingURL=cli.js.map