#!/usr/bin/env runts -- --allow-read --allow-import import { formatSize2, joinPath, log, parseIntVal, term, } from "https://global.hatter.ink/script/get/@21/deno-commons-mod.ts"; import {parseArgs} from "jsr:@std/cli/parse-args"; const defaultSkipDirs = [ ".git", ".idea", ".gradle", "target", ".DS_Store", ".localized", "node_modules", ]; async function listDir( dir: string, depth: number, maxDepth: number, ): Promise { const tab = " ".repeat(depth * 4); try { for await (const dirEntry of Deno.readDir(dir)) { if (defaultSkipDirs.includes(dirEntry.name)) { continue; } const fullName = joinPath(dir, dirEntry.name); if (dirEntry.isDirectory) { const showNextDepth = (depth + 1) <= maxDepth; console.log( `${tab}- [${dirEntry.name}]${ showNextDepth ? "" : term.blue(" \t[...more dirs...]") }`, ); if (showNextDepth) { await listDir(fullName, depth + 1, maxDepth); } } else { let fileDesc = ""; if (dirEntry.isSymlink) { fileDesc = " 🔗"; } else if (dirEntry.isFile) { const fileInfo = await Deno.stat(fullName); if (fileInfo.size > 1024 * 1024) { fileDesc = term.red( ` - ${formatSize2(fileInfo.size)}`, ); } else { fileDesc = term.yellow( ` - ${formatSize2(fileInfo.size)}`, ); } } console.log( `${tab}- ${term.green(dirEntry.name)} \t${fileDesc}`, ); } } } catch (e) { console.log(term.red(`${tab} ERROR: ${e}`)); } } async function main(): Promise { const flags = parseArgs(Deno.args, { boolean: ["help"], number: ["depth"], }); if (flags.help) { console.log(`Help massage for tree.ts tree.ts [parameters] --depth 3 - Directory depth - default '.' current dir`); return; } const maxDepth = parseIntVal(flags.depth, 10); let baseDir = "."; if (flags._.length > 0) { baseDir = flags._[0]; } await listDir(baseDir, 0, maxDepth); } main().catch((e) => log.error(e)); // @SCRIPT-SIGNATURE-V1: yk-r1.ES256.20260130T005327+08:00.MEUCICFLf8ZlGN4bSzCiRBlW // AnPVvd4by4hrwq6ZZPaN/cY6AiEAtyx0B6/EINNU2ilPoY1g0+LGc5FylLEJ5Ybn+pkpn8I=