{
  "$schema": "http://json-schema.org/draft-07/schema#",
  "$id": "https://peaks-loop.dev/schemas/replay-fixture.schema.json",
  "title": "Replay Fixture Metadata",
  "description": "Meta envelope for v2.14.0 G1 fixture-replay anti-fake-green test fixtures. Records the CLI command that produced the fixture, its source origin, sanitization report, and SHA-256 checksum. Every fixture under tests/fixtures/replay/ MUST have a co-located fixture.meta.json that validates against this schema.",
  "type": "object",
  "required": [
    "schemaVersion",
    "fixtureId",
    "envelopeKind",
    "producer",
    "producerVersion",
    "sourceOrigin",
    "capturedAt",
    "sanitization",
    "checksum",
    "edgeCases"
  ],
  "additionalProperties": false,
  "properties": {
    "schemaVersion": {
      "type": "integer",
      "const": 1,
      "description": "Schema version. Bump on breaking changes; old fixtures remain valid when read with backward-compat logic."
    },
    "fixtureId": {
      "type": "string",
      "pattern": "^[a-z0-9][a-z0-9-]{2,80}$",
      "description": "Stable fixture identifier (lowercase + dashes). Matches the fixture basename (without extension)."
    },
    "envelopeKind": {
      "type": "string",
      "enum": [
        "audit-security",
        "audit-perf",
        "karpathy-review",
        "mut-report",
        "qa-report",
        "prd-handoff"
      ],
      "description": "The on-disk envelope kind this fixture represents. Maps 1:1 to the parser used in replay."
    },
    "producer": {
      "type": "string",
      "const": "peaks-fixture-capture-cli",
      "description": "AC-1.4: every fixture MUST be produced by the peaks fixture capture CLI. Hard-coded constant — hand-written fixtures are forbidden."
    },
    "producerVersion": {
      "type": "string",
      "pattern": "^2\\.14\\.0$",
      "description": "CLI version that produced this fixture."
    },
    "sourceOrigin": {
      "type": "object",
      "required": ["kind", "path"],
      "additionalProperties": false,
      "properties": {
        "kind": {
          "type": "string",
          "enum": ["historical-artifact", "derived-variant"],
          "description": "historical-artifact = copied verbatim from .peaks/_runtime/<sid>/...; derived-variant = produced by the CLI's --variant-from <fixture> --variant <edge-case> sub-mode."
        },
        "path": {
          "type": "string",
          "description": "POSIX path to the source. For historical-artifact this is the original on-disk path; for derived-variant this is the parent fixture's path."
        },
        "changeId": {
          "type": ["string", "null"],
          "description": "Source change-id (e.g. v2-13-2-aggregate-verdict-dedup)."
        },
        "sessionId": {
          "type": ["string", "null"],
          "description": "Source session-id (e.g. 2026-06-27-session-83acf5)."
        },
        "parentFixtureId": {
          "type": ["string", "null"],
          "description": "For derived-variant, the fixtureId of the parent fixture this variant was derived from."
        },
        "variantCommand": {
          "type": ["string", "null"],
          "description": "For derived-variant, the CLI sub-mode invoked (e.g. 'chinese-colon', 'crlf-frontmatter', 'empty-body', 'multi-findings', 'double-format')."
        }
      }
    },
    "capturedAt": {
      "type": "string",
      "format": "date-time",
      "description": "ISO-8601 timestamp of capture."
    },
    "sanitization": {
      "type": "object",
      "required": ["passed", "rulesApplied", "issues"],
      "additionalProperties": false,
      "properties": {
        "passed": {
          "type": "boolean",
          "description": "true when all sanitize rules succeeded; false blocks the fixture from being committed."
        },
        "rulesApplied": {
          "type": "array",
          "items": {
            "type": "string",
            "enum": [
              "cookie-redaction",
              "token-redaction",
              "sso-url-redaction",
              "personal-email-redaction",
              "username-path-segment-redaction"
            ]
          },
          "description": "AC-1.5: 5 sanitize rule names that MUST be applied."
        },
        "issues": {
          "type": "array",
          "items": {
            "type": "object",
            "required": ["rule", "match", "position"],
            "additionalProperties": false,
            "properties": {
              "rule": { "type": "string" },
              "match": { "type": "string", "description": "Sanitized-redacted form (e.g. <REDACTED-cookie>)." },
              "position": { "type": "integer", "minimum": 0 }
            }
          }
        }
      }
    },
    "checksum": {
      "type": "object",
      "required": ["algorithm", "value"],
      "additionalProperties": false,
      "properties": {
        "algorithm": { "type": "string", "const": "sha256" },
        "value": {
          "type": "string",
          "pattern": "^[a-f0-9]{64}$",
          "description": "SHA-256 hex digest of the sanitized fixture body (excluding fixture.meta.json)."
        }
      }
    },
    "edgeCases": {
      "type": "array",
      "items": {
        "type": "string",
        "enum": [
          "chinese-colon",
          "yaml-frontmatter-variation",
          "double-format",
          "empty-body",
          "multi-findings",
          "historical-canonical"
        ]
      },
      "minItems": 1,
      "description": "AC-1.2: each fixture MUST hit ≥1 of the 5 v2.13.x historical edge cases (or 'historical-canonical' for the unmodified ship artifact)."
    }
  }
}
