fix(db): index tool payloads by message

Eliminate full-table scans from subagent tool queries and guardian retractions by indexing message_uuid on tool_calls and tool_results. Add query-plan regressions for both access paths.
This commit is contained in:
tommy0103
2026-07-16 03:02:03 +08:00
parent cec66d0656
commit c2ecc59cc7
2 changed files with 55 additions and 0 deletions
+2
View File
@@ -56,8 +56,10 @@ CREATE INDEX IF NOT EXISTS idx_messages_ts ON messages(session_id, timestamp);
CREATE INDEX IF NOT EXISTS idx_sessions_source ON sessions(source); CREATE INDEX IF NOT EXISTS idx_sessions_source ON sessions(source);
CREATE INDEX IF NOT EXISTS idx_messages_source ON messages(source); CREATE INDEX IF NOT EXISTS idx_messages_source ON messages(source);
CREATE INDEX IF NOT EXISTS idx_tc_session_name ON tool_calls(session_id, name); CREATE INDEX IF NOT EXISTS idx_tc_session_name ON tool_calls(session_id, name);
CREATE INDEX IF NOT EXISTS idx_tc_message ON tool_calls(message_uuid);
CREATE INDEX IF NOT EXISTS idx_tc_file ON tool_calls(file_path); CREATE INDEX IF NOT EXISTS idx_tc_file ON tool_calls(file_path);
CREATE INDEX IF NOT EXISTS idx_tr_session ON tool_results(session_id); CREATE INDEX IF NOT EXISTS idx_tr_session ON tool_results(session_id);
CREATE INDEX IF NOT EXISTS idx_tr_message ON tool_results(message_uuid);
CREATE INDEX IF NOT EXISTS idx_sa_session ON subagents(session_id); CREATE INDEX IF NOT EXISTS idx_sa_session ON subagents(session_id);
CREATE INDEX IF NOT EXISTS idx_wf_session ON workflows(session_id); CREATE INDEX IF NOT EXISTS idx_wf_session ON workflows(session_id);
CREATE INDEX IF NOT EXISTS idx_wa_run ON workflow_agents(run_id); CREATE INDEX IF NOT EXISTS idx_wa_run ON workflow_agents(run_id);
+53
View File
@@ -67,6 +67,59 @@ test('tool results schema indexes live session patch lookups', async () => {
} }
}); });
test('tool payload schema indexes subagent joins and guardian retractions', async () => {
const db = new DatabaseSync(':memory:');
try {
db.exec(await readExecutableSchema());
const toolCallJoinPlan = db.prepare(`
EXPLAIN QUERY PLAN
SELECT tc.* FROM tool_calls tc
JOIN messages m ON m.uuid = tc.message_uuid
WHERE m.agent_id = ?
`).all('agent-1');
const toolResultJoinPlan = db.prepare(`
EXPLAIN QUERY PLAN
SELECT tr.* FROM tool_results tr
JOIN messages m ON m.uuid = tr.message_uuid
WHERE m.agent_id = ?
`).all('agent-1');
const toolCallRetractionPlan = db.prepare(`
EXPLAIN QUERY PLAN
SELECT rowid FROM tool_calls
WHERE session_id = ? OR message_uuid IN (
SELECT uuid FROM messages WHERE session_id = ? OR agent_id = ?
)
`).all('session-1', 'session-1', 'session-1');
const toolResultRetractionPlan = db.prepare(`
EXPLAIN QUERY PLAN
SELECT rowid FROM tool_results
WHERE session_id = ? OR message_uuid IN (
SELECT uuid FROM messages WHERE session_id = ? OR agent_id = ?
)
`).all('session-1', 'session-1', 'session-1');
const details = plans => plans.map(row => String(row.detail));
assert.ok(
details(toolCallJoinPlan).some(detail => /USING INDEX idx_tc_message/.test(detail)),
`expected indexed tool call join, got: ${details(toolCallJoinPlan).join('; ')}`,
);
assert.ok(
details(toolResultJoinPlan).some(detail => /USING INDEX idx_tr_message/.test(detail)),
`expected indexed tool result join, got: ${details(toolResultJoinPlan).join('; ')}`,
);
assert.ok(
details(toolCallRetractionPlan).some(detail => /USING INDEX idx_tc_message/.test(detail)),
`expected indexed tool call retraction, got: ${details(toolCallRetractionPlan).join('; ')}`,
);
assert.ok(
details(toolResultRetractionPlan).some(detail => /USING INDEX idx_tr_message/.test(detail)),
`expected indexed tool result retraction, got: ${details(toolResultRetractionPlan).join('; ')}`,
);
} finally {
db.close();
}
});
test('schema reference stays focused on raw SQL structure', async () => { test('schema reference stays focused on raw SQL structure', async () => {
const ref = await readSchemaReference(); const ref = await readSchemaReference();