From a2d68e5d9c9c4f809b7194fccc79c6e6db4dde07 Mon Sep 17 00:00:00 2001 From: James Prevett Date: Wed, 2 Oct 2024 22:05:58 -0500 Subject: [PATCH] Refactored `Directory` to extend `Map` --- jest.config.json | 19 --------------- src/Directory.ts | 61 +++++++++++++++++------------------------------- src/IsoFS.ts | 10 ++++---- 3 files changed, 26 insertions(+), 64 deletions(-) delete mode 100644 jest.config.json diff --git a/jest.config.json b/jest.config.json deleted file mode 100644 index bef010f..0000000 --- a/jest.config.json +++ /dev/null @@ -1,19 +0,0 @@ -{ - "preset": "ts-jest/presets/default-esm", - "testEnvironment": "node", - "extensionsToTreatAsEsm": [".ts"], - "testMatch": ["./**/*.test.ts"], - "moduleNameMapper": { - "^(\\.{1,2}/.*)\\.js$": "$1" - }, - "transform": { - "^.+\\.ts$": [ - "ts-jest", - { - "tsconfig": "tests/tsconfig.json", - "useESM": true - } - ] - }, - "verbose": true -} diff --git a/src/Directory.ts b/src/Directory.ts index b3d93e9..d94463c 100644 --- a/src/Directory.ts +++ b/src/Directory.ts @@ -2,40 +2,40 @@ import { DirectoryRecord, ISODirectoryRecord, JolietDirectoryRecord } from './Di import { FileFlags } from './constants.js'; import { CLEntry, REEntry } from './entries.js'; -export abstract class Directory { - protected _record: T; - private _fileList: string[] = []; - private _fileMap: { [name: string]: T } = {}; +export abstract class Directory extends Map { + //public readonly files: string[] = []; + //private fileMap = new Map(); - public constructor(record: T, isoData: Uint8Array) { - this._record = record; + public constructor( + protected record: T, + isoData: Uint8Array + ) { + super(); let i = record.lba; let limit = i + record.dataLength; if (!(record.fileFlags & FileFlags.Directory)) { // Must have a CL entry. - const cl = record.getSUEntries(isoData).filter(e => e instanceof CLEntry)[0] as CLEntry; + const cl = record.getSUEntries(isoData).find(e => e instanceof CLEntry); + if (!cl) { + throw new ReferenceError('No CL entry'); + } i = cl.childDirectoryLba * 2048; limit = Infinity; } while (i < limit) { - const len = isoData[i]; + const length = isoData[i]; // Zero-padding between sectors. - // TODO: Could optimize this to seek to nearest-sector upon - // seeing a 0. - if (len === 0) { + // Could optimize this to seek to nearest-sector upon seeing a 0. + if (!length) { i++; continue; } const r = this._constructDirectoryRecord(isoData.slice(i)); const fname = r.fileName(isoData); // Skip '.' and '..' entries. - if (fname !== '\u0000' && fname !== '\u0001') { - // Skip relocated entries. - if (!r.hasRockRidge || r.getSUEntries(isoData).filter(e => e instanceof REEntry).length === 0) { - this._fileMap[fname] = r; - this._fileList.push(fname); - } + if (fname !== '\u0000' && fname !== '\u0001' && (!r.hasRockRidge || !r.getSUEntries(isoData).filter(e => e instanceof REEntry).length)) { + this.set(fname, r); } else if (limit === Infinity) { // First entry contains needed data. limit = i + r.dataLength; @@ -44,40 +44,21 @@ export abstract class Directory { } } - /** - * Get the record with the given name. - * Returns undefined if not present. - */ - public getRecord(name: string): DirectoryRecord { - return this._fileMap[name]; - } - - public get fileList(): string[] { - return this._fileList; - } - public getDotEntry(isoData: Uint8Array): T { - return this._constructDirectoryRecord(isoData.slice(this._record.lba)); + return this._constructDirectoryRecord(isoData.slice(this.record.lba)); } protected abstract _constructDirectoryRecord(data: Uint8Array): T; } -export class ISODirectory extends Directory { - public constructor(record: ISODirectoryRecord, isoData: Uint8Array) { - super(record, isoData); - } +export class ISODirectory extends Directory { protected _constructDirectoryRecord(data: Uint8Array): ISODirectoryRecord { - return new ISODirectoryRecord(data, this._record.rockRidgeOffset); + return new ISODirectoryRecord(data, this.record.rockRidgeOffset); } } export class JolietDirectory extends Directory { - public constructor(record: JolietDirectoryRecord, isoData: Uint8Array) { - super(record, isoData); - } - protected _constructDirectoryRecord(data: Uint8Array): JolietDirectoryRecord { - return new JolietDirectoryRecord(data, this._record.rockRidgeOffset); + return new JolietDirectoryRecord(data, this.record.rockRidgeOffset); } } diff --git a/src/IsoFS.ts b/src/IsoFS.ts index 0d8ae3d..07453c0 100644 --- a/src/IsoFS.ts +++ b/src/IsoFS.ts @@ -135,7 +135,7 @@ export class IsoFS extends Readonly(Sync(FileSystem)) { } if (record.isDirectory(this.data)) { - return record.getDirectory(this.data).fileList.slice(0); + return Array.from(record.getDirectory(this.data).keys()); } throw ErrnoError.With('ENOTDIR', path, 'readdir'); @@ -146,13 +146,13 @@ export class IsoFS extends Readonly(Sync(FileSystem)) { if (path === '/') { return this._root; } - const components = path.split('/').slice(1); - let dir = this._root; - for (const component of components) { + const parts = path.split('/').slice(1); + let dir: DirectoryRecord | undefined = this._root; + for (const part of parts) { if (!dir.isDirectory(this.data)) { return; } - dir = dir.getDirectory(this.data).getRecord(component); + dir = dir.getDirectory(this.data).get(part); if (!dir) { return; }