thedotmack/claude-mem · error
Invalid topic
Error message
Invalid topic
What it means
GET /api/instructions validates the topic query parameter against the ALLOWED_TOPICS allow-list; any value not in the list returns 400 'Invalid topic' before operation validation or content lookup. Omitting the parameter is fine (defaults to 'all').
Source
Thrown at src/services/server/Server.ts:294
});
} else {
res.status(503).json({
status: 'initializing',
message: 'Worker is still initializing, please retry',
});
}
});
this.app.get('/api/version', (_req: Request, res: Response) => {
res.status(200).json({ version: BUILT_IN_VERSION });
});
this.app.get('/api/instructions', (req: Request, res: Response) => {
const topic = (req.query.topic as string) || 'all';
const operation = req.query.operation as string | undefined;
if (topic && !ALLOWED_TOPICS.includes(topic)) {
return res.status(400).json({ error: 'Invalid topic' });
}
if (operation && !ALLOWED_OPERATIONS.includes(operation)) {
return res.status(400).json({ error: 'Invalid operation' });
}
if (operation) {
const cached = cachedOperationContent.get(operation);
if (cached === undefined) {
logger.debug('HTTP', 'Instruction file not cached at boot', { operation });
return res.status(404).json({ error: 'Instruction not found' });
}
return res.json({ content: [{ type: 'text', text: cached }] });
}
if (cachedSkillMd === null) {
logger.debug('HTTP', 'SKILL.md not cached at boot', { topic });
return res.status(404).json({ error: 'Instruction not found' });View on GitHub (pinned to 8bc631a71a)
Solutions
- Omit ?topic to receive the full SKILL.md content
- Use an allowed topic name exactly as the server defines it
- Check ALLOWED_TOPICS in the server source for the current set of values
Example fix
// before
fetch(`${base}/api/instructions?topic=memoriez`); // 400 Invalid topic
// after
fetch(`${base}/api/instructions?topic=memory`); // 200 Defensive patterns
Strategy: validation
Validate before calling
const ALLOWED_TOPICS = new Set(['all', /* mirror the server's list */ 'memory', 'sessions', 'projects']);
function instructionsUrl(base: string, topic?: string): string {
if (topic && !ALLOWED_TOPICS.has(topic)) {
console.warn(`unknown topic ${topic}; falling back to full SKILL.md`);
return `${base}/api/instructions`;
}
return topic ? `${base}/api/instructions?topic=${encodeURIComponent(topic)}` : `${base}/api/instructions`;
} Type guard
function isInvalidParameter(status: number, body: unknown, field: 'topic' | 'operation'): body is { error: string } {
return status === 400 && typeof body === 'object' && body !== null && (body as { error?: string }).error === `Invalid ${field}`;
} Try / catch
const res = await fetch(`${base}/api/instructions?topic=${topic}`);
if (res.status === 400) {
const body = await res.json().catch(() => ({}));
if (body.error === 'Invalid topic') return fetch(`${base}/api/instructions`).then(r => r.json()); // fall back to full content
throw new Error(`instructions request rejected: ${JSON.stringify(body)}`);
} Prevention
- Pin topic names in constants reviewed on server upgrades
- Default to omitting ?topic — full SKILL.md is always valid
- Topics are case-sensitive: match the server's spelling exactly
When it happens
Trigger: GET /api/instructions?topic=<value> where value is not an allowed topic — typo, wrong casing, or a topic name removed/renamed in the current server version.
Common situations: Prompt templates or agents referencing topic names from an older release; passing an operation name into the topic param; case-sensitive topic strings.
Understand the failure class
Background: "Invalid query parameter" / "Failed to parse value of ...": fixing bad query string parameters across APIs — this error's family across 36 libraries.
Related errors
AI-assisted analysis of thedotmack/claude-mem@8bc631a71a (2026-08-20).
Data as JSON: /api/errors/a1f666a3829ddfcf.
Report an issue: GitHub.