const UNITS: [Intl.RelativeTimeFormatUnit, number][] = [ ["year", 365 * 24 * 3600e3], ["month", 30 * 24 * 3600e3], ["week", 7 * 24 * 3600e3], ["day", 24 * 3600e3], ["hour", 3600e3], ["minute", 60e3], ]; const rtf = new Intl.RelativeTimeFormat("en", { numeric: "auto" }); export function timeAgo(ms: number) { const diff = ms - Date.now(); for (const [unit, size] of UNITS) { if (Math.abs(diff) >= size) return rtf.format(Math.round(diff / size), unit); } return "just now"; } export function formatDate(ms: number) { return new Date(ms).toLocaleDateString("en", { month: "short", day: "numeric", year: "numeric" }); } export function formatBytes(n: number) { if (n < 1024) return `${n} Bytes`; if (n < 1024 * 1024) return `${(n / 1024).toFixed(1)} KB`; if (n < 1024 * 1024 * 1024) return `${(n / 1024 / 1024).toFixed(1)} MB`; return `${(n / 1024 / 1024 / 1024).toFixed(2)} GB`; } export function shortSha(sha: string) { return sha.slice(0, 7); } /** Encodes each path segment but keeps the slashes. */ export function encodePath(p: string) { return p.split("/").map(encodeURIComponent).join("/"); }