{
  "slug": "data-drift-summary",
  "name": "gizza-ai/data-drift-summary",
  "version": "0.1.0",
  "title": "Data Drift Summary — Compare Two CSV Datasets Column by Column — gizza.ai",
  "description": "Paste a baseline and a current CSV to get a per-column drift report: type, null rate, cardinality, range, new or missing categories and a PSI or JSD score.",
  "tags": [
    "data drift",
    "drift detection",
    "psi",
    "population stability index",
    "jensen-shannon",
    "csv compare",
    "dataset comparison",
    "schema drift",
    "data quality",
    "machine learning monitoring"
  ],
  "category": "data",
  "urls": {
    "page": "https://gizza.ai/tools/data-drift-summary/",
    "markdown": "https://gizza.ai/tools/data-drift-summary/index.md",
    "descriptor": "https://gizza.ai/tools/data-drift-summary/tool.json",
    "deep_link_example": "https://gizza.ai/tools/data-drift-summary/?reference=order_id%2Camount%2Ccountry%0A1%2C10%2CUS%0A2%2C12%2CUS%0A3%2C11%2CFR&current=order_id%2Camount%2Ccountry%0A1%2C40%2CUS%0A2%2C44%2CUS%0A3%2C%2CFR&delimiter=comma&header=true&columns=amount%2C%20country&method=psi&threshold=0.2&bins=10&max_categories=20&drift_share=0.5&ignore_case=true&sort=drift&format=table"
  },
  "cli": "gizza tool data-drift-summary \"order_id,amount,country\n1,10,US\n2,12,US\n3,11,FR\" 'current=order_id,amount,country\n1,40,US\n2,44,US\n3,,FR'",
  "tool": {
    "description": "Compare a reference (baseline) dataset against a current one, column by column, and report what changed: the inferred type on each side and whether it flipped, the null/missing rate and its delta, the distinct-value count, the numeric range and mean, the category values that are new in the current data and the ones that went missing, and a distribution drift score per column (Population Stability Index or Jensen-Shannon distance). Columns present on only one side are reported as schema drift, and a dataset-level verdict fires once a configurable share of columns has drifted. Accepts CSV/TSV text with comma, tab, semicolon or pipe delimiters, with or without a header row; outputs a readable table, a markdown report, structured JSON, or one CSV row per column.",
    "parameters": {
      "additionalProperties": false,
      "properties": {
        "bins": {
          "default": 10,
          "description": "Number of equal-population bins used to compare numeric columns, derived from the reference values. Default 10. More bins are more sensitive to small shifts.",
          "maximum": 50,
          "minimum": 2,
          "type": "integer"
        },
        "columns": {
          "default": "",
          "description": "Comma-separated allow-list of columns to report on, e.g. amount,country. Leave empty to report on every column present in both datasets.",
          "type": "string"
        },
        "current": {
          "description": "The new dataset to check for drift, with the same columns as the reference. Example: id,amount,country\\n1,12,DE",
          "type": "string"
        },
        "delimiter": {
          "default": "comma",
          "description": "Field delimiter used by both datasets. Default comma.",
          "enum": [
            "comma",
            "tab",
            "semicolon",
            "pipe"
          ],
          "type": "string"
        },
        "drift_share": {
          "default": 0.5,
          "description": "Share of compared columns that must drift before the whole dataset is flagged. Default 0.5, i.e. half the columns.",
          "maximum": 1,
          "minimum": 0,
          "type": "number"
        },
        "format": {
          "default": "table",
          "description": "Output: table (readable report), markdown (report table you can paste into a PR), json (structured report), or csv (one row per column).",
          "enum": [
            "table",
            "markdown",
            "json",
            "csv"
          ],
          "type": "string"
        },
        "header": {
          "default": true,
          "description": "Treat the first row as a header and match columns by name, so reordered columns still line up. Turn off to match by position (col1, col2, …).",
          "type": "boolean"
        },
        "ignore_case": {
          "default": false,
          "description": "Trim whitespace and fold case before comparing category values, so 'New York' and 'new york ' count as the same value instead of a new category.",
          "type": "boolean"
        },
        "max_categories": {
          "default": 20,
          "description": "A numeric column with more than this many distinct reference values is binned as a distribution; anything at or below it is compared as categories. Default 20.",
          "maximum": 1000,
          "minimum": 2,
          "type": "integer"
        },
        "method": {
          "default": "psi",
          "description": "Drift metric: psi = Population Stability Index (unbounded, 0.1 moderate / 0.2 significant), jsd = Jensen-Shannon distance (0 to 1, 0.1 is a common cutoff). Default psi.",
          "enum": [
            "psi",
            "jsd"
          ],
          "type": "string"
        },
        "reference": {
          "description": "The baseline (older) dataset as delimited text — for example the training set or last month's export. Example: id,amount,country\\n1,10,US",
          "type": "string"
        },
        "sort": {
          "default": "drift",
          "description": "Column order in the report: drift (highest score first, the default), name (alphabetical), or order (as they appear in the reference).",
          "enum": [
            "drift",
            "name",
            "order"
          ],
          "type": "string"
        },
        "threshold": {
          "default": 0.2,
          "description": "A column counts as drifted when its score reaches this value. Default 0.2 (the usual PSI significant-shift line); use 0.1 for jsd or for a stricter PSI check.",
          "minimum": 0,
          "type": "number"
        }
      },
      "required": [
        "reference",
        "current"
      ],
      "type": "object"
    }
  }
}