{
  "$schema": "https://json-schema.org/draft/2020-12/schema",
  "$id": "https://artifacts.apis.io/mailcheer-com/json-schema/mailcheer-com-campaign-update-schema.json",
  "title": "CampaignUpdate",
  "description": "The fields of `CampaignRequest`, all optional. Unknown fields are refused (`422`): a misspelled field ignored in silence would let the old subject go to the whole list. `content` and `text` together are refused. New content without `preheader` keeps the draft's.",
  "x-generated": "2026-10-31",
  "x-method": "derived",
  "x-generator": "derive-json-schema.py",
  "x-source": "openapi/mailcheer-com-openapi.json#/components/schemas/CampaignUpdate",
  "type": "object",
  "properties": {
    "name": {
      "type": "string",
      "minLength": 1,
      "maxLength": 160
    },
    "subject": {
      "type": "string",
      "maxLength": 400,
      "description": "The subject. It may stay empty on a draft, but the send will refuse it."
    },
    "preheader": {
      "type": "string",
      "maxLength": 400,
      "description": "Preview shown after the subject in the inbox."
    },
    "kind": {
      "type": "string",
      "maxLength": 40,
      "default": "newsletter",
      "description": "Your own classification label. Free text, no imposed value."
    },
    "from": {
      "type": "string",
      "maxLength": 320,
      "description": "The address of a sender **already registered** in the workspace — not any address on a verified domain, unlike an individual send. Unknown: 404, with the list of available addresses. `GET /api/v1/me` gives them in `senders`."
    },
    "sender_id": {
      "type": "string",
      "maxLength": 60,
      "description": "The sender's identifier, if you know it (`senders[].id` from `GET /api/v1/me`). Takes precedence over `from`.\n\nWith neither `from` nor `sender_id`, Mailcheer takes the workspace's default sender; failing that, if a single sender exists, that one. If several exist with no default, the campaign is created **without a sender** and it is the send that will fail: designate one."
    },
    "text": {
      "type": "string",
      "maxLength": 200000,
      "description": "The content in plain text — the form to prefer from code or from an agent. A blank line separates two paragraphs, `# ` at the start of a line makes a heading, `## ` a subheading. Ignored if `content` is provided."
    },
    "content": {
      "type": "object",
      "description": "The content in blocks, the editor's full form. Write this only if you are reusing the content of an existing campaign: to compose, `text` does the same job without your having to fabricate block identifiers.",
      "properties": {
        "preheader": {
          "type": "string"
        },
        "blocks": {
          "type": "array",
          "description": "Editor blocks, each with its `id` and its `type` (`heading`, `text`, …).",
          "items": {
            "type": "object",
            "additionalProperties": true
          }
        }
      }
    }
  },
  "additionalProperties": false
}