JuliusBrussee/caveman · error
${label}:${lineNo}: "${blockKey}" mixes map and sequence ent
Error message
${label}:${lineNo}: "${blockKey}" mixes map and sequence entries What it means
Thrown by the catalog parser (dash branch) when a "- " item at indent 4 is added to a block key whose value was already established as a map (an object), not a sequence. The parser allows a block key to hold either a list of items or a map of sub-keys, but not both — mixing them would produce an ambiguous structure the generator cannot render.
Source
Thrown at scripts/generate-agent-catalog.mjs:90
if (dash) throw new Error(`${label}:${lineNo}: unexpected sequence item at row level`);
const entry = splitKeyValue(rest, label, lineNo);
if (Object.prototype.hasOwnProperty.call(row, entry.key)) {
throw new Error(`${label}:${lineNo}: duplicate key "${entry.key}"`);
}
if (entry.value === undefined) {
blockKey = entry.key;
row[entry.key] = undefined;
} else {
blockKey = null;
row[entry.key] = entry.value;
}
continue;
}
if (indent === 4) {
if (blockKey === null) throw new Error(`${label}:${lineNo}: nested line without an open block`);
if (dash) {
if (row[blockKey] === undefined) row[blockKey] = [];
if (!Array.isArray(row[blockKey])) throw new Error(`${label}:${lineNo}: "${blockKey}" mixes map and sequence entries`);
row[blockKey].push(rest);
continue;
}
if (row[blockKey] === undefined) row[blockKey] = {};
if (Array.isArray(row[blockKey]) || typeof row[blockKey] !== "object") {
throw new Error(`${label}:${lineNo}: "${blockKey}" mixes map and sequence entries`);
}
const entry = splitKeyValue(rest, label, lineNo);
if (entry.value === undefined) throw new Error(`${label}:${lineNo}: nesting deeper than two levels is not supported`);
if (Object.prototype.hasOwnProperty.call(row[blockKey], entry.key)) {
throw new Error(`${label}:${lineNo}: duplicate key "${blockKey}.${entry.key}"`);
}
row[blockKey][entry.key] = entry.value;
continue;
}
throw new Error(`${label}:${lineNo}: unexpected indent of ${indent} spaces`);
}
return rows;View on GitHub (pinned to 27d5a3981a)
Solutions
- Pick one shape for the block named in the error: all indent-4 "- item" lines (sequence) or all indent-4 "key: value" lines (map), and rewrite the block accordingly.
- If you need both, split into two sibling block keys at indent 2 (e.g. "endpoints:" and "default_endpoint:").
Example fix
# before
- provider: anthropic
endpoints:
default: /v1/messages
- /v1/count_tokens
# after
- provider: anthropic
endpoints:
- /v1/messages
- /v1/count_tokens
default_endpoint: /v1/messages Defensive patterns
Strategy: validation
Validate before calling
function blockNotMixed(text) {
const blocks = new Map();
let current = null;
for (const line of text.split("\n")) {
const m = /^ {2}([A-Za-z_][A-Za-z0-9_]*):\s*$/.exec(line.replace(/\s+$/, ""));
if (m) { current = m[1]; blocks.set(current, new Set()); continue; }
if (/^ {4}- /.test(line) && current) blocks.get(current).add("seq");
else if (/^ {4}[A-Za-z_]/.test(line) && current) blocks.get(current).add("map");
}
return [...blocks.values()].every((s) => s.size <= 1);
} Try / catch
try {
parseCatalog(text);
} catch (err) {
if (/mixes map and sequence entries/.test(err.message)) {
// split the named blockKey into one sequence block and one map block
} else throw err;
} Prevention
- Decide each block's shape (list or map) before writing it and stick to it.
- Put metadata like "default" in a sibling indent-2 key, never inside a list block.
When it happens
Trigger: Under one block key, first writing " subkey: value" (making it a map) and later " - item" (a sequence item), e.g. " endpoints:" containing both " - /v1" and " default: /v1".
Common situations: Growing a config block incrementally where an early map entry sets the type and a later edit adds list items (or vice versa); pasting heterogeneous examples into one block.
Related errors
- ${label}:${lineNo}: expected a top-level "- provider: ..." r
- ${label}:${lineNo}: row must start with an inline "provider"
- ${label}:${lineNo}: indented line before any row
- ${label}:${lineNo}: unexpected sequence item at row level
- ${label}:${lineNo}: duplicate key "${entry.key}"
AI-assisted analysis of JuliusBrussee/caveman@27d5a3981a (2026-08-15).
Data as JSON: /api/errors/7023149317ac0e60.
Report an issue: GitHub.