@zenfs/core
Advanced tools
Comparing version
@@ -47,3 +47,3 @@ /// <reference types="node" resolution-mode="require"/> | ||
*/ | ||
static fromBuffer(buffer: Buffer, i?: number): ApiError; | ||
static Derserialize(data: ArrayBufferLike | ArrayBufferView, i?: number): ApiError; | ||
static FileError(code: ErrorCode, p: string): ApiError; | ||
@@ -81,3 +81,3 @@ static EACCES(path: string): ApiError; | ||
*/ | ||
writeToBuffer(buffer?: Buffer, i?: number): Buffer; | ||
serialize(data?: ArrayBufferLike | ArrayBufferView, i?: number): Uint8Array; | ||
/** | ||
@@ -84,0 +84,0 @@ * The size of the API error in buffer-form in bytes. |
@@ -1,2 +0,2 @@ | ||
import { Buffer } from 'buffer'; | ||
import { decode, encode } from './utils.js'; | ||
/** | ||
@@ -59,4 +59,6 @@ * Standard libc error codes. More will be added to this enum and ErrorStrings as they are | ||
*/ | ||
static fromBuffer(buffer, i = 0) { | ||
return ApiError.fromJSON(JSON.parse(buffer.toString('utf8', i + 4, i + 4 + buffer.readUInt32LE(i)))); | ||
static Derserialize(data, i = 0) { | ||
const view = new DataView('buffer' in data ? data.buffer : data); | ||
const dataText = decode(view.buffer.slice(i + 4, i + 4 + view.getUint32(i, true))); | ||
return ApiError.fromJSON(JSON.parse(dataText)); | ||
} | ||
@@ -124,5 +126,7 @@ static FileError(code, p) { | ||
*/ | ||
writeToBuffer(buffer = Buffer.alloc(this.bufferSize()), i = 0) { | ||
const bytesWritten = buffer.write(JSON.stringify(this.toJSON()), i + 4); | ||
buffer.writeUInt32LE(bytesWritten, i); | ||
serialize(data = new Uint8Array(this.bufferSize()), i = 0) { | ||
const view = new DataView('buffer' in data ? data.buffer : data), buffer = new Uint8Array(view.buffer); | ||
const newData = encode(JSON.stringify(this.toJSON())); | ||
buffer.set(newData); | ||
view.setUint32(i, newData.byteLength, true); | ||
return buffer; | ||
@@ -135,4 +139,4 @@ } | ||
// 4 bytes for string length. | ||
return 4 + Buffer.byteLength(JSON.stringify(this.toJSON())); | ||
return 4 + JSON.stringify(this.toJSON()).length; | ||
} | ||
} |
@@ -1,2 +0,1 @@ | ||
/// <reference types="node" resolution-mode="require"/> | ||
import { Cred } from '../cred.js'; | ||
@@ -36,3 +35,3 @@ import { PreloadFile, File, FileFlag } from '../file.js'; | ||
*/ | ||
get(key: string): Promise<Buffer>; | ||
get(key: string): Promise<Uint8Array>; | ||
} | ||
@@ -51,3 +50,3 @@ /** | ||
*/ | ||
put(key: string, data: Buffer, overwrite: boolean): Promise<boolean>; | ||
put(key: string, data: Uint8Array, overwrite: boolean): Promise<boolean>; | ||
/** | ||
@@ -68,3 +67,3 @@ * Deletes the data at the given key. | ||
export declare class AsyncKeyValueFile extends PreloadFile<AsyncKeyValueFileSystem> implements File { | ||
constructor(_fs: AsyncKeyValueFileSystem, _path: string, _flag: FileFlag, _stat: Stats, contents?: Buffer); | ||
constructor(_fs: AsyncKeyValueFileSystem, _path: string, _flag: FileFlag, _stat: Stats, contents?: Uint8Array); | ||
sync(): Promise<void>; | ||
@@ -110,3 +109,3 @@ close(): Promise<void>; | ||
chown(p: string, new_uid: number, new_gid: number, cred: Cred): Promise<void>; | ||
_sync(p: string, data: Buffer, stats: Stats): Promise<void>; | ||
_sync(p: string, data: Uint8Array, stats: Stats): Promise<void>; | ||
/** | ||
@@ -113,0 +112,0 @@ * Checks if the root directory exists. Creates it if it doesn't. |
@@ -17,3 +17,3 @@ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) { | ||
import { FileType } from '../stats.js'; | ||
import { ROOT_NODE_ID, randomUUID, getEmptyDirNode } from '../utils.js'; | ||
import { ROOT_NODE_ID, randomUUID, encode } from '../utils.js'; | ||
class LRUNode { | ||
@@ -259,4 +259,4 @@ constructor(key, value) { | ||
try { | ||
yield tx.put(oldDirNode.id, Buffer.from(JSON.stringify(oldDirList)), true); | ||
yield tx.put(newDirNode.id, Buffer.from(JSON.stringify(newDirList)), true); | ||
yield tx.put(oldDirNode.id, encode(JSON.stringify(oldDirList)), true); | ||
yield tx.put(newDirNode.id, encode(JSON.stringify(newDirList)), true); | ||
} | ||
@@ -289,3 +289,3 @@ catch (e) { | ||
return __awaiter(this, void 0, void 0, function* () { | ||
const tx = this.store.beginTransaction('readwrite'), data = Buffer.alloc(0), newFile = yield this.commitNewFile(tx, p, FileType.FILE, mode, cred, data); | ||
const tx = this.store.beginTransaction('readwrite'), data = new Uint8Array(0), newFile = yield this.commitNewFile(tx, p, FileType.FILE, mode, cred, data); | ||
// Open the file. | ||
@@ -324,3 +324,3 @@ return new AsyncKeyValueFile(this, p, flag, newFile.toStats(), data); | ||
return __awaiter(this, void 0, void 0, function* () { | ||
const tx = this.store.beginTransaction('readwrite'), data = Buffer.from('{}'); | ||
const tx = this.store.beginTransaction('readwrite'), data = encode('{}'); | ||
yield this.commitNewFile(tx, p, FileType.DIRECTORY, mode, cred, data); | ||
@@ -363,3 +363,3 @@ }); | ||
if (inodeChanged) { | ||
yield tx.put(fileInodeId, fileInode.toBuffer(), true); | ||
yield tx.put(fileInodeId, fileInode.serialize(), true); | ||
} | ||
@@ -387,4 +387,4 @@ } | ||
// either. | ||
yield tx.put(dirInode.id, getEmptyDirNode(), false); | ||
yield tx.put(ROOT_NODE_ID, dirInode.toBuffer(), false); | ||
yield tx.put(dirInode.id, encode('{}'), false); | ||
yield tx.put(ROOT_NODE_ID, dirInode.serialize(), false); | ||
yield tx.commit(); | ||
@@ -478,3 +478,3 @@ } | ||
} | ||
return Inode.fromBuffer(data); | ||
return Inode.Deserialize(data); | ||
}); | ||
@@ -563,6 +563,6 @@ } | ||
// Commit file node. | ||
const fileNodeId = yield this.addNewNode(tx, fileNode.toBuffer()); | ||
const fileNodeId = yield this.addNewNode(tx, fileNode.serialize()); | ||
// Update and commit parent directory listing. | ||
dirListing[fname] = fileNodeId; | ||
yield tx.put(parentNode.id, Buffer.from(JSON.stringify(dirListing)), true); | ||
yield tx.put(parentNode.id, encode(JSON.stringify(dirListing)), true); | ||
yield tx.commit(); | ||
@@ -618,3 +618,3 @@ return fileNode; | ||
// Update directory listing. | ||
yield tx.put(parentNode.id, Buffer.from(JSON.stringify(parentListing)), true); | ||
yield tx.put(parentNode.id, encode(JSON.stringify(parentListing)), true); | ||
} | ||
@@ -621,0 +621,0 @@ catch (e) { |
@@ -1,2 +0,1 @@ | ||
/// <reference types="node" resolution-mode="require"/> | ||
import { SyncKeyValueStore, SimpleSyncStore, SyncKeyValueRWTransaction, SyncKeyValueFileSystem } from './SyncStore.js'; | ||
@@ -12,4 +11,4 @@ import { type BackendOptions } from './backend.js'; | ||
beginTransaction(type: string): SyncKeyValueRWTransaction; | ||
get(key: string): Buffer; | ||
put(key: string, data: Buffer, overwrite: boolean): boolean; | ||
get(key: string): Uint8Array; | ||
put(key: string, data: Uint8Array, overwrite: boolean): boolean; | ||
del(key: string): void; | ||
@@ -16,0 +15,0 @@ } |
@@ -1,2 +0,1 @@ | ||
/// <reference types="node" resolution-mode="require"/> | ||
import { Cred } from '../cred.js'; | ||
@@ -38,3 +37,3 @@ import { FileFlag, PreloadFile } from '../file.js'; | ||
*/ | ||
get(key: string): Buffer | undefined; | ||
get(key: string): Uint8Array | undefined; | ||
} | ||
@@ -53,3 +52,3 @@ /** | ||
*/ | ||
put(key: string, data: Buffer, overwrite: boolean): boolean; | ||
put(key: string, data: Uint8Array, overwrite: boolean): boolean; | ||
/** | ||
@@ -74,4 +73,4 @@ * Deletes the data at the given key. | ||
export interface SimpleSyncStore { | ||
get(key: string): Buffer | undefined; | ||
put(key: string, data: Buffer, overwrite: boolean): boolean; | ||
get(key: string): Uint8Array | undefined; | ||
put(key: string, data: Uint8Array, overwrite: boolean): boolean; | ||
del(key: string): void; | ||
@@ -94,4 +93,4 @@ } | ||
constructor(store: SimpleSyncStore); | ||
get(key: string): Buffer | undefined; | ||
put(key: string, data: Buffer, overwrite: boolean): boolean; | ||
get(key: string): Uint8Array | undefined; | ||
put(key: string, data: Uint8Array, overwrite: boolean): boolean; | ||
del(key: string): void; | ||
@@ -134,3 +133,3 @@ commit(): void; | ||
export declare class SyncKeyValueFile extends PreloadFile<SyncKeyValueFileSystem> { | ||
constructor(_fs: SyncKeyValueFileSystem, _path: string, _flag: FileFlag, _stat: Stats, contents?: Buffer); | ||
constructor(_fs: SyncKeyValueFileSystem, _path: string, _flag: FileFlag, _stat: Stats, contents?: Uint8Array); | ||
syncSync(): void; | ||
@@ -172,3 +171,3 @@ closeSync(): void; | ||
chownSync(p: string, new_uid: number, new_gid: number, cred: Cred): void; | ||
_syncSync(p: string, data: Buffer, stats: Stats): void; | ||
_syncSync(p: string, data: Uint8Array, stats: Stats): void; | ||
/** | ||
@@ -175,0 +174,0 @@ * Checks if the root directory exists. Creates it if it doesn't. |
@@ -8,3 +8,3 @@ import { dirname, basename, join, resolve, sep } from '../emulation/path.js'; | ||
import { FileType } from '../stats.js'; | ||
import { randomUUID, getEmptyDirNode, ROOT_NODE_ID } from '../utils.js'; | ||
import { encode, randomUUID, ROOT_NODE_ID } from '../utils.js'; | ||
/** | ||
@@ -198,4 +198,4 @@ * A simple RW transaction for simple synchronous key-value stores. | ||
try { | ||
tx.put(oldDirNode.id, Buffer.from(JSON.stringify(oldDirList)), true); | ||
tx.put(newDirNode.id, Buffer.from(JSON.stringify(newDirList)), true); | ||
tx.put(oldDirNode.id, encode(JSON.stringify(oldDirList)), true); | ||
tx.put(newDirNode.id, encode(JSON.stringify(newDirList)), true); | ||
} | ||
@@ -217,3 +217,3 @@ catch (e) { | ||
createFileSync(p, flag, mode, cred) { | ||
const tx = this.store.beginTransaction('readwrite'), data = Buffer.alloc(0), newFile = this.commitNewFile(tx, p, FileType.FILE, mode, cred, data); | ||
const tx = this.store.beginTransaction('readwrite'), data = new Uint8Array(0), newFile = this.commitNewFile(tx, p, FileType.FILE, mode, cred, data); | ||
// Open the file. | ||
@@ -245,3 +245,3 @@ return new SyncKeyValueFile(this, p, flag, newFile.toStats(), data); | ||
mkdirSync(p, mode, cred) { | ||
const tx = this.store.beginTransaction('readwrite'), data = Buffer.from('{}'); | ||
const tx = this.store.beginTransaction('readwrite'), data = encode('{}'); | ||
this.commitNewFile(tx, p, FileType.DIRECTORY, mode, cred, data); | ||
@@ -276,3 +276,3 @@ } | ||
if (inodeChanged) { | ||
tx.put(fileInodeId, fileInode.toBuffer(), true); | ||
tx.put(fileInodeId, fileInode.serialize(), true); | ||
} | ||
@@ -298,4 +298,4 @@ } | ||
// either. | ||
tx.put(dirInode.id, getEmptyDirNode(), false); | ||
tx.put(ROOT_NODE_ID, dirInode.toBuffer(), false); | ||
tx.put(dirInode.id, encode('{}'), false); | ||
tx.put(ROOT_NODE_ID, dirInode.serialize(), false); | ||
tx.commit(); | ||
@@ -362,3 +362,3 @@ } | ||
} | ||
return Inode.fromBuffer(inode); | ||
return Inode.Deserialize(inode); | ||
} | ||
@@ -431,6 +431,6 @@ /** | ||
// Commit file node. | ||
const fileNodeId = this.addNewNode(tx, fileNode.toBuffer()); | ||
const fileNodeId = this.addNewNode(tx, fileNode.serialize()); | ||
// Update and commit parent directory listing. | ||
dirListing[fname] = fileNodeId; | ||
tx.put(parentNode.id, Buffer.from(JSON.stringify(dirListing)), true); | ||
tx.put(parentNode.id, encode(JSON.stringify(dirListing)), true); | ||
} | ||
@@ -475,3 +475,3 @@ catch (e) { | ||
// Update directory listing. | ||
tx.put(parentNode.id, Buffer.from(JSON.stringify(parentListing)), true); | ||
tx.put(parentNode.id, encode(JSON.stringify(parentListing)), true); | ||
} | ||
@@ -478,0 +478,0 @@ catch (e) { |
@@ -93,6 +93,6 @@ /// <reference types="node" resolution-mode="require"/> | ||
*/ | ||
export declare function readFile(filename: string, cb: BFSCallback<Buffer>): void; | ||
export declare function readFile(filename: string, cb: BFSCallback<Uint8Array>): void; | ||
export declare function readFile(filename: string, options: { | ||
flag?: string; | ||
}, callback?: BFSCallback<Buffer>): void; | ||
}, callback?: BFSCallback<Uint8Array>): void; | ||
export declare function readFile(filename: string, options: { | ||
@@ -192,3 +192,3 @@ encoding: string; | ||
* @param fd | ||
* @param buffer Buffer containing the data to write to | ||
* @param buffer Uint8Array containing the data to write to | ||
* the file. | ||
@@ -202,4 +202,4 @@ * @param offset Offset in the buffer to start reading data from. | ||
*/ | ||
export declare function write(fd: number, buffer: Buffer, offset: number, length: number, cb?: BFSThreeArgCallback<number, Buffer>): void; | ||
export declare function write(fd: number, buffer: Buffer, offset: number, length: number, position: number | null, cb?: BFSThreeArgCallback<number, Buffer>): void; | ||
export declare function write(fd: number, buffer: Uint8Array, offset: number, length: number, cb?: BFSThreeArgCallback<number, Uint8Array>): void; | ||
export declare function write(fd: number, buffer: Uint8Array, offset: number, length: number, position: number | null, cb?: BFSThreeArgCallback<number, Uint8Array>): void; | ||
export declare function write(fd: number, data: FileContents, cb?: BFSThreeArgCallback<number, string>): void; | ||
@@ -220,3 +220,3 @@ export declare function write(fd: number, data: FileContents, position: number | null, cb?: BFSThreeArgCallback<number, string>): void; | ||
*/ | ||
export declare function read(fd: number, buffer: Buffer, offset: number, length: number, position?: number, cb?: BFSThreeArgCallback<number, Buffer>): void; | ||
export declare function read(fd: number, buffer: Uint8Array, offset: number, length: number, position?: number, cb?: BFSThreeArgCallback<number, Uint8Array>): void; | ||
/** | ||
@@ -223,0 +223,0 @@ * Asynchronous `fchown`. |
@@ -5,2 +5,3 @@ import { ApiError, ErrorCode } from '../ApiError.js'; | ||
import { R_OK } from './constants.js'; | ||
import { decode, encode } from '../utils.js'; | ||
/** | ||
@@ -171,3 +172,3 @@ * Asynchronous rename. No arguments other than a possible exception are given | ||
} | ||
buffer = Buffer.from(arg2, encoding); | ||
buffer = encode(arg2); | ||
offset = 0; | ||
@@ -178,3 +179,3 @@ length = buffer.length; | ||
.write(fd, buffer, offset, length, position) | ||
.then(bytesWritten => _cb(null, bytesWritten, buffer.toString(encoding))) | ||
.then(bytesWritten => _cb(null, bytesWritten, decode(buffer))) | ||
.catch(_cb); | ||
@@ -181,0 +182,0 @@ } |
@@ -58,7 +58,7 @@ /// <reference types="node" resolution-mode="require"/> | ||
* @option options [String] flag Defaults to `'r'`. | ||
* @return [String | ZenFS.node.Buffer] | ||
* @return [String | ZenFS.node.Uint8Array] | ||
*/ | ||
export declare function readFile(filename: string, options?: { | ||
flag?: string; | ||
}): Promise<Buffer>; | ||
}): Promise<Uint8Array>; | ||
export declare function readFile(filename: string, options: { | ||
@@ -148,3 +148,3 @@ encoding: string; | ||
* @param fd | ||
* @param buffer Buffer containing the data to write to | ||
* @param buffer Uint8Array containing the data to write to | ||
* the file. | ||
@@ -157,3 +157,3 @@ * @param offset Offset in the buffer to start reading data from. | ||
*/ | ||
export declare function write(fd: number, buffer: Buffer, offset: number, length: number, position?: number): Promise<number>; | ||
export declare function write(fd: number, buffer: Uint8Array, offset: number, length: number, position?: number): Promise<number>; | ||
export declare function write(fd: number, data: string, position?: number | null, encoding?: BufferEncoding): Promise<number>; | ||
@@ -172,5 +172,5 @@ /** | ||
*/ | ||
export declare function read(fd: number, buffer: Buffer, offset: number, length: number, position?: number): Promise<{ | ||
export declare function read(fd: number, buffer: Uint8Array, offset: number, length: number, position?: number): Promise<{ | ||
bytesRead: number; | ||
buffer: Buffer; | ||
buffer: Uint8Array; | ||
}>; | ||
@@ -177,0 +177,0 @@ /** |
@@ -15,2 +15,3 @@ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) { | ||
import { normalizePath, normalizeMode, getFdForFile, normalizeOptions, fd2file, fdMap, normalizeTime, cred, nop, resolveFS, fixError, mounts } from './shared.js'; | ||
import { encode } from '../utils.js'; | ||
/** | ||
@@ -238,3 +239,3 @@ * Utility for FS ops. It handles | ||
offset = 0; | ||
buffer = Buffer.from(arg2, encoding); | ||
buffer = encode(arg2); | ||
length = buffer.length; | ||
@@ -241,0 +242,0 @@ } |
@@ -57,7 +57,7 @@ /// <reference types="node" resolution-mode="require"/> | ||
* @option options [String] flag Defaults to `'r'`. | ||
* @return [String | ZenFS.node.Buffer] | ||
* @return [String | ZenFS.node.Uint8Array] | ||
*/ | ||
export declare function readFileSync(filename: string, options?: { | ||
flag?: string; | ||
}): Buffer; | ||
}): Uint8Array; | ||
export declare function readFileSync(filename: string, options: { | ||
@@ -142,3 +142,3 @@ encoding: string; | ||
* @param fd | ||
* @param buffer Buffer containing the data to write to | ||
* @param buffer Uint8Array containing the data to write to | ||
* the file. | ||
@@ -151,3 +151,3 @@ * @param offset Offset in the buffer to start reading data from. | ||
*/ | ||
export declare function writeSync(fd: number, buffer: Buffer, offset: number, length: number, position?: number | null): number; | ||
export declare function writeSync(fd: number, buffer: Uint8Array, offset: number, length: number, position?: number | null): number; | ||
export declare function writeSync(fd: number, data: string, position?: number | null, encoding?: BufferEncoding): number; | ||
@@ -166,4 +166,4 @@ /** | ||
*/ | ||
export declare function readSync(fd: number, buffer: Buffer, opts?: ReadSyncOptions): number; | ||
export declare function readSync(fd: number, buffer: Buffer, offset: number, length: number, position?: number): number; | ||
export declare function readSync(fd: number, buffer: Uint8Array, opts?: ReadSyncOptions): number; | ||
export declare function readSync(fd: number, buffer: Uint8Array, offset: number, length: number, position?: number): number; | ||
/** | ||
@@ -170,0 +170,0 @@ * Synchronous `fchown`. |
import { ApiError, ErrorCode } from '../ApiError.js'; | ||
import { FileFlag } from '../file.js'; | ||
import { normalizePath, cred, getFdForFile, normalizeMode, normalizeOptions, fdMap, fd2file, normalizeTime, resolveFS, fixError, mounts } from './shared.js'; | ||
import { encode } from '../utils.js'; | ||
function doOp(...[name, resolveSymlinks, path, ...args]) { | ||
@@ -178,3 +179,3 @@ path = normalizePath(path); | ||
offset = 0; | ||
buffer = Buffer.from(arg2, encoding); | ||
buffer = encode(arg2); | ||
length = buffer.length; | ||
@@ -181,0 +182,0 @@ } |
@@ -1,2 +0,1 @@ | ||
/// <reference types="node" resolution-mode="require"/> | ||
import { Stats } from './stats.js'; | ||
@@ -130,3 +129,3 @@ import { FileSystem } from './filesystem.js'; | ||
* without waiting for the callback. | ||
* @param buffer Buffer containing the data to write to | ||
* @param buffer Uint8Array containing the data to write to | ||
* the file. | ||
@@ -140,3 +139,3 @@ * @param offset Offset in the buffer to start reading data from. | ||
*/ | ||
write(buffer: Buffer, offset: number, length: number, position: number | null): Promise<number>; | ||
write(buffer: Uint8Array, offset: number, length: number, position: number | null): Promise<number>; | ||
/** | ||
@@ -146,3 +145,3 @@ * **Core**: Write buffer to the file. | ||
* without waiting for it to return. | ||
* @param buffer Buffer containing the data to write to | ||
* @param buffer Uint8Array containing the data to write to | ||
* the file. | ||
@@ -155,3 +154,3 @@ * @param offset Offset in the buffer to start reading data from. | ||
*/ | ||
writeSync(buffer: Buffer, offset: number, length: number, position: number | null): number; | ||
writeSync(buffer: Uint8Array, offset: number, length: number, position: number | null): number; | ||
/** | ||
@@ -169,5 +168,5 @@ * **Core**: Read data from the file. | ||
*/ | ||
read(buffer: Buffer, offset: number, length: number, position: number | null): Promise<{ | ||
read(buffer: Uint8Array, offset: number, length: number, position: number | null): Promise<{ | ||
bytesRead: number; | ||
buffer: Buffer; | ||
buffer: Uint8Array; | ||
}>; | ||
@@ -183,3 +182,3 @@ /** | ||
*/ | ||
readSync(buffer: Buffer, offset: number, length: number, position: number): number; | ||
readSync(buffer: Uint8Array, offset: number, length: number, position: number): number; | ||
/** | ||
@@ -240,3 +239,3 @@ * **Supplementary**: Asynchronous `datasync`. | ||
* An implementation of the File interface that operates on a file that is | ||
* completely in-memory. PreloadFiles are backed by a Buffer. | ||
* completely in-memory. PreloadFiles are backed by a Uint8Array. | ||
* | ||
@@ -254,3 +253,3 @@ * This is also an abstract class, as it lacks an implementation of 'sync' and | ||
protected _flag: FileFlag; | ||
protected _buffer: Buffer; | ||
protected _buffer: Uint8Array; | ||
protected _dirty: boolean; | ||
@@ -271,7 +270,7 @@ /** | ||
*/ | ||
constructor(_fs: T, _path: string, _flag: FileFlag, _stat: Stats, contents?: Buffer); | ||
constructor(_fs: T, _path: string, _flag: FileFlag, _stat: Stats, contents?: Uint8Array); | ||
/** | ||
* NONSTANDARD: Get the underlying buffer for this file. !!DO NOT MUTATE!! Will mess up dirty tracking. | ||
*/ | ||
getBuffer(): Buffer; | ||
getBuffer(): Uint8Array; | ||
/** | ||
@@ -351,3 +350,3 @@ * NONSTANDARD: Get underlying stats for this file. !!DO NOT MUTATE!! | ||
* without waiting for the callback. | ||
* @param [ZenFS.node.Buffer] buffer Buffer containing the data to write to | ||
* @param [ZenFS.node.Uint8Array] buffer Uint8Array containing the data to write to | ||
* the file. | ||
@@ -359,6 +358,6 @@ * @param [Number] offset Offset in the buffer to start reading data from. | ||
* the current position. | ||
* @param [Function(ZenFS.ApiError, Number, ZenFS.node.Buffer)] | ||
* @param [Function(ZenFS.ApiError, Number, ZenFS.node.Uint8Array)] | ||
* cb The number specifies the number of bytes written into the file. | ||
*/ | ||
write(buffer: Buffer, offset: number, length: number, position: number): Promise<number>; | ||
write(buffer: Uint8Array, offset: number, length: number, position: number): Promise<number>; | ||
/** | ||
@@ -368,3 +367,3 @@ * Write buffer to the file. | ||
* without waiting for the callback. | ||
* @param [ZenFS.node.Buffer] buffer Buffer containing the data to write to | ||
* @param [ZenFS.node.Uint8Array] buffer Uint8Array containing the data to write to | ||
* the file. | ||
@@ -378,6 +377,6 @@ * @param [Number] offset Offset in the buffer to start reading data from. | ||
*/ | ||
writeSync(buffer: Buffer, offset: number, length: number, position: number): number; | ||
writeSync(buffer: Uint8Array, offset: number, length: number, position: number): number; | ||
/** | ||
* Read data from the file. | ||
* @param [ZenFS.node.Buffer] buffer The buffer that the data will be | ||
* @param [ZenFS.node.Uint8Array] buffer The buffer that the data will be | ||
* written to. | ||
@@ -390,12 +389,12 @@ * @param [Number] offset The offset within the buffer where writing will | ||
* position. | ||
* @param [Function(ZenFS.ApiError, Number, ZenFS.node.Buffer)] cb The | ||
* @param [Function(ZenFS.ApiError, Number, ZenFS.node.Uint8Array)] cb The | ||
* number is the number of bytes read | ||
*/ | ||
read(buffer: Buffer, offset: number, length: number, position: number): Promise<{ | ||
read(buffer: Uint8Array, offset: number, length: number, position: number): Promise<{ | ||
bytesRead: number; | ||
buffer: Buffer; | ||
buffer: Uint8Array; | ||
}>; | ||
/** | ||
* Read data from the file. | ||
* @param [ZenFS.node.Buffer] buffer The buffer that the data will be | ||
* @param [ZenFS.node.Uint8Array] buffer The buffer that the data will be | ||
* written to. | ||
@@ -410,3 +409,3 @@ * @param [Number] offset The offset within the buffer where writing will | ||
*/ | ||
readSync(buffer: Buffer, offset: number, length: number, position: number): number; | ||
readSync(buffer: Uint8Array, offset: number, length: number, position: number): number; | ||
/** | ||
@@ -445,3 +444,3 @@ * Asynchronous `fchmod`. | ||
export declare class NoSyncFile<T extends FileSystem> extends PreloadFile<T> implements File { | ||
constructor(_fs: T, _path: string, _flag: FileFlag, _stat: Stats, contents?: Buffer); | ||
constructor(_fs: T, _path: string, _flag: FileFlag, _stat: Stats, contents?: Uint8Array); | ||
/** | ||
@@ -448,0 +447,0 @@ * Asynchronous sync. Doesn't do anything, simply calls the cb. |
@@ -13,3 +13,2 @@ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) { | ||
import { getMount } from './emulation/shared.js'; | ||
import { Buffer } from 'buffer'; | ||
export var ActionType; | ||
@@ -204,3 +203,3 @@ (function (ActionType) { | ||
* An implementation of the File interface that operates on a file that is | ||
* completely in-memory. PreloadFiles are backed by a Buffer. | ||
* completely in-memory. PreloadFiles are backed by a Uint8Array. | ||
* | ||
@@ -235,3 +234,3 @@ * This is also an abstract class, as it lacks an implementation of 'sync' and | ||
this._stat = _stat; | ||
this._buffer = contents ? contents : Buffer.alloc(0); | ||
this._buffer = contents ? contents : new Uint8Array(0); | ||
// Note: This invariant is *not* maintained once the file starts getting | ||
@@ -242,3 +241,3 @@ // modified. | ||
if (this._stat.size !== this._buffer.length && this._flag.isReadable()) { | ||
throw new Error(`Invalid buffer: Buffer is ${this._buffer.length} long, yet Stats object specifies that file is ${this._stat.size} long.`); | ||
throw new Error(`Invalid buffer: Uint8Array is ${this._buffer.length} long, yet Stats object specifies that file is ${this._stat.size} long.`); | ||
} | ||
@@ -366,3 +365,3 @@ } | ||
if (len > this._buffer.length) { | ||
const buf = Buffer.alloc(len - this._buffer.length, 0); | ||
const buf = new Uint8Array(len - this._buffer.length); | ||
// Write will set @_stat.size for us. | ||
@@ -377,5 +376,3 @@ this.writeSync(buf, 0, buf.length, this._buffer.length); | ||
// Truncate buffer to 'len'. | ||
const newBuff = Buffer.alloc(len); | ||
this._buffer.copy(newBuff, 0, 0, len); | ||
this._buffer = newBuff; | ||
this._buffer = this._buffer.subarray(0, len); | ||
if (this._flag.isSynchronous() && getMount('/').metadata.synchronous) { | ||
@@ -389,3 +386,3 @@ this.syncSync(); | ||
* without waiting for the callback. | ||
* @param [ZenFS.node.Buffer] buffer Buffer containing the data to write to | ||
* @param [ZenFS.node.Uint8Array] buffer Uint8Array containing the data to write to | ||
* the file. | ||
@@ -397,3 +394,3 @@ * @param [Number] offset Offset in the buffer to start reading data from. | ||
* the current position. | ||
* @param [Function(ZenFS.ApiError, Number, ZenFS.node.Buffer)] | ||
* @param [Function(ZenFS.ApiError, Number, ZenFS.node.Uint8Array)] | ||
* cb The number specifies the number of bytes written into the file. | ||
@@ -410,3 +407,3 @@ */ | ||
* without waiting for the callback. | ||
* @param [ZenFS.node.Buffer] buffer Buffer containing the data to write to | ||
* @param [ZenFS.node.Uint8Array] buffer Uint8Array containing the data to write to | ||
* the file. | ||
@@ -433,8 +430,9 @@ * @param [Number] offset Offset in the buffer to start reading data from. | ||
// Extend the buffer! | ||
const newBuff = Buffer.alloc(endFp); | ||
this._buffer.copy(newBuff); | ||
this._buffer = newBuff; | ||
const newBuffer = new Uint8Array(endFp); | ||
newBuffer.set(this._buffer); | ||
this._buffer = newBuffer; | ||
} | ||
} | ||
const len = buffer.copy(this._buffer, position, offset, offset + length); | ||
this._buffer.set(buffer.slice(offset, offset + length), position); | ||
const len = this._buffer.length; | ||
this._stat.mtimeMs = Date.now(); | ||
@@ -450,3 +448,3 @@ if (this._flag.isSynchronous()) { | ||
* Read data from the file. | ||
* @param [ZenFS.node.Buffer] buffer The buffer that the data will be | ||
* @param [ZenFS.node.Uint8Array] buffer The buffer that the data will be | ||
* written to. | ||
@@ -459,3 +457,3 @@ * @param [Number] offset The offset within the buffer where writing will | ||
* position. | ||
* @param [Function(ZenFS.ApiError, Number, ZenFS.node.Buffer)] cb The | ||
* @param [Function(ZenFS.ApiError, Number, ZenFS.node.Uint8Array)] cb The | ||
* number is the number of bytes read | ||
@@ -470,3 +468,3 @@ */ | ||
* Read data from the file. | ||
* @param [ZenFS.node.Buffer] buffer The buffer that the data will be | ||
* @param [ZenFS.node.Uint8Array] buffer The buffer that the data will be | ||
* written to. | ||
@@ -492,6 +490,6 @@ * @param [Number] offset The offset within the buffer where writing will | ||
} | ||
const rv = this._buffer.copy(buffer, offset, position, position + length); | ||
this._buffer.set(buffer.slice(offset, offset + length), position); | ||
this._stat.atimeMs = Date.now(); | ||
this._pos = position + length; | ||
return rv; | ||
return this._buffer.length; | ||
} | ||
@@ -498,0 +496,0 @@ /** |
@@ -9,3 +9,3 @@ /// <reference types="node" resolution-mode="require"/> | ||
export type BFSThreeArgCallback<T, U> = (e?: ApiError, arg1?: T, arg2?: U) => unknown; | ||
export type FileContents = Buffer | string; | ||
export type FileContents = Uint8Array | string; | ||
/** | ||
@@ -185,3 +185,3 @@ * Metadata about a FileSystem | ||
* into a string using that encoding. Otherwise, if encoding is null, fetch | ||
* the file's contents as a Buffer. | ||
* the file's contents as a Uint8Array. | ||
* If no encoding is specified, then the raw buffer is returned. | ||
@@ -194,3 +194,3 @@ */ | ||
* into a string using that encoding. Otherwise, if encoding is null, fetch | ||
* the file's contents as a Buffer. | ||
* the file's contents as a Uint8Array. | ||
*/ | ||
@@ -197,0 +197,0 @@ abstract readFileSync(fname: string, encoding: BufferEncoding | null, flag: FileFlag, cred: Cred): FileContents; |
@@ -16,3 +16,3 @@ /* eslint-disable @typescript-eslint/no-unused-vars */ | ||
import * as path from './emulation/path.js'; | ||
import { Buffer } from 'buffer'; | ||
import { decode, encode } from './utils.js'; | ||
/** | ||
@@ -328,3 +328,3 @@ * Structure for a filesystem. **All** ZenFS FileSystems must implement | ||
// Allocate buffer. | ||
const buf = Buffer.alloc(stat.size); | ||
const buf = new Uint8Array(stat.size); | ||
yield fd.read(buf, 0, stat.size, 0); | ||
@@ -335,3 +335,3 @@ yield fd.close(); | ||
} | ||
return buf.toString(encoding); | ||
return decode(buf); | ||
} | ||
@@ -349,3 +349,3 @@ finally { | ||
// Allocate buffer. | ||
const buf = Buffer.alloc(stat.size); | ||
const buf = new Uint8Array(stat.size); | ||
fd.readSync(buf, 0, stat.size, 0); | ||
@@ -356,3 +356,3 @@ fd.closeSync(); | ||
} | ||
return buf.toString(encoding); | ||
return decode(buf); | ||
} | ||
@@ -369,3 +369,3 @@ finally { | ||
if (typeof data === 'string') { | ||
data = Buffer.from(data, encoding); | ||
data = encode(data); | ||
} | ||
@@ -385,3 +385,3 @@ // Write into file. | ||
if (typeof data === 'string') { | ||
data = Buffer.from(data, encoding); | ||
data = encode(data); | ||
} | ||
@@ -400,3 +400,3 @@ // Write into file. | ||
if (typeof data === 'string') { | ||
data = Buffer.from(data, encoding); | ||
data = encode(data); | ||
} | ||
@@ -414,3 +414,3 @@ yield fd.write(data, 0, data.length, null); | ||
if (typeof data === 'string') { | ||
data = Buffer.from(data, encoding); | ||
data = encode(data); | ||
} | ||
@@ -417,0 +417,0 @@ fd.writeSync(data, 0, data.length, null); |
@@ -1,2 +0,1 @@ | ||
/// <reference types="node" resolution-mode="require"/> | ||
import { Stats } from './stats.js'; | ||
@@ -18,3 +17,3 @@ /** | ||
*/ | ||
static fromBuffer(buffer: Buffer): Inode; | ||
static Deserialize(data: ArrayBufferLike | ArrayBufferView): Inode; | ||
constructor(id: string, size: number, mode: number, atime: number, mtime: number, ctime: number, uid: number, gid: number); | ||
@@ -32,3 +31,3 @@ /** | ||
*/ | ||
toBuffer(buff?: Buffer): Buffer; | ||
serialize(data?: ArrayBufferLike | ArrayBufferView): Uint8Array; | ||
/** | ||
@@ -35,0 +34,0 @@ * Updates the Inode using information from the stats object. Used by file |
import { Stats, FileType } from './stats.js'; | ||
import { Buffer } from 'buffer'; | ||
import { decode, encode } from './utils.js'; | ||
/** | ||
@@ -10,7 +10,5 @@ * Generic inode definition that can easily be serialized. | ||
*/ | ||
static fromBuffer(buffer) { | ||
if (buffer === undefined) { | ||
throw new Error('NO'); | ||
} | ||
return new Inode(buffer.toString('ascii', 38), buffer.readUInt32LE(0), buffer.readUInt16LE(4), buffer.readDoubleLE(6), buffer.readDoubleLE(14), buffer.readDoubleLE(22), buffer.readUInt32LE(30), buffer.readUInt32LE(34)); | ||
static Deserialize(data) { | ||
const view = new DataView('buffer' in data ? data.buffer : data); | ||
return new Inode(decode(view.buffer.slice(38)), view.getUint32(0, true), view.getUint16(4, true), view.getFloat64(6, true), view.getFloat64(14, true), view.getFloat64(22, true), view.getUint32(30, true), view.getUint32(34, true)); | ||
} | ||
@@ -37,3 +35,3 @@ constructor(id, size, mode, atime, mtime, ctime, uid, gid) { | ||
getSize() { | ||
// ASSUMPTION: ID is ASCII (1 byte per char). | ||
// ASSUMPTION: ID is 1 byte per char. | ||
return 38 + this.id.length; | ||
@@ -44,12 +42,14 @@ } | ||
*/ | ||
toBuffer(buff = Buffer.alloc(this.getSize())) { | ||
buff.writeUInt32LE(this.size, 0); | ||
buff.writeUInt16LE(this.mode, 4); | ||
buff.writeDoubleLE(this.atime, 6); | ||
buff.writeDoubleLE(this.mtime, 14); | ||
buff.writeDoubleLE(this.ctime, 22); | ||
buff.writeUInt32LE(this.uid, 30); | ||
buff.writeUInt32LE(this.gid, 34); | ||
buff.write(this.id, 38, this.id.length, 'ascii'); | ||
return buff; | ||
serialize(data = new Uint8Array(this.getSize())) { | ||
const view = new DataView('buffer' in data ? data.buffer : data); | ||
view.setUint32(0, this.size, true); | ||
view.setUint16(4, this.mode, true); | ||
view.setFloat64(6, this.atime, true); | ||
view.setFloat64(14, this.mtime, true); | ||
view.setFloat64(22, this.ctime, true); | ||
view.setUint32(30, this.uid, true); | ||
view.setUint32(34, this.gid, true); | ||
const buffer = new Uint8Array(view.buffer); | ||
buffer.set(encode(this.id), 38); | ||
return buffer; | ||
} | ||
@@ -56,0 +56,0 @@ /** |
/// <reference types="node" resolution-mode="require"/> | ||
/// <reference types="node" resolution-mode="require"/> | ||
import type { StatsBase } from 'fs'; | ||
@@ -21,3 +20,3 @@ import { Cred } from './cred.js'; | ||
export declare class Stats implements StatsBase<number> { | ||
static fromBuffer(buffer: Buffer): Stats; | ||
static Deserialize(data: ArrayBufferLike | ArrayBufferView): Stats; | ||
/** | ||
@@ -36,3 +35,3 @@ * Clones the stats object. | ||
gid: number; | ||
fileData: Buffer | null; | ||
fileData: Uint8Array | null; | ||
atimeMs: number; | ||
@@ -61,3 +60,3 @@ mtimeMs: number; | ||
constructor(itemType: FileType, size: number, mode?: number, atimeMs?: number, mtimeMs?: number, ctimeMs?: number, uid?: number, gid?: number, birthtimeMs?: number); | ||
toBuffer(): Buffer; | ||
serialize(): Uint8Array; | ||
/** | ||
@@ -64,0 +63,0 @@ * @return [Boolean] True if this item is a file. |
import { Cred } from './cred.js'; | ||
import { Buffer } from 'buffer'; | ||
import { S_IFDIR, S_IFLNK, S_IFMT, S_IFREG } from './emulation/constants.js'; | ||
@@ -21,4 +20,5 @@ /** | ||
export class Stats { | ||
static fromBuffer(buffer) { | ||
const size = buffer.readUInt32LE(0), mode = buffer.readUInt32LE(4), atime = buffer.readDoubleLE(8), mtime = buffer.readDoubleLE(16), ctime = buffer.readDoubleLE(24), uid = buffer.readUInt32LE(32), gid = buffer.readUInt32LE(36); | ||
static Deserialize(data) { | ||
const view = new DataView('buffer' in data ? data.buffer : data); | ||
const size = view.getUint32(0, true), mode = view.getUint32(4, true), atime = view.getFloat64(8, true), mtime = view.getFloat64(16, true), ctime = view.getFloat64(24, true), uid = view.getUint32(32, true), gid = view.getUint32(36, true); | ||
return new Stats(mode & S_IFMT, size, mode & ~S_IFMT, atime, mtime, ctime, uid, gid); | ||
@@ -129,12 +129,12 @@ } | ||
} | ||
toBuffer() { | ||
const buffer = Buffer.alloc(32); | ||
buffer.writeUInt32LE(this.size, 0); | ||
buffer.writeUInt32LE(this.mode, 4); | ||
buffer.writeDoubleLE(this.atime.getTime(), 8); | ||
buffer.writeDoubleLE(this.mtime.getTime(), 16); | ||
buffer.writeDoubleLE(this.ctime.getTime(), 24); | ||
buffer.writeUInt32LE(this.uid, 32); | ||
buffer.writeUInt32LE(this.gid, 36); | ||
return buffer; | ||
serialize() { | ||
const data = new Uint8Array(32), view = new DataView(data.buffer); | ||
view.setUint32(0, this.size, true); | ||
view.setUint32(4, this.mode, true); | ||
view.setFloat64(8, this.atime.getTime(), true); | ||
view.setFloat64(16, this.mtime.getTime(), true); | ||
view.setFloat64(24, this.ctime.getTime(), true); | ||
view.setUint32(32, this.uid, true); | ||
view.setUint32(36, this.gid, true); | ||
return data; | ||
} | ||
@@ -141,0 +141,0 @@ /** |
/// <reference types="node" resolution-mode="require"/> | ||
/// <reference types="node" resolution-mode="require"/> | ||
/** | ||
@@ -8,2 +9,3 @@ * Grab bag of utility functions used across the code. | ||
import type { BaseBackendConstructor } from './backends/backend.js'; | ||
import type { TextEncoder as TextEncoderType, TextDecoder as TextDecoderType } from 'node:util'; | ||
/** | ||
@@ -34,8 +36,11 @@ * Synchronous recursive makedir. | ||
export declare const ROOT_NODE_ID: string; | ||
declare global { | ||
const TextEncoder: typeof TextEncoderType; | ||
const TextDecoder: typeof TextDecoderType; | ||
} | ||
export declare const encode: (input?: string) => Uint8Array; | ||
export declare const decode: (input?: ArrayBuffer | NodeJS.ArrayBufferView, options?: { | ||
stream?: boolean; | ||
}) => string; | ||
/** | ||
* Returns an empty directory node. | ||
* @internal | ||
*/ | ||
export declare function getEmptyDirNode(): Buffer; | ||
/** | ||
* Generates a random ID. | ||
@@ -42,0 +47,0 @@ * @internal |
@@ -12,3 +12,2 @@ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) { | ||
import * as path from './emulation/path.js'; | ||
import { Buffer } from 'buffer'; | ||
/** | ||
@@ -217,10 +216,5 @@ * Synchronous recursive makedir. | ||
export const ROOT_NODE_ID = '/'; | ||
export const encode = new TextEncoder().encode; | ||
export const decode = new TextDecoder().decode; | ||
/** | ||
* Returns an empty directory node. | ||
* @internal | ||
*/ | ||
export function getEmptyDirNode() { | ||
return Buffer.from('{}'); | ||
} | ||
/** | ||
* Generates a random ID. | ||
@@ -227,0 +221,0 @@ * @internal |
{ | ||
"name": "@zenfs/core", | ||
"version": "0.0.8", | ||
"version": "0.0.9", | ||
"description": "A filesystem in your browser", | ||
@@ -47,3 +47,2 @@ "main": "dist/index.js", | ||
"@jest/globals": "^29.5.0", | ||
"@types/archiver": "~2.1.2", | ||
"@types/jest": "^29.5.1", | ||
@@ -53,3 +52,2 @@ "@types/node": "^14.18.62", | ||
"@typescript-eslint/parser": "^5.55.0", | ||
"archiver": "~2.1.1", | ||
"buffer": "~5.1.0", | ||
@@ -56,0 +54,0 @@ "cross-env": "^7.0.3", |
Sorry, the diff of this file is too big to display
Sorry, the diff of this file is not supported yet
14
-12.5%859480
-11.84%10750
-0.96%