BREAKING(structure): modernize internal structure and support unpacking
This commit is contained in:
144
ts/mod_fs/classes.fshelpers.ts
Normal file
144
ts/mod_fs/classes.fshelpers.ts
Normal file
@@ -0,0 +1,144 @@
|
||||
import * as fs from 'fs';
|
||||
import * as path from 'path';
|
||||
import * as smartfsModule from '@push.rocks/smartfs';
|
||||
|
||||
// Create a smartfs instance with Node.js provider
|
||||
const smartfs = new smartfsModule.SmartFs(new smartfsModule.SmartFsProviderNode());
|
||||
|
||||
/**
|
||||
* FsHelpers provides filesystem utility methods for tsbuild.
|
||||
* All methods are static for convenience.
|
||||
*/
|
||||
export class FsHelpers {
|
||||
/**
|
||||
* The smartfs instance for filesystem operations
|
||||
*/
|
||||
public static readonly smartfs = smartfs;
|
||||
|
||||
/**
|
||||
* List files matching a glob pattern like './ts/**\/*.ts'
|
||||
* Parses the pattern to extract base directory and filter pattern
|
||||
*/
|
||||
public static async listFilesWithGlob(basePath: string, globPattern: string): Promise<string[]> {
|
||||
// Remove leading ./ if present
|
||||
const pattern = globPattern.replace(/^\.\//, '');
|
||||
|
||||
// Find the first directory part before any glob characters
|
||||
const globChars = ['*', '?', '{', '['];
|
||||
let baseDir = basePath;
|
||||
|
||||
// Find where the glob pattern starts
|
||||
const parts = pattern.split('/');
|
||||
const staticParts: string[] = [];
|
||||
const filterParts: string[] = [];
|
||||
let foundGlob = false;
|
||||
|
||||
for (const part of parts) {
|
||||
if (!foundGlob && !globChars.some(c => part.includes(c))) {
|
||||
staticParts.push(part);
|
||||
} else {
|
||||
foundGlob = true;
|
||||
filterParts.push(part);
|
||||
}
|
||||
}
|
||||
|
||||
// Build the base directory
|
||||
if (staticParts.length > 0) {
|
||||
baseDir = path.join(basePath, ...staticParts);
|
||||
}
|
||||
|
||||
// Build the filter pattern (just the filename part, ignoring ** for directories)
|
||||
// The recursive() handles the ** part
|
||||
const fileFilter = filterParts[filterParts.length - 1] || '*';
|
||||
|
||||
// Check if we need recursive search
|
||||
const needsRecursive = filterParts.some(p => p === '**' || p.includes('**'));
|
||||
|
||||
let dirBuilder = smartfs.directory(baseDir);
|
||||
if (needsRecursive) {
|
||||
dirBuilder = dirBuilder.recursive();
|
||||
}
|
||||
|
||||
try {
|
||||
const entries = await dirBuilder.filter(fileFilter).list();
|
||||
return entries.filter(e => e.isFile).map(e => e.path);
|
||||
} catch {
|
||||
// Directory doesn't exist or other error
|
||||
return [];
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Extract source folder name from a glob pattern
|
||||
* './ts_core/**\/*.ts' → 'ts_core'
|
||||
* 'ts_foo/**\/*.ts' → 'ts_foo'
|
||||
*/
|
||||
public static extractSourceFolder(pattern: string): string | null {
|
||||
const match = pattern.match(/^\.?\/?([^\/\*]+)/);
|
||||
return match ? match[1] : null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the current working directory
|
||||
*/
|
||||
public static getCwd(): string {
|
||||
return process.cwd();
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the package directory (where package.json is located)
|
||||
*/
|
||||
public static getPackageDir(): string {
|
||||
return path.resolve(__dirname, '../../');
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if a file exists
|
||||
*/
|
||||
public static async fileExists(filePath: string): Promise<boolean> {
|
||||
return smartfs.file(filePath).exists();
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if a directory exists
|
||||
*/
|
||||
public static async directoryExists(dirPath: string): Promise<boolean> {
|
||||
return smartfs.directory(dirPath).exists();
|
||||
}
|
||||
|
||||
/**
|
||||
* Read a JSON file and parse it
|
||||
*/
|
||||
public static readJsonSync<T = any>(filePath: string): T {
|
||||
const content = fs.readFileSync(filePath, 'utf8');
|
||||
return JSON.parse(content);
|
||||
}
|
||||
|
||||
/**
|
||||
* List directory contents
|
||||
*/
|
||||
public static async listDirectory(dirPath: string) {
|
||||
return smartfs.directory(dirPath).list();
|
||||
}
|
||||
|
||||
/**
|
||||
* Remove a directory recursively
|
||||
*/
|
||||
public static async removeDirectory(dirPath: string): Promise<void> {
|
||||
await fs.promises.rm(dirPath, { recursive: true });
|
||||
}
|
||||
|
||||
/**
|
||||
* Move/rename a file or directory
|
||||
*/
|
||||
public static async move(src: string, dest: string): Promise<void> {
|
||||
await fs.promises.rename(src, dest);
|
||||
}
|
||||
|
||||
/**
|
||||
* Remove an empty directory
|
||||
*/
|
||||
public static async removeEmptyDirectory(dirPath: string): Promise<void> {
|
||||
await fs.promises.rmdir(dirPath);
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user