affaan-m/ECC · error · Error

Memory document ${sourcePath} is missing fields: ${missing.j

Error message

Memory document ${sourcePath} is missing fields: ${missing.join(', ')}.

What it means

Thrown by parseMemoryDocument() after parsing all frontmatter lines, when one or more of the 13 required FRONTMATTER_FIELDS (schema, id, title, kind, scope, trust, status, source_harness, target_harnesses, tags, links, created_at, updated_at) was not seen. The error message lists the missing object keys. Required-field enforcement prevents silent partial documents from entering the vault.

Source

Thrown at scripts/lib/memory-vault-format.js:274

  const closingMarker = /\r?\n---(?=\r?\n|$)/.exec(remainder);
  if (!closingMarker) {
    throw new Error(`Memory document ${sourcePath} has no closing frontmatter marker.`);
  }

  const frontmatterSource = remainder.slice(0, closingMarker.index);
  const parsed = frontmatterSource.split(/\r?\n/).reduce((state, line) => {
    const next = parseFrontmatterLine(line, sourcePath, state.seen);
    return {
      values: { ...state.values, [next.objectKey]: next.value },
      seen: new Set([...state.seen, next.objectKey]),
    };
  }, { values: {}, seen: new Set() });

  const missing = FRONTMATTER_FIELDS
    .map(([, objectKey]) => objectKey)
    .filter(objectKey => !parsed.seen.has(objectKey));
  if (missing.length > 0) {
    throw new Error(`Memory document ${sourcePath} is missing fields: ${missing.join(', ')}.`);
  }

  const afterMarker = remainder.slice(closingMarker.index + closingMarker[0].length);
  const body = afterMarker.replace(/^\r?\n/, '').replace(/\r?\n$/, '');
  return normalizeMemory({ ...parsed.values, body });
}

function findPotentialSecrets(value) {
  const text = typeof value === 'string' ? value : '';
  return SECRET_PATTERNS
    .filter(item => item.pattern.test(text))
    .map(item => item.label)
    .filter((label, index, labels) => labels.indexOf(label) === index);
}

module.exports = {
  MAX_BODY_BYTES,
  MAX_DOCUMENT_BYTES,

View on GitHub (pinned to 01e15490f0)

Solutions

  1. Read the error message — it lists exactly which object keys are missing (e.g. 'trust, links').
  2. Add each missing field with a valid JSON value: trust: "unreviewed", links: [].
  3. Author new files via saveMemory() so every field is populated by normalizeSaveInput().
  4. Keep a template file with all 13 fields and copy it as the starting point.

Example fix

// before — missing trust, links, tags
---
schema: "ecc.memory.v1"
id: "mem_x"
title: "x"
kind: "note"
scope: "project"
status: "active"
source_harness: "claude"
target_harnesses: ["all"]
created_at: "2024-08-12T00:00:00.000Z"
updated_at: "2024-08-12T00:00:00.000Z"
---

// after — add the missing fields
trust: "unreviewed"
tags: []
links: []
Defensive patterns

Strategy: validation

Validate before calling

const REQUIRED = ['schema','id','title','kind','scope','trust','status','source_harness','target_harnesses','tags','links','created_at','updated_at'];
const present = new Set(parsedFrontmatterLines.map(l => l.slice(0, l.indexOf(':')).trim()));
const missing = REQUIRED.filter(k => !present.has(k));
if (missing.length) throw new Error(`missing frontmatter fields: ${missing.join(', ')}`);

Prevention

When it happens

Trigger: A hand-written file that omits 'trust:' (an easy-to-forget field). A migration from a v0 schema that lacked tags/links. An editor that dropped a field with an empty value. A copy-paste that lost the last line. AI agent that produced an incomplete document.

Common situations: Authoring memories by hand without a template. Ad-hoc export from another tool that did not emit all fields. Refactor that removed a field by accident. Merge conflict where one side deleted a line.

Related errors


AI-assisted analysis of affaan-m/ECC@01e15490f0 (2026-08-13). Data as JSON: /api/errors/9563e745df911592. Report an issue: GitHub.