@maxax/x-builder-files
v1.0.0
Published
一个功能完善的文件系统遍历工具库,提供文件的读取、写入、复制、删除等操作。
Readme
@maxax/x-builder-files
一个功能完善的文件系统遍历工具库,提供文件的读取、写入、复制、删除等操作。
安装
pnpm install @maxax/x-builder-files使用
ESM(推荐)
import {
FileTraversalReader,
FileTraversalWriter,
DEFAULT_TRAVERSAL_OPTIONS,
} from "@maxax/x-builder-files";CommonJS
const {
FileTraversalReader,
FileTraversalWriter,
DEFAULT_TRAVERSAL_OPTIONS,
} = require("@maxax/x-builder-files");开发
# 构建(使用 tsup)
pnpm build
# 监听模式(自动重新构建)
pnpm dev
# 清理构建产物
pnpm clean构建说明
本项目使用 tsup 进行构建,同时支持 ESM 和 CommonJS 两种格式:
- ✅ 源代码中无需使用
.js扩展名 - ✅ 打包后的代码体积更小,加载更快
- ✅ 自动处理模块依赖关系
- ✅ 生成完整的类型定义文件
- ✅ 兼容 NestJS、Express 等 CommonJS 项目
- ✅ 兼容 Vite、ESM 等现代构建工具
构建产物:
dist/index.js- ESM 格式dist/index.cjs- CommonJS 格式dist/index.d.ts- ESM 类型定义dist/index.d.cts- CommonJS 类型定义
API
FileTraversalReader(文件读取)
traverse(options) - 遍历目录
遍历指定目录,返回文件信息集合。
import { FileTraversalReader } from "@maxax/x-builder-files";
const files = await FileTraversalReader.traverse({
baseDir: "/path/to/dir",
includeFolders: true,
readContent: true,
pattern: "**/*.ts",
ignore: ["**/node_modules/**"],
dot: false,
deep: Infinity,
encoding: "utf-8",
});
// 返回的文件信息
files.forEach((file) => {
console.log({
isDirectory: file.isDirectory, // 是否是文件夹
fileType: file.fileType, // 文件类型: 'file' | 'directory' | 'symlink' | 'unknown'
fileName: file.fileName, // 文件名
fileSize: file.fileSize, // 文件大小(字节)
relativePath: file.relativePath, // 文件相对路径
absolutePath: file.absolutePath, // 文件绝对路径
fileExtension: file.fileExtension, // 文件后缀
fileContent: file.fileContent, // 文件内容
lastModified: file.lastModified, // 最后修改时间
createdAt: file.createdAt, // 创建时间
});
});参数说明:
| 参数 | 类型 | 默认值 | 说明 | | -------------- | ------------------ | ------------------------------------ | ---------------- | | baseDir | string | - | 基础目录(必填) | | includeFolders | boolean | false | 是否包含文件夹 | | readContent | boolean | true | 是否读取文件内容 | | pattern | string | string[] | '*/' | glob 匹配模式 | | ignore | string[] | ['/node_modules/', '/.git/'] | 忽略的模式 | | dot | boolean | true | 是否包含隐藏文件 | | deep | number | Infinity | 遍历深度 | | encoding | BufferEncoding | 'utf-8' | 文件编码 |
提示:默认参数值可以从 DEFAULT_TRAVERSAL_OPTIONS 常量中获取:
import { DEFAULT_TRAVERSAL_OPTIONS } from "@maxax/x-builder-files";
console.log(DEFAULT_TRAVERSAL_OPTIONS);
// {
// includeFolders: false,
// readContent: true,
// pattern: '**/*',
// ignore: ['**/node_modules/**', '**/.git/**'],
// dot: false,
// deep: Infinity,
// encoding: 'utf-8'
// }getFileInfo(options) - 获取文件信息
获取单个文件的详细信息(异步方法)。
const fileInfo = await FileTraversalReader.getFileInfo({
filePath: "/path/to/file.ts",
baseDir: "/path/to",
readContent: true,
encoding: "utf-8",
});readFile(filePath, encoding) - 读取文件内容
读取文件内容为字符串。
const content = FileTraversalReader.readFile("/path/to/file.ts", "utf-8");readFileBuffer(filePath) - 读取文件为 Buffer
读取文件内容为 Buffer。
const buffer = FileTraversalReader.readFileBuffer("/path/to/image.png");exists(path) - 检查路径是否存在
const exists = FileTraversalReader.exists("/path/to/file");isDirectory(path) - 检查是否是目录
const isDir = FileTraversalReader.isDirectory("/path/to/dir");isFile(path) - 检查是否是文件
const isFile = FileTraversalReader.isFile("/path/to/file");getFileSize(filePath) - 获取文件大小
const size = FileTraversalReader.getFileSize("/path/to/file");getStats(filePath) - 获取文件统计信息
const stats = FileTraversalReader.getStats("/path/to/file");FileTraversalWriter(文件写入)
writeFile(filePath, content, options) - 写入文件
写入文件内容。
import { FileTraversalWriter } from "@maxax/x-builder-files";
FileTraversalWriter.writeFile("/path/to/file.ts", 'console.log("Hello")', {
encoding: "utf-8",
createDir: true, // 自动创建目录
overwrite: true, // 允许覆盖
});writeFileBuffer(filePath, buffer, options) - 写入 Buffer
const buffer = Buffer.from("Hello");
FileTraversalWriter.writeFileBuffer("/path/to/file", buffer, {
createDir: true,
});appendFile(filePath, content, encoding) - 追加内容
FileTraversalWriter.appendFile("/path/to/log.txt", "New log entry\n", "utf-8");createDirectory(dirPath, recursive) - 创建目录
FileTraversalWriter.createDirectory("/path/to/new/dir", true);ensureDirectory(dirPath) - 确保目录存在
如果目录不存在则创建。
FileTraversalWriter.ensureDirectory("/path/to/dir");delete(path, options) - 删除文件或目录
FileTraversalWriter.delete("/path/to/file", {
recursive: true,
force: true,
});deleteFile(filePath, force) - 删除文件
FileTraversalWriter.deleteFile("/path/to/file.ts", true);deleteDirectory(dirPath, recursive, force) - 删除目录
FileTraversalWriter.deleteDirectory("/path/to/dir", true, true);copyFile(sourcePath, destPath, options) - 复制文件
FileTraversalWriter.copyFile("/path/to/source.ts", "/path/to/dest.ts", {
overwrite: true,
filter: (src) => !src.includes("test"),
});copyDirectory(sourcePath, destPath, options) - 复制目录
await FileTraversalWriter.copyDirectory("/path/to/source", "/path/to/dest", {
overwrite: true,
filter: (src) => !src.includes("node_modules"),
});move(sourcePath, destPath, overwrite) - 移动文件或目录
FileTraversalWriter.move("/path/to/old", "/path/to/new", true);rename(oldPath, newPath, overwrite) - 重命名
FileTraversalWriter.rename("/path/to/old.ts", "/path/to/new.ts", false);writeBatch(files, options) - 批量写入文件
FileTraversalWriter.writeBatch(
[
{ path: "/path/to/file1.ts", content: "content1" },
{ path: "/path/to/file2.ts", content: "content2" },
],
{ createDir: true },
);clearDirectory(dirPath) - 清空目录
删除目录下所有内容,但保留目录本身。
await FileTraversalWriter.clearDirectory("/path/to/dir");使用示例
示例 1:遍历项目文件
import { FileTraversalReader } from "@maxax/x-builder-files";
// 遍历所有 TypeScript 文件
const tsFiles = await FileTraversalReader.traverse({
baseDir: "./src",
pattern: "**/*.ts",
ignore: ["**/*.spec.ts", "**/*.test.ts"],
readContent: true,
});
console.log(`找到 ${tsFiles.length} 个 TypeScript 文件`);
// 分析文件
tsFiles.forEach((file) => {
console.log(`文件: ${file.relativePath}`);
console.log(`大小: ${(file.fileSize / 1024).toFixed(2)} KB`);
console.log(`类型: ${file.fileType}`); // 'file', 'directory', 'symlink', 'unknown'
console.log(`扩展名: ${file.fileExtension}`); // .ts
});示例 2:复制项目模板
import { FileTraversalWriter } from "@maxax/x-builder-files";
// 复制项目模板
await FileTraversalWriter.copyDirectory(
"./templates/vue-project",
"./new-project",
{
overwrite: false,
filter: (src) => {
// 排除 node_modules 和 .git
return !src.includes("node_modules") && !src.includes(".git");
},
},
);示例 3:批量处理文件
import {
FileTraversalReader,
FileTraversalWriter,
} from "@maxax/x-builder-files";
// 读取所有 Vue 文件
const vueFiles = await FileTraversalReader.traverse({
baseDir: "./src",
pattern: "**/*.vue",
readContent: true,
});
// 处理并写入
const processedFiles = vueFiles.map((file) => ({
path: file.absolutePath,
content: file.fileContent.replace(/console\.log/g, "// console.log"),
}));
FileTraversalWriter.writeBatch(processedFiles, { overwrite: true });示例 4:文件统计
import { FileTraversalReader } from "@maxax/x-builder-files";
const files = await FileTraversalReader.traverse({
baseDir: "./src",
includeFolders: false,
readContent: false, // 不读取内容以提高性能
});
// 统计各文件类型数量
const stats = files.reduce(
(acc, file) => {
const type = file.fileType;
acc[type] = (acc[type] || 0) + 1;
return acc;
},
{} as Record<string, number>,
);
console.log("文件类型统计:", stats);
// 例如: { 'file': 100, 'directory': 10, 'symlink': 2 }
// 计算总大小
const totalSize = files.reduce((sum, file) => sum + file.fileSize, 0);
console.log(`总大小: ${(totalSize / 1024 / 1024).toFixed(2)} MB`);示例 5:清理构建文件
import { FileTraversalWriter } from "@maxax/x-builder-files";
// 清理 dist 目录
await FileTraversalWriter.clearDirectory("./dist");
// 删除所有 .map 文件
const mapFiles = await FileTraversalReader.traverse({
baseDir: "./dist",
pattern: "**/*.map",
readContent: false,
});
mapFiles.forEach((file) => {
FileTraversalWriter.deleteFile(file.absolutePath, true);
});MIME 类型识别
文件类型说明
FileInfo 接口中的 fileType 字段用于标识文件系统对象的类型:
'file'- 普通文件'directory'- 目录/文件夹'symlink'- 符号链接'unknown'- 未知类型
这个字段基于文件系统的 stats 信息判断,与文件扩展名无关。如果需要根据文件内容或扩展名判断具体的文件格式(如 TypeScript、图片等),请使用 fileExtension 字段。
注意事项
- 性能优化:如果只需要文件信息而不需要内容,设置
readContent: false可以大幅提升性能 - 大文件处理:对于大文件,建议使用
readFileBuffer或流式处理 - 异步操作:
traverse和copyDirectory等方法是异步的,需要使用await - 路径处理:所有路径都会被解析为绝对路径,支持相对路径输入
- 错误处理:建议使用 try-catch 包裹操作以处理可能的错误
License
MIT
