{"record":{"id":"26a9036018da99be","repo":"JuliusBrussee/caveman","slug":"at-appears-twice-in-the-dataset","errorCode":null,"errorMessage":"${at} appears twice in the dataset","messagePattern":"(.+?) appears twice in the dataset","errorType":"exception","errorClass":"Error","httpStatus":null,"severity":"error","filePath":"packages/shared/contracts/scripts/validate-continuous-improvement.mjs","lineNumber":259,"sourceCode":"    }\n\n    // Every dataset case — recorded or generated — must name a real analysis\n    // unit of this case's own task family, and its generator and perturbation\n    // must agree. A generated case whose source unit cannot be resolved would be\n    // invented evidence wearing an adversarial label.\n    const dataset = item.eval_pack.dataset;\n    const generatorPerturbation = new Map([\n      [\"recorded_case.v1\", \"none\"],\n      [\"boundary_guard_threshold.v1\", \"guard_threshold_boundary\"],\n      [\"adversarial_misleading_tool_output.v1\", \"misleading_tool_output\"],\n      [\"adversarial_stale_input.v1\", \"stale_input\"],\n    ]);\n    const roleCounts = { target_failure: 0, prior_success: 0, boundary: 0, adversarial: 0 };\n    const recordedSources = new Set();\n    const datasetCaseIDs = new Set();\n    for (const entry of dataset.cases) {\n      const at = `${where} dataset case ${entry.id}`;\n      if (datasetCaseIDs.has(entry.id)) throw new Error(`${at} appears twice in the dataset`);\n      datasetCaseIDs.add(entry.id);\n      if (!unitsByID.has(entry.source_unit_id)) throw new Error(`${at} names source unit ${entry.source_unit_id} that is not an analysis unit of this report`);\n      if (!familyUnits.has(entry.source_unit_id)) throw new Error(`${at} names source unit ${entry.source_unit_id} that is not a member of task family ${family.id}`);\n      if (generatorPerturbation.get(entry.generator) !== entry.perturbation) {\n        throw new Error(`${at} generator ${entry.generator} disagrees with perturbation ${entry.perturbation}`);\n      }\n      if (entry.perturbation === \"none\" && entry.id !== entry.source_unit_id) {\n        throw new Error(`${at} replays a recorded flow but is not identified by its source unit`);\n      }\n      if (entry.perturbation !== \"none\" && entry.id !== `${entry.generator}:${entry.source_unit_id}`) {\n        throw new Error(`${at} is a generated case whose id does not name its generator and source unit`);\n      }\n      roleCounts[entry.role] += 1;\n      if (entry.role === \"target_failure\" || entry.role === \"prior_success\") recordedSources.add(entry.source_unit_id);\n    }\n    for (const entry of dataset.cases) {\n      // Leakage: a generated case must not perturb a unit the manifest already\n      // replays unperturbed.","sourceCodeStart":241,"sourceCodeEnd":277,"githubUrl":"https://github.com/JuliusBrussee/caveman/blob/27d5a3981a347890211bb1bf2439e5c821a63bc9/packages/shared/contracts/scripts/validate-continuous-improvement.mjs#L241-L277","documentation":"Thrown when two entries in eval_pack.dataset.cases share the same id. Dataset case ids are the join key between the composed dataset, the role lists and the replay manifest; duplicates would double-count roles and make replay_case_ids ambiguous.","triggerScenarios":"Appending the same case entry twice during dataset assembly; two generators producing colliding ids (only possible when the id convention — generator:source_unit_id or bare source_unit_id — is violated); copy-paste of an entry with a hand-invented id.","commonSituations":"Manual dataset editing; merging dataset fragments from two drafts without deduplication.","solutions":["Delete the duplicate entry so every id in dataset.cases is unique.","If two distinct cases collided, fix their ids to follow the convention: source_unit_id for recorded (perturbation \"none\") cases, `${generator}:${source_unit_id}` for generated cases.","Audit dataset.replay_case_ids and the role lists (target_failure_cases, boundary_cases, generated_cases) for the same duplication."],"exampleFix":"// before\ndataset.cases: [{id:\"u-1\",...},{id:\"u-1\",...}]\n\n// after\ndataset.cases: [{id:\"u-1\",...},{id:\"adversarial_stale_input.v1:u-2\",...}]","handlingStrategy":"validation","validationCode":"const ids = dataset.cases.map((c) => c.id);\nconst unique = new Set(ids).size === ids.length;","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Compute dataset case ids by the fixed convention (recorded: source_unit_id; generated: `${generator}:${source_unit_id}`) instead of inventing them.","Deduplicate on id whenever merging dataset fragments."],"tags":["validation","dataset","deduplication"],"backgroundTag":null,"analyzedSha":"27d5a3981a347890211bb1bf2439e5c821a63bc9","analyzedAt":"2026-08-15T09:26:11.751Z","schemaVersion":2},"datasetVersion":"2026-08-15T17:31:12.345Z"}