Files
bare-operating-system/packages/bare-os-coreutils/test/agent-helpers.test.mjs
T
snxraven eb0683abe3
Release rolling / release (push) Successful in 10m16s
Fixes
2026-08-18 23:56:09 -04:00

77 lines
2.8 KiB
JavaScript

/**
* Path / proc / apropos helpers (VM, same preamble as /bin/agent).
*/
import test from 'brittle'
import { readFileSync } from 'node:fs'
import vm from 'node:vm'
const CODE = readFileSync(new URL('../lib/agent/agent-helpers.js', import.meta.url), 'utf8')
function load() {
const sandbox = { TextDecoder, TextEncoder, Uint8Array, console }
vm.createContext(sandbox)
vm.runInContext(CODE, sandbox, { filename: 'agent-helpers.js' })
return sandbox
}
test('mutate paths use a denylist (base system read-only, rest writable)', async (t) => {
const s = load()
t.ok(s.bareAgentPathAllowedMutate('/home/guest/x'))
t.ok(s.bareAgentPathAllowedMutate('/tmp/a'))
t.ok(s.bareAgentPathAllowedMutate('/var/log/app.log'))
t.ok(s.bareAgentPathAllowedMutate('/opt/pkg/bin'))
t.ok(s.bareAgentPathAllowedMutate('/mnt/extra/file'))
t.ok(s.bareAgentPathAllowedMutate('/root/.ssh/config'))
t.absent(s.bareAgentPathAllowedMutate('/bin/foo'))
t.absent(s.bareAgentPathAllowedMutate('/etc/passwd'))
t.absent(s.bareAgentPathAllowedMutate('/proc/x'))
t.absent(s.bareAgentPathAllowedMutate('/usr/lib/x'))
t.absent(s.bareAgentPathAllowedMutate('/'))
})
test('normalize guest script strips ctx redeclare and export', async (t) => {
const s = load()
const n = s.bareAgentNormalizeGuestScript
const exported = n(
'export async function run(ctx, argv) {\n const vfs = ctx.vfs\n}\nexport { run }\n'
)
t.ok(exported.includes('async function run(ctx, argv)'))
t.absent(exported.includes('export'))
const rebound = n('const ctx = {}\nctx.console.log(1)\n')
t.ok(rebound.includes('async function run(ctx, argv)'))
t.absent(/const ctx/.test(rebound))
const plain = n('ctx.console.log("hi")')
t.ok(plain.includes('async function run(ctx, argv)'))
t.ok(plain.includes('ctx.console.log'))
})
test('reads allow any absolute path including kernel /proc', async (t) => {
const s = load()
t.ok(s.bareAgentPathAllowedRead('/home/guest/x'))
t.ok(s.bareAgentPathAllowedRead('/bin/sh'))
t.ok(s.bareAgentPathAllowedRead('/proc/bare_os/other.json'))
t.ok(s.bareAgentProcReadPathAllowed('/proc/bare_os/other.json'))
t.ok(s.bareAgentProcReadPathAllowed('/proc/bare_os/features'))
t.absent(s.bareAgentPathAllowedRead('../etc/passwd'))
t.absent(s.bareAgentProcReadPathAllowed('/home/guest/x'))
t.absent(s.bareAgentProcReadPathAllowed('/proc/../proc/bare_os/swarm.json'))
})
test('apropos substring matches kw like man -k', async (t) => {
const s = load()
const db = {
pages: [
{ name: 'grep', section: 1, title: 'pattern search' },
{ name: 'true', section: 1, title: 'exit successfully' }
],
apropos: [
{ kw: 'grep', pageRef: 0 },
{ kw: 'pattern', pageRef: 0 },
{ kw: 'true', pageRef: 1 }
]
}
const r = s.bareAgentManAproposHits(db, 'pat', 10)
t.is(r.lines.length, 1)
t.ok(r.lines[0].startsWith('grep('))
})