fsdb/utils/walk.ts
Andy Burke 05178c924f refactor: make all() take filter and sort options
refactor: return unload item entries from all()/find()
2025-07-02 17:46:04 -07:00

62 lines
1.2 KiB
TypeScript

import * as path from '@std/path';
export type WALK_OPTIONS<T> = {
max_depth?: number;
depth?: number;
index?: number;
filter?: (entry: WALK_ENTRY<T>) => boolean;
sort?: (a: WALK_ENTRY<T>, b: WALK_ENTRY<T>) => number;
};
export type WALK_ENTRY<T> = {
path: string;
info: Deno.FileInfo;
depth: number;
load: () => T;
};
export async function* walk<T>(
root: string | URL,
{
depth = 0,
filter = undefined,
sort = undefined
}: WALK_OPTIONS<T> = {}
): AsyncIterableIterator<WALK_ENTRY<T>> {
const root_path = typeof root === 'string' ? path.resolve(root) : path.resolve(path.fromFileUrl(root));
const entries: WALK_ENTRY<T>[] = [];
for await (const dir_entry of Deno.readDir(root_path)) {
const full_path = path.join(root, dir_entry.name);
const info = await Deno.lstat(full_path);
const entry = {
path: full_path,
info,
depth,
load: function () {
return JSON.parse(Deno.readTextFileSync(this.path)) as T;
}
};
entries.push(entry);
}
if (sort) {
entries.sort(sort);
}
for (const entry of entries) {
if (!filter || filter(entry)) {
yield entry;
}
if (entry.info.isDirectory) {
yield* walk(entry.path, {
depth: depth + 1,
filter,
sort
});
}
}
}