Files
Mini-Nav/.opencode/plugins/memorix.js

83 lines
2.9 KiB
JavaScript

/**
* Memorix — Cross-Agent Memory Bridge Plugin for OpenCode
*
* Automatically captures session context and tool usage,
* piping events to `memorix hook` for cross-agent memory persistence.
*
* Generated by: memorix installHooks('opencode', projectRoot)
* Docs: https://github.com/AVIDS2/memorix
*/
export const MemorixPlugin = async ({ project, client, $, directory, worktree }) => {
console.log('[memorix] plugin loaded, directory:', directory);
/** Pipe event JSON to memorix hook via temp file (Windows .cmd stdin workaround) */
async function runHook(payload) {
const tmpDir = Bun.env.TEMP || Bun.env.TMP || '/tmp';
const tmpPath = `${tmpDir}/memorix-hook-${Date.now()}.json`;
try {
const data = JSON.stringify(payload);
await Bun.write(tmpPath, data);
// cat | pipe works through .cmd wrappers; < redirect does NOT
await $`cat ${tmpPath} | memorix hook`.quiet().nothrow();
console.log('[memorix] hook fired:', payload.hook_event_name);
} catch (err) {
console.log('[memorix] hook error:', err?.message ?? err);
} finally {
try { const { unlinkSync } = await import('node:fs'); unlinkSync(tmpPath); } catch {}
}
}
return {
/** Catch-all event handler for session lifecycle + file events */
event: async ({ event }) => {
if (event.type === 'session.created') {
await runHook({
agent: 'opencode',
hook_event_name: 'session.created',
cwd: directory,
});
} else if (event.type === 'session.idle') {
await runHook({
agent: 'opencode',
hook_event_name: 'session.idle',
cwd: directory,
});
} else if (event.type === 'file.edited') {
await runHook({
agent: 'opencode',
hook_event_name: 'file.edited',
file_path: event.properties?.path ?? '',
cwd: directory,
});
} else if (event.type === 'command.executed') {
await runHook({
agent: 'opencode',
hook_event_name: 'command.executed',
command: event.properties?.command ?? '',
cwd: directory,
});
}
},
/** Record tool usage after execution (hook, not event) */
'tool.execute.after': async (input, output) => {
await runHook({
agent: 'opencode',
hook_event_name: 'tool.execute.after',
tool_name: input.tool,
tool_input: input.args,
cwd: directory,
});
},
/** Inject memorix context into compaction prompt */
'experimental.session.compacting': async (input, output) => {
output.context.push(
'## Memorix Cross-Agent Memory\n' +
'Before compacting, use memorix_store to save important discoveries, decisions, and gotchas.\n' +
'After compacting, use memorix_session_start to reload session context, then memorix_search for specific topics.'
);
},
};
};