#!/usr/bin/env node // Smoke test for the OpenCode adapter: the plugin's hooks behave against the // real (structural) OpenCode hook shapes. No live OpenCode needed. const test = require('node:test'); const assert = require('node:assert/strict'); const fs = require('fs'); const os = require('os'); const path = require('path'); const { pathToFileURL } = require('url'); // Point the plugin's mode-flag at a temp config home BEFORE it loads — the // plugin resolves its state path once at load (as it does under a real OpenCode // process, where XDG_CONFIG_HOME is already set). The dynamic import below runs // after this assignment, so the ordering holds. const tmp = fs.mkdtempSync(path.join(os.tmpdir(), 'ponytail-opencode-')); process.env.XDG_CONFIG_HOME = tmp; delete process.env.PONYTAIL_DEFAULT_MODE; const statePath = path.join(tmp, 'opencode', '.ponytail-active'); let loadPlugin; test.before(async () => { const url = pathToFileURL(path.join(__dirname, '..', '.opencode', 'plugins', 'ponytail.mjs')); loadPlugin = (await import(url)).default; }); function transform(hooks) { const output = { system: [] }; return hooks['experimental.chat.system.transform']({ model: {} }, output).then(() => output.system); } test('system.transform injects the ruleset at the default mode (full)', async () => { try { fs.unlinkSync(statePath); } catch (e) {} const hooks = await loadPlugin({}); const system = await transform(hooks); assert.equal(system.length, 1); assert.match(system[0], /PONYTAIL MODE ACTIVE — level: full/); assert.match(system[0], /lazy senior developer/); }); test('command.execute.before persists /ponytail ultra, transform follows it', async () => { const hooks = await loadPlugin({}); await hooks['command.execute.before']({ command: 'ponytail', arguments: 'ultra', sessionID: 's' }); assert.equal(fs.readFileSync(statePath, 'utf8'), 'ultra'); const system = await transform(hooks); assert.match(system[0], /PONYTAIL MODE ACTIVE — level: ultra/); }); test('/ponytail off persists off and transform injects nothing', async () => { const hooks = await loadPlugin({}); await hooks['command.execute.before']({ command: 'ponytail', arguments: 'off', sessionID: 's' }); assert.equal(fs.readFileSync(statePath, 'utf8'), 'off'); const system = await transform(hooks); assert.deepEqual(system, []); }); test('unrelated commands do not touch the flag', async () => { try { fs.unlinkSync(statePath); } catch (e) {} const hooks = await loadPlugin({}); await hooks['command.execute.before']({ command: 'commit', arguments: 'x', sessionID: 's' }); assert.equal(fs.existsSync(statePath), false); }); test.after(() => fs.rmSync(tmp, { recursive: true, force: true }));