{"record":{"id":"fda9cc99d4b29fd4","repo":"pbakaus/impeccable","slug":"entry-is-not-object","errorCode":null,"errorMessage":"entry is not object","messagePattern":"entry is not object","errorType":"exception","errorClass":"Error","httpStatus":null,"severity":"warning","filePath":"plugin/skills/impeccable/scripts/live/session-store.mjs","lineNumber":297,"sourceCode":"  if (snapshot.mountedVariants.length > 0) return 'mounted';\n  if (snapshot.mountFailures.length > 0) return 'failed';\n  if (snapshot.generationCompletedAt) return 'pending';\n  return null;\n}\n\nfunction rebuildSnapshotFromJournal(journalPath, id) {\n  let snapshot = baseSnapshot(id);\n  const diagnostics = [];\n  let nextSeq = 1;\n  if (!fs.existsSync(journalPath)) return { snapshot, diagnostics, nextSeq };\n\n  const lines = fs.readFileSync(journalPath, 'utf-8').split('\\n');\n  for (let i = 0; i < lines.length; i++) {\n    const line = lines[i];\n    if (!line.trim()) continue;\n    try {\n      const entry = JSON.parse(line);\n      if (!entry || typeof entry !== 'object') throw new Error('entry is not object');\n      if (Number.isInteger(entry.seq)) nextSeq = Math.max(nextSeq, entry.seq + 1);\n      snapshot = applyEvent(snapshot, entry);\n    } catch (err) {\n      diagnostics.push({\n        error: 'journal_parse_failed',\n        line: i + 1,\n        message: err.message,\n      });\n    }\n  }\n  snapshot.diagnostics = [...snapshot.diagnostics, ...diagnostics];\n  return { snapshot, diagnostics, nextSeq };\n}\n\nfunction applyEvent(snapshot, entry) {\n  const event = entry.event || entry;\n  const next = {\n    ...snapshot,","sourceCodeStart":279,"sourceCodeEnd":315,"githubUrl":"https://github.com/pbakaus/impeccable/blob/d14711ae3d1a1dd62dee61a358d27f107c51ccd0/plugin/skills/impeccable/scripts/live/session-store.mjs#L279-L315","documentation":"Thrown while replaying the session journal in rebuildSnapshotFromJournal when a non-blank journal line parses as JSON but yields a value that is not an object (e.g. a bare number or string). The message is collected as a diagnostic, not rethrown, so journal corruption is reported without aborting the rebuild.","triggerScenarios":"A session journal line under .impeccable/live that is valid JSON but not an object, such as `42` or `\"text\"`. Each offending line produces a journal_parse_failed diagnostic carrying this message.","commonSituations":"Concurrent writers appending partial/corrupt entries, a hand-edit that left a stray value, or a version-skewed writer emitting an unexpected shape.","solutions":["Inspect snapshot.diagnostics to find the offending line numbers in the journal file.","Delete or repair the corrupt lines in the journal; the next rebuild skips invalid entries.","If the journal is unrecoverable, archive it and let the session reinitialize from baseSnapshot."],"exampleFix":"// before: corrupt journal line `42` throws inside the try\n// the rebuild swallows it into diagnostics; snapshot is still returned\n\n// after: filter non-object lines when writing the journal\nfunction appendJournalEntry(filePath, entry) {\n  if (!entry || typeof entry !== 'object') return; // guard\n  fs.appendFileSync(filePath, JSON.stringify(entry) + '\\n');\n}","handlingStrategy":"try-catch","validationCode":"function isJournalLineValid(line) {\n  if (!line.trim()) return true;\n  try {\n    const v = JSON.parse(line);\n    return v !== null && typeof v === 'object';\n  } catch { return false; }\n}","typeGuard":"function isJournalEntry(value) {\n  return value !== null && typeof value === 'object' && (!('seq' in value) || Number.isInteger(value.seq));\n}","tryCatchPattern":"// rebuildSnapshotFromJournal already catches per-line and records diagnostics;\n// surface diagnostics to detect corruption:\nconst { snapshot, diagnostics } = rebuildSnapshotFromJournal(journalPath, id);\nif (diagnostics.length) console.warn('journal corruption:', diagnostics);","preventionTips":["Write journal entries atomically (one JSON object per line, append-only).","Validate entries with isJournalEntry before appending.","Periodically compact the journal so corruption surface area stays small."],"tags":["json","state","session","impeccable-live","diagnostic"],"backgroundTag":null,"analyzedSha":"d14711ae3d1a1dd62dee61a358d27f107c51ccd0","analyzedAt":"2026-08-13T00:52:25.771Z","schemaVersion":2},"datasetVersion":"2026-08-13T04:17:16.726Z"}