UNPKG

openclaw

Version:

Multi-channel AI gateway with extensible messaging integrations

57 lines (56 loc) 2.47 kB
import fs from "node:fs"; import path from "node:path"; //#region src/infra/disk-space.ts const LOW_DISK_SPACE_WARNING_THRESHOLD_BYTES = 1073741824; function finiteNonNegativeNumber(value) { const numberValue = Number(value); return Number.isFinite(numberValue) && numberValue >= 0 ? numberValue : null; } function findExistingDiskSpacePath(targetPath) { let current = path.resolve(targetPath); while (true) try { return fs.statSync(current).isDirectory() ? current : path.dirname(current); } catch { const parent = path.dirname(current); if (parent === current) return null; current = parent; } } /** Reads available bytes for the volume containing a target path when statfs is available. */ function tryReadDiskSpace(targetPath) { if (typeof fs.statfsSync !== "function") return null; const checkedPath = findExistingDiskSpacePath(targetPath); if (!checkedPath) return null; try { const stats = fs.statfsSync(checkedPath); const blockSize = finiteNonNegativeNumber(stats.bsize); const availableBlocks = finiteNonNegativeNumber(stats.bavail); if (blockSize === null || availableBlocks === null) return null; const totalBlocks = finiteNonNegativeNumber(stats.blocks); return { targetPath, checkedPath, availableBytes: blockSize * availableBlocks, totalBytes: totalBlocks === null ? null : blockSize * totalBlocks }; } catch { return null; } } /** Formats byte counts for compact operator-facing disk-space warnings. */ function formatDiskSpaceBytes(bytes) { const mib = bytes / 1048576; const roundedMib = Math.max(0, Math.round(mib)); if (roundedMib < 1024) return `${roundedMib} MiB`; const gib = mib / 1024; return `${gib.toFixed(gib < 10 ? 1 : 0)} GiB`; } /** Builds a soft low-disk warning for setup/update flows without failing the operation. */ function createLowDiskSpaceWarning(params) { const thresholdBytes = params.thresholdBytes ?? LOW_DISK_SPACE_WARNING_THRESHOLD_BYTES; const snapshot = tryReadDiskSpace(params.targetPath); if (!snapshot || snapshot.availableBytes >= thresholdBytes) return null; return `Low disk space near ${path.resolve(snapshot.targetPath) === path.resolve(snapshot.checkedPath) ? snapshot.checkedPath : `${snapshot.targetPath} (volume checked at ${snapshot.checkedPath})`}: ${formatDiskSpaceBytes(snapshot.availableBytes)} available; ${params.purpose} may fail.`; } //#endregion export { formatDiskSpaceBytes as n, tryReadDiskSpace as r, createLowDiskSpaceWarning as t };