fix(fs): Improve fs and stream handling, enhance SmartFile/StreamFile, update tests and CI configs

This commit is contained in:
2025-08-18 00:13:03 +00:00
parent 9b0d89b9ef
commit cd147ca38e
25 changed files with 3003 additions and 1221 deletions

View File

@@ -20,7 +20,10 @@ export class SmartFile extends plugins.smartjson.Smartjson {
* creates a Smartfile from a filePath
* @param filePath
*/
public static async fromFilePath(filePath: string, baseArg: string = process.cwd()) {
public static async fromFilePath(
filePath: string,
baseArg: string = process.cwd(),
) {
filePath = plugins.path.resolve(filePath);
const fileBuffer = fs.toBufferSync(filePath);
const smartfile = new SmartFile({
@@ -34,7 +37,7 @@ export class SmartFile extends plugins.smartjson.Smartjson {
public static async fromBuffer(
filePath: string,
contentBufferArg: Buffer,
baseArg: string = process.cwd()
baseArg: string = process.cwd(),
) {
const smartfile = new SmartFile({
contentBuffer: contentBufferArg,
@@ -49,7 +52,7 @@ export class SmartFile extends plugins.smartjson.Smartjson {
filePath: string,
contentStringArg: string,
encodingArg: 'utf8' | 'binary',
baseArg = process.cwd()
baseArg = process.cwd(),
) {
const smartfile = new SmartFile({
contentBuffer: Buffer.from(contentStringArg, encodingArg),
@@ -73,7 +76,7 @@ export class SmartFile extends plugins.smartjson.Smartjson {
public static async fromStream(
stream: plugins.stream.Readable,
filePath: string,
baseArg: string = process.cwd()
baseArg: string = process.cwd(),
): Promise<SmartFile> {
return new Promise<SmartFile>((resolve, reject) => {
const chunks: Buffer[] = [];
@@ -92,8 +95,12 @@ export class SmartFile extends plugins.smartjson.Smartjson {
}
public static async fromUrl(urlArg: string) {
const response = await plugins.smartrequest.getBinary(urlArg);
const smartfile = await SmartFile.fromBuffer(urlArg, response.body);
const response = await plugins.smartrequest.SmartRequest.create()
.url(urlArg)
.accept('binary')
.get();
const buffer = Buffer.from(await response.arrayBuffer());
const smartfile = await SmartFile.fromBuffer(urlArg, buffer);
return smartfile;
}
@@ -159,7 +166,10 @@ export class SmartFile extends plugins.smartjson.Smartjson {
* set contents from string
* @param contentString
*/
public setContentsFromString(contentString: string, encodingArg: 'utf8' | 'binary' = 'utf8') {
public setContentsFromString(
contentString: string,
encodingArg: 'utf8' | 'binary' = 'utf8',
) {
this.contents = Buffer.from(contentString, encodingArg);
}
@@ -169,7 +179,10 @@ export class SmartFile extends plugins.smartjson.Smartjson {
* - no argument write to exactly where the file was picked up
*/
public async write() {
let writePath = plugins.smartpath.transform.makeAbsolute(this.path, this.base);
let writePath = plugins.smartpath.transform.makeAbsolute(
this.path,
this.base,
);
console.log(`writing to ${writePath}`);
await memory.toFs(this.contentBuffer, writePath);
}
@@ -202,7 +215,9 @@ export class SmartFile extends plugins.smartjson.Smartjson {
* read file from disk
*/
public async read() {
this.contentBuffer = await fs.toBuffer(plugins.path.join(this.base, this.path));
this.contentBuffer = await fs.toBuffer(
plugins.path.join(this.base, this.path),
);
}
/**
@@ -220,7 +235,10 @@ export class SmartFile extends plugins.smartjson.Smartjson {
* @param writeToDisk (optional) If true, also renames the file on the disk.
* @returns The updated file path after renaming.
*/
public async rename(newName: string, writeToDisk: boolean = false): Promise<string> {
public async rename(
newName: string,
writeToDisk: boolean = false,
): Promise<string> {
// Validate the new name
if (!newName || typeof newName !== 'string') {
throw new Error('Invalid new name provided.');
@@ -238,8 +256,14 @@ export class SmartFile extends plugins.smartjson.Smartjson {
// Optionally write the renamed file to disk
if (writeToDisk) {
const oldAbsolutePath = plugins.smartpath.transform.makeAbsolute(oldFilePath, this.base);
const newAbsolutePath = plugins.smartpath.transform.makeAbsolute(newFilePath, this.base);
const oldAbsolutePath = plugins.smartpath.transform.makeAbsolute(
oldFilePath,
this.base,
);
const newAbsolutePath = plugins.smartpath.transform.makeAbsolute(
newFilePath,
this.base,
);
// Rename the file on disk
await plugins.fsExtra.rename(oldAbsolutePath, newAbsolutePath);
@@ -310,8 +334,12 @@ export class SmartFile extends plugins.smartjson.Smartjson {
public async getHash(typeArg: 'path' | 'content' | 'all' = 'all') {
const pathHash = await plugins.smarthash.sha256FromString(this.path);
const contentHash = await plugins.smarthash.sha256FromBuffer(this.contentBuffer);
const combinedHash = await plugins.smarthash.sha256FromString(pathHash + contentHash);
const contentHash = await plugins.smarthash.sha256FromBuffer(
this.contentBuffer,
);
const combinedHash = await plugins.smarthash.sha256FromString(
pathHash + contentHash,
);
switch (typeArg) {
case 'path':
return pathHash;
@@ -329,7 +357,9 @@ export class SmartFile extends plugins.smartjson.Smartjson {
this.path = this.path.replace(new RegExp(oldFileName + '$'), fileNameArg);
}
public async editContentAsString(editFuncArg: (fileStringArg: string) => Promise<string>) {
public async editContentAsString(
editFuncArg: (fileStringArg: string) => Promise<string>,
) {
const newFileString = await editFuncArg(this.contentBuffer.toString());
this.contentBuffer = Buffer.from(newFileString);
}