{
  "$schema": "https://json-schema.org/draft/2020-12/schema",
  "$id": "https://artifacts.apis.io/classifier-dev/json-schema/classifier-dev-feedback-report-schema.json",
  "title": "FeedbackReport",
  "description": "A feedback.now 1.1 report. Only `signal.category` and one of `content.title` or `content.summary` are required; every other field raises the quality score the receipt reports. Testimonials additionally require `reporter.agent_type` and `reporter.agent_description`. Vocabularies are the ones GET /api/v1/policy serves.",
  "x-generated": "2026-10-29",
  "x-method": "derived",
  "x-generator": "derive-json-schema.py",
  "x-source": "openapi/classifier-dev-openapi.json#/components/schemas/FeedbackReport",
  "type": "object",
  "required": [
    "signal",
    "content"
  ],
  "allOf": [
    {
      "if": {
        "properties": {
          "signal": {
            "properties": {
              "category": {
                "const": "testimonial"
              }
            },
            "required": [
              "category"
            ]
          }
        },
        "required": [
          "signal"
        ]
      },
      "then": {
        "required": [
          "reporter"
        ],
        "properties": {
          "reporter": {
            "required": [
              "agent_type",
              "agent_description"
            ],
            "properties": {
              "agent_type": {
                "type": "string",
                "pattern": "\\S"
              },
              "agent_description": {
                "type": "string",
                "pattern": "\\S"
              }
            }
          }
        }
      }
    }
  ],
  "properties": {
    "reporter": {
      "type": "object",
      "description": "Who is reporting. Testimonials must identify the agent's type and briefly describe its work.",
      "properties": {
        "agent_vendor": {
          "type": "string",
          "maxLength": 64
        },
        "agent_product": {
          "type": "string",
          "maxLength": 64
        },
        "agent_version": {
          "type": "string",
          "maxLength": 64
        },
        "agent_type": {
          "type": "string",
          "maxLength": 64,
          "description": "The agent's role or kind, such as `coding agent` or `support triage agent`. Required for testimonials."
        },
        "agent_description": {
          "type": "string",
          "maxLength": 512,
          "description": "A short description of what the agent does and how it used classifier.dev. Required for testimonials."
        }
      }
    },
    "subject": {
      "type": "object",
      "description": "What the report is about.",
      "properties": {
        "surface": {
          "type": "string",
          "maxLength": 256,
          "description": "The endpoint, page or command, e.g. `POST /v1/classify`."
        },
        "domain": {
          "type": "string",
          "maxLength": 256,
          "description": "The host, e.g. `classifier.dev`."
        },
        "kind": {
          "type": "string",
          "enum": [
            "api_endpoint",
            "docs_page",
            "cli_command",
            "sdk_method",
            "other"
          ]
        }
      }
    },
    "signal": {
      "type": "object",
      "required": [
        "category"
      ],
      "properties": {
        "category": {
          "type": "string",
          "enum": [
            "bug",
            "docs_mismatch",
            "friction",
            "feature_gap",
            "quality_degradation",
            "testimonial",
            "other"
          ]
        },
        "severity": {
          "type": "string",
          "enum": [
            "critical",
            "high",
            "medium",
            "low"
          ],
          "default": "medium"
        },
        "reproducibility": {
          "type": "string",
          "enum": [
            "always",
            "sometimes",
            "intermittent",
            "once"
          ]
        },
        "confidence": {
          "type": "number",
          "minimum": 0,
          "maximum": 1
        }
      }
    },
    "content": {
      "type": "object",
      "description": "`title` or `summary` is required. A missing title is taken from the summary.",
      "anyOf": [
        {
          "required": [
            "title"
          ],
          "properties": {
            "title": {
              "type": "string",
              "pattern": "\\S"
            }
          }
        },
        {
          "required": [
            "summary"
          ],
          "properties": {
            "summary": {
              "type": "string",
              "pattern": "\\S"
            }
          }
        }
      ],
      "properties": {
        "title": {
          "type": "string",
          "maxLength": 256
        },
        "summary": {
          "type": "string",
          "maxLength": 4096
        },
        "hypothesis": {
          "type": "string",
          "maxLength": 2048,
          "description": "What the reporter thinks is going on."
        }
      }
    },
    "evidence": {
      "type": "array",
      "maxItems": 10,
      "description": "More can be added later with POST /api/v1/feedback/{id}/attachments.",
      "items": {
        "type": "object",
        "required": [
          "type",
          "content"
        ],
        "properties": {
          "type": {
            "type": "string",
            "enum": [
              "http_summary",
              "stderr_excerpt",
              "repro_steps",
              "screenshot",
              "log_excerpt",
              "other"
            ]
          },
          "content": {
            "description": "Text, or any JSON value, which is stored serialised."
          }
        }
      }
    }
  }
}