source.fact.ngo a coherence.ngo project

scripts/lib.js

raw ↗ · AGPL-3.0

// Shared utilities for xray scripts. Zero dependencies by design. import fs from "node:fs"; import os from "node:os"; import path from "node:path"; import crypto from "node:crypto"; export const REPO_ROOT = path.resolve(path.dirname(new URL(import.meta.url).pathname), ".."); export const PROTOCOL_VERSION = "1.0"; export const AUTH_FILE = path.join(os.homedir(), ".local/share/opencode/auth.json"); export function getCloudflareAuth() { const token = process.env.CLOUDFLARE_API_TOKEN || null; const account = process.env.CLOUDFLARE_ACCOUNT_ID || null; if (token) return { token, account, source: "env" }; try { const raw = JSON.parse(fs.readFileSync(AUTH_FILE, "utf8")); const key = raw?.["cloudflare-workers-ai"]?.key || null; if (key) return { token: key, account, source: "auth.json" }; } catch {} return { token: null, account, source: "none" }; } // Parses the controlled YAML subset used by ontology/*.yaml: // list of mappings at indent 0 ("- id: x"), string fields at indent 2, // and string-list fields ("seeds:" + indent-4 " - item") entries. export function parseOntologyYaml(text) { const items = []; let cur = null; let listKey = null; for (const raw of String(text).split("\n")) { const line = raw.replace(/\r$/, ""); if (!line.trim() || /^\s*#/.test(line)) continue; const indent = line.length - line.trimStart().length; const t = line.trim(); if (t.startsWith("- ")) { const rest = t.slice(2).trim(); if (indent === 0) { cur = {}; items.push(cur); listKey = null; } else { if (listKey) cur[listKey].push(rest); continue; } const ci = rest.indexOf(":"); if (ci > -1) cur[rest.slice(0, ci).trim()] = rest.slice(ci + 1).trim(); continue; } const ci = t.indexOf(":"); if (ci === -1) continue; const key = t.slice(0, ci).trim(); const val = t.slice(ci + 1).trim(); if (val === "") { cur[key] = []; listKey = key; } else { cur[key] = val; listKey = null; } } return items; } export function loadDomains() { return parseOntologyYaml(fs.readFileSync(path.join(REPO_ROOT, "ontology/domains.yaml"), "utf8")); } export function loadLenses() { return parseOntologyYaml(fs.readFileSync(path.join(REPO_ROOT, "ontology/lenses.yaml"), "utf8")); } export function modelSlug(modelId) { return modelId.replace(/^@cf\//, "").replace(/[/._]/g, "-"); } export function nowIso() { return new Date().toISOString(); } export function hashId(prefix, content) { const h = crypto.createHash("sha256").update(content).digest("hex").slice(0, 12); return `${prefix}_${h}`; } export function appendJsonl(filePath, obj) { fs.mkdirSync(path.dirname(filePath), { recursive: true }); fs.appendFileSync(filePath, JSON.stringify(obj) + "\n", "utf8"); } export function readJsonl(filePath) { if (!fs.existsSync(filePath)) return []; return fs.readFileSync(filePath, "utf8").split("\n").filter(Boolean).map((l) => JSON.parse(l)); } export function fmtUsd(x) { return "$" + x.toFixed(x < 1 ? 3 : 2); } export function parseArgs(argv, spec) { // spec: { flag: {takes: "value"|"none"|"optional", default: any}} const out = {}; const positional = []; for (const k of Object.keys(spec)) out[k] = spec[k].default; for (let i = 0; i < argv.length; i++) { const a = argv[i]; if (a.startsWith("--")) { const key = a.slice(2).replace(/-/g, "_"); const s = spec[key]; if (!s) { console.error(`Unknown flag --${key}`); process.exit(2); } if (s.takes === "none") out[key] = true; else { let val = argv[i + 1]; if (val === undefined || val.startsWith("--")) { if (s.takes === "optional") val = true; else { console.error(`--${key} requires a value`); process.exit(2); } out[key] = val; } else { out[key] = val; i++; } } } else positional.push(a); } return { args: out, positional }; }