> ## Documentation Index
> Fetch the complete documentation index at: https://docs.brudcast.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Update a campaign

> Changes a campaign that is still in `draft` or `scheduled` status. Submitting `channels` replaces the channel set and deletes the content and per-channel statistics of any channel dropped from it, so a de-selected channel must have its content supplied again if it is re-selected. Submitting `recipients` replaces the whole audience selection, and submitting `abTest` replaces its variants but never creates a test that does not already exist. Requires the `campaigns:write` scope.



## OpenAPI

````yaml /api-reference/openapi.json patch /api/v1/user/campaigns/{id}
openapi: 3.0.0
info:
  title: Brudcast API
  version: 1.0.0
servers:
  - url: https://core-service.prod.brudcast.com
    description: Production
security: []
tags:
  - name: Analytics
    x-displayName: Analytics
  - name: Campaigns
    x-displayName: Campaigns
  - name: Contacts
    x-displayName: Contacts
  - name: Mailboxes
    x-displayName: Mailboxes
  - name: Messages
    x-displayName: Messages
  - name: Sender Identities
    x-displayName: Sender Identities
  - name: Sending Domains
    x-displayName: Sending Domains
  - name: Templates
    x-displayName: Templates
  - name: Webhooks
    x-displayName: Webhooks
paths:
  /api/v1/user/campaigns/{id}:
    patch:
      tags:
        - Campaigns
      summary: Update a campaign
      description: >-
        Changes a campaign that is still in `draft` or `scheduled` status.
        Submitting `channels` replaces the channel set and deletes the content
        and per-channel statistics of any channel dropped from it, so a
        de-selected channel must have its content supplied again if it is
        re-selected. Submitting `recipients` replaces the whole audience
        selection, and submitting `abTest` replaces its variants but never
        creates a test that does not already exist. Requires the
        `campaigns:write` scope.
      parameters:
        - in: header
          name: X-Organization-Id
          required: false
          description: >-
            Required when authenticating with an access token. Optional with an
            API key, whose own organization binding is authoritative; a value
            contradicting it is refused with 403.
          schema:
            type: string
            format: uuid
        - in: path
          name: id
          required: true
          schema:
            type: string
      requestBody:
        content:
          application/json:
            schema:
              type: object
              properties:
                name:
                  type: string
                  minLength: 1
                  maxLength: 255
                channels:
                  type: array
                  items:
                    enum:
                      - email
                      - sms
                      - whatsapp
                      - push
                  minItems: 1
                tags:
                  type: array
                  items:
                    type: string
                  nullable: true
                brief:
                  type: object
                  properties:
                    goal:
                      type: string
                      maxLength: 2000
                    audience:
                      type: string
                      maxLength: 500
                      nullable: true
                    keyInfo:
                      type: string
                      maxLength: 2000
                      nullable: true
                    tone:
                      type: string
                      maxLength: 100
                      nullable: true
                  required:
                    - goal
                  additionalProperties: false
                  nullable: true
                recipients:
                  type: object
                  properties:
                    listIds:
                      type: array
                      items:
                        type: string
                    segmentIds:
                      type: array
                      items:
                        type: string
                    contactIds:
                      type: array
                      items:
                        type: string
                    excludeListIds:
                      type: array
                      items:
                        type: string
                    excludeSegmentIds:
                      type: array
                      items:
                        type: string
                    excludeContactIds:
                      type: array
                      items:
                        type: string
                  additionalProperties: false
                emailContent:
                  type: object
                  properties:
                    fromName:
                      type: string
                    fromEmail:
                      type: string
                      format: email
                    replyTo:
                      type: string
                      format: email
                      nullable: true
                    subject:
                      type: string
                    previewText:
                      type: string
                      nullable: true
                    htmlContent:
                      type: string
                      nullable: true
                    plainTextContent:
                      type: string
                      nullable: true
                    editorMode:
                      enum:
                        - visual
                        - html
                        - plain
                    builderData:
                      anyOf:
                        - type: string
                        - type: number
                        - type: boolean
                        - type: array
                        - type: object
                  additionalProperties: false
                smsContent:
                  type: object
                  properties:
                    body:
                      type: string
                    senderId:
                      type: string
                  additionalProperties: false
                whatsappContent:
                  type: object
                  properties:
                    templateName:
                      type: string
                      minLength: 1
                    languageCode:
                      type: string
                    variables:
                      type: object
                      additionalProperties:
                        type: string
                      nullable: true
                    headerMediaUrl:
                      type: string
                      format: uri
                      nullable: true
                    bodyPreview:
                      type: string
                      nullable: true
                    phoneNumberId:
                      type: string
                      nullable: true
                    senderId:
                      type: string
                      nullable: true
                  additionalProperties: false
                pushContent:
                  type: object
                  properties:
                    title:
                      type: string
                    body:
                      type: string
                    imageUrl:
                      type: string
                      nullable: true
                    clickUrl:
                      type: string
                      nullable: true
                  additionalProperties: false
                settings:
                  type: object
                  properties:
                    trackOpens:
                      type: boolean
                    trackClicks:
                      type: boolean
                    utmEnabled:
                      type: boolean
                    utmSource:
                      type: string
                      nullable: true
                    utmMedium:
                      type: string
                      nullable: true
                    utmCampaign:
                      type: string
                      nullable: true
                    includeUnsubLink:
                      type: boolean
                    footerText:
                      type: string
                      nullable: true
                  additionalProperties: false
                abTest:
                  type: object
                  properties:
                    variable:
                      enum:
                        - subject
                        - content
                        - send_time
                    variantCount:
                      type: number
                      minimum: 2
                      maximum: 4
                    winnerCriteria:
                      enum:
                        - open_rate
                        - click_rate
                    testDurationHrs:
                      type: number
                      minimum: 0
                    samplePercent:
                      type: number
                      minimum: 1
                      maximum: 100
                    variants:
                      type: array
                      items:
                        type: object
                        properties:
                          variantLabel:
                            type: string
                          subject:
                            type: string
                          htmlContent:
                            type: string
                          sendTime:
                            type: string
                        required:
                          - variantLabel
                        additionalProperties: false
                  additionalProperties: false
              additionalProperties: false
      responses:
        '200':
          description: ''
          content:
            application/json:
              schema:
                type: object
                properties:
                  success:
                    type: boolean
                    example: true
                  message:
                    type: string
                  data:
                    $ref: '#/components/schemas/CampaignObject'
                required:
                  - success
                  - message
                  - data
        '400':
          description: >-
            The campaign is not in draft or scheduled status, or a submitted
            channel names a product the organization is not subscribed to
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
        '401':
          description: The credential is missing, malformed, revoked or expired
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
        '403':
          description: >-
            The key lacks the scope the endpoint requires, or the organization
            does not match the credential
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
        '404':
          description: No such campaign in the organization
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
        '422':
          description: The payload or query string failed validation
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ValidationErrorResponse'
        '429':
          description: >-
            Rate limit exceeded; retry after the number of seconds in
            `retryAfter`
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/RateLimitErrorResponse'
      security:
        - apiKey: []
        - apiKeyBearer: []
components:
  schemas:
    CampaignObject:
      type: object
      properties:
        id:
          type: string
          format: uuid
        organizationId:
          type: string
          format: uuid
        name:
          type: string
          example: Spring collection launch
        status:
          type: string
          enum:
            - draft
            - scheduled
            - sending
            - sent
            - completed
            - paused
            - cancelled
        type:
          type: string
          enum:
            - regular
            - ab_test
        channels:
          type: array
          items:
            type: string
            enum:
              - email
              - sms
              - whatsapp
              - push
          description: Channels the campaign is dispatched on
        tags:
          type: array
          items:
            type: string
        brief:
          $ref: '#/components/schemas/CampaignBrief'
          nullable: true
          description: >-
            The brief the content was generated from, null when the campaign was
            written by hand
        estimatedRecipients:
          type: number
          description: >-
            Reachable recipients across every channel, recomputed whenever the
            audience is edited. Stays 0 until an audience is attached
        channelReach:
          type: object
          additionalProperties:
            type: integer
          nullable: true
          description: >-
            The recipient estimate broken down by channel, null until an
            audience is attached
        scheduledAt:
          type: string
          format: date-time
          nullable: true
        sentAt:
          type: string
          format: date-time
          nullable: true
        completedAt:
          type: string
          format: date-time
          nullable: true
        createdAt:
          type: string
          format: date-time
        updatedAt:
          type: string
          format: date-time
        emailContent:
          $ref: '#/components/schemas/CampaignEmailContentObject'
        smsContent:
          $ref: '#/components/schemas/CampaignSmsContentObject'
        whatsappContent:
          $ref: '#/components/schemas/CampaignWhatsappContentObject'
        pushContent:
          $ref: '#/components/schemas/CampaignPushContentObject'
        recipients:
          type: array
          items:
            $ref: '#/components/schemas/CampaignRecipientSourceObject'
        settings:
          $ref: '#/components/schemas/CampaignSettingsObject'
        abTest:
          $ref: '#/components/schemas/CampaignAbTestObject'
        statistics:
          $ref: '#/components/schemas/CampaignStatisticsObject'
        channelStatistics:
          type: array
          items:
            $ref: '#/components/schemas/CampaignChannelStatisticsObject'
      required:
        - id
        - organizationId
        - name
        - status
        - type
        - channels
        - tags
        - brief
        - estimatedRecipients
        - channelReach
        - scheduledAt
        - sentAt
        - completedAt
        - createdAt
        - updatedAt
    ErrorResponse:
      type: object
      properties:
        success:
          type: boolean
          example: false
        message:
          type: string
          example: Resource not found
        code:
          type: string
          enum:
            - E_VALIDATION_ERROR
            - E_UNAUTHORIZED_ACCESS
            - E_UNAUTHORIZED
            - E_FORBIDDEN
            - E_INSUFFICIENT_SCOPE
            - E_ROW_NOT_FOUND
            - E_TOO_MANY_REQUESTS
            - E_BUSINESS_RULE_VIOLATION
            - E_CAMPAIGN_NOT_SENDABLE
            - INSUFFICIENT_CREDITS
            - SUBSCRIPTION_REQUIRED
          example: E_ROW_NOT_FOUND
      required:
        - success
        - message
        - code
    ValidationErrorResponse:
      type: object
      properties:
        success:
          type: boolean
          example: false
        message:
          type: string
          example: The payload is invalid
        code:
          type: string
          enum:
            - E_VALIDATION_ERROR
            - E_UNAUTHORIZED_ACCESS
            - E_UNAUTHORIZED
            - E_FORBIDDEN
            - E_INSUFFICIENT_SCOPE
            - E_ROW_NOT_FOUND
            - E_TOO_MANY_REQUESTS
            - E_BUSINESS_RULE_VIOLATION
            - E_CAMPAIGN_NOT_SENDABLE
            - INSUFFICIENT_CREDITS
            - SUBSCRIPTION_REQUIRED
          example: E_VALIDATION_ERROR
        errors:
          type: array
          items:
            $ref: '#/components/schemas/ValidationErrorItem'
      required:
        - success
        - message
        - code
        - errors
    RateLimitErrorResponse:
      type: object
      properties:
        success:
          type: boolean
          example: false
        message:
          type: string
          example: Too many requests
        code:
          type: string
          enum:
            - E_VALIDATION_ERROR
            - E_UNAUTHORIZED_ACCESS
            - E_UNAUTHORIZED
            - E_FORBIDDEN
            - E_INSUFFICIENT_SCOPE
            - E_ROW_NOT_FOUND
            - E_TOO_MANY_REQUESTS
            - E_BUSINESS_RULE_VIOLATION
            - E_CAMPAIGN_NOT_SENDABLE
            - INSUFFICIENT_CREDITS
            - SUBSCRIPTION_REQUIRED
          example: E_TOO_MANY_REQUESTS
        retryAfter:
          type: number
          example: 60
      required:
        - success
        - message
        - code
        - retryAfter
    CampaignBrief:
      type: object
      properties:
        goal:
          type: string
          example: Announce the spring collection to lapsed buyers
        audience:
          type: string
          nullable: true
          example: Customers who bought in 2024
        keyInfo:
          type: string
          nullable: true
        tone:
          type: string
          nullable: true
          example: friendly
      required:
        - goal
    CampaignEmailContentObject:
      type: object
      properties:
        id:
          type: string
          format: uuid
        campaignId:
          type: string
          format: uuid
        fromName:
          type: string
          example: Acme Marketing
        fromEmail:
          type: string
          format: email
          example: hello@mail.example.com
        replyTo:
          type: string
          format: email
          nullable: true
        subject:
          type: string
          example: Your spring picks are here
        previewText:
          type: string
          nullable: true
          description: Preheader text shown after the subject line in the inbox
        htmlContent:
          type: string
          nullable: true
        plainTextContent:
          type: string
          nullable: true
        editorMode:
          type: string
          enum:
            - visual
            - html
            - plain
        builderData:
          type: object
          additionalProperties: true
          nullable: true
          description: >-
            Visual builder state. In visual editor mode the HTML and plain text
            are re-rendered from `builderData.design` server side, so the stored
            content always matches this design
      required:
        - id
        - campaignId
        - fromName
        - fromEmail
        - replyTo
        - subject
        - previewText
        - htmlContent
        - plainTextContent
        - editorMode
        - builderData
    CampaignSmsContentObject:
      type: object
      properties:
        id:
          type: string
          format: uuid
        campaignId:
          type: string
          format: uuid
        body:
          type: string
          example: 'Spring picks are live. Shop now: https://exa.mp/le'
        senderId:
          type: string
          description: Alphanumeric sender ID the message is sent from
      required:
        - id
        - campaignId
        - body
        - senderId
    CampaignWhatsappContentObject:
      type: object
      properties:
        id:
          type: string
          format: uuid
        campaignId:
          type: string
          format: uuid
        templateName:
          type: string
          description: Name of the pre-approved Meta template the message is sent from
        languageCode:
          type: string
          example: en_US
        variables:
          type: object
          additionalProperties:
            type: string
          nullable: true
          description: Values substituted into the template placeholders
        headerMediaUrl:
          type: string
          nullable: true
        bodyPreview:
          type: string
          nullable: true
          description: >-
            Display-only copy of the template body; the template itself is
            authoritative
        phoneNumberId:
          type: string
          nullable: true
        senderId:
          type: string
          nullable: true
        createdAt:
          type: string
          format: date-time
        updatedAt:
          type: string
          format: date-time
      required:
        - id
        - campaignId
        - templateName
        - languageCode
        - variables
        - headerMediaUrl
        - bodyPreview
        - phoneNumberId
        - senderId
        - createdAt
        - updatedAt
    CampaignPushContentObject:
      type: object
      properties:
        id:
          type: string
          format: uuid
        campaignId:
          type: string
          format: uuid
        title:
          type: string
        body:
          type: string
        imageUrl:
          type: string
          nullable: true
        clickUrl:
          type: string
          nullable: true
      required:
        - id
        - campaignId
        - title
        - body
        - imageUrl
        - clickUrl
    CampaignRecipientSourceObject:
      type: object
      properties:
        id:
          type: string
          format: uuid
        campaignId:
          type: string
          format: uuid
        sourceType:
          type: string
          enum:
            - list
            - segment
            - contact
        sourceId:
          type: string
          format: uuid
          description: >-
            Identifier of the contact list, segment or contact this row points
            at
        sourceName:
          type: string
          nullable: true
          description: >-
            Name of the list, segment or contact the row points at, resolved
            only when the campaign is fetched individually. Reads 'Unknown' when
            the record it names no longer exists or belongs to another
            organization
        isExcluded:
          type: boolean
          description: >-
            Whether the source is subtracted from the audience rather than added
            to it
      required:
        - id
        - campaignId
        - sourceType
        - sourceId
        - isExcluded
    CampaignSettingsObject:
      type: object
      properties:
        id:
          type: string
          format: uuid
        campaignId:
          type: string
          format: uuid
        trackOpens:
          type: boolean
        trackClicks:
          type: boolean
        utmEnabled:
          type: boolean
        utmSource:
          type: string
          nullable: true
        utmMedium:
          type: string
          nullable: true
        utmCampaign:
          type: string
          nullable: true
        includeUnsubLink:
          type: boolean
        footerText:
          type: string
          nullable: true
      required:
        - id
        - campaignId
        - trackOpens
        - trackClicks
        - utmEnabled
        - utmSource
        - utmMedium
        - utmCampaign
        - includeUnsubLink
        - footerText
    CampaignAbTestObject:
      type: object
      properties:
        id:
          type: string
          format: uuid
        campaignId:
          type: string
          format: uuid
        variable:
          type: string
          enum:
            - subject
            - content
            - send_time
        variantCount:
          type: number
          example: 2
        winnerCriteria:
          type: string
          enum:
            - open_rate
            - click_rate
        testDurationHrs:
          type: number
          example: 4
        samplePercent:
          type: number
          example: 20
          description: >-
            Percentage of the audience the test is run against before the winner
            is picked
        variants:
          type: array
          items:
            $ref: '#/components/schemas/CampaignAbTestVariantObject'
      required:
        - id
        - campaignId
        - variable
        - variantCount
        - winnerCriteria
        - testDurationHrs
        - samplePercent
    CampaignStatisticsObject:
      type: object
      properties:
        id:
          type: string
          format: uuid
        campaignId:
          type: string
          format: uuid
        sent:
          type: number
        delivered:
          type: number
        opened:
          type: number
        uniqueOpened:
          type: number
        clicked:
          type: number
        uniqueClicked:
          type: number
        bounced:
          type: number
        hardBounced:
          type: number
        softBounced:
          type: number
        unsubscribed:
          type: number
        complained:
          type: number
        audienceSize:
          type: number
          nullable: true
          description: >-
            Audience frozen at dispatch, unaffected by later edits to the
            campaign audience
        channelReach:
          type: object
          additionalProperties:
            type: integer
          nullable: true
          description: Reach frozen at dispatch, keyed by channel
        openRate:
          type: number
          description: >-
            Unique opens over delivered as a percentage, 0 when nothing was
            delivered
        clickRate:
          type: number
          description: >-
            Unique clicks over delivered as a percentage, 0 when nothing was
            delivered
        bounceRate:
          type: number
          description: >-
            Hard and soft bounces together over sent as a percentage, 0 when
            nothing was sent
        unsubscribeRate:
          type: number
          description: >-
            Unsubscribes over delivered as a percentage, 0 when nothing was
            delivered
      required:
        - id
        - campaignId
        - sent
        - delivered
        - opened
        - uniqueOpened
        - clicked
        - uniqueClicked
        - bounced
        - hardBounced
        - softBounced
        - unsubscribed
        - complained
        - audienceSize
        - channelReach
        - openRate
        - clickRate
        - bounceRate
        - unsubscribeRate
    CampaignChannelStatisticsObject:
      type: object
      properties:
        id:
          type: string
          format: uuid
        campaignId:
          type: string
          format: uuid
        channel:
          type: string
          enum:
            - email
            - sms
            - whatsapp
            - push
        sent:
          type: number
        delivered:
          type: number
        opened:
          type: number
        uniqueOpened:
          type: number
        clicked:
          type: number
        uniqueClicked:
          type: number
        bounced:
          type: number
        hardBounced:
          type: number
        softBounced:
          type: number
        unsubscribed:
          type: number
        complained:
          type: number
        openRate:
          type: number
          description: >-
            Unique opens over delivered on this channel as a percentage, 0 when
            nothing was delivered
        clickRate:
          type: number
          description: >-
            Unique clicks over delivered on this channel as a percentage, 0 when
            nothing was delivered
        bounceRate:
          type: number
          description: >-
            Bounces over sent on this channel as a percentage, 0 when nothing
            was sent
        unsubscribeRate:
          type: number
          description: >-
            Unsubscribes over delivered on this channel as a percentage, 0 when
            nothing was delivered
        status:
          type: string
          enum:
            - draft
            - scheduled
            - sending
            - sent
            - completed
            - paused
            - cancelled
          nullable: true
          description: >-
            Dispatch status of this channel alone, null until the channel starts
            sending
        snapshotAt:
          type: number
          nullable: true
          description: >-
            When the counters were last reported by the delivery service, in
            epoch millis
        createdAt:
          type: string
          format: date-time
        updatedAt:
          type: string
          format: date-time
      required:
        - id
        - campaignId
        - channel
        - sent
        - delivered
        - opened
        - uniqueOpened
        - clicked
        - uniqueClicked
        - bounced
        - hardBounced
        - softBounced
        - unsubscribed
        - complained
        - openRate
        - clickRate
        - bounceRate
        - unsubscribeRate
        - status
        - snapshotAt
        - createdAt
        - updatedAt
    ValidationErrorItem:
      type: object
      properties:
        field:
          type: string
          example: emailAddress
        rule:
          type: string
          example: email
        message:
          type: string
          example: The emailAddress field must be a valid email address
      required:
        - field
        - rule
        - message
    CampaignAbTestVariantObject:
      type: object
      properties:
        id:
          type: string
          format: uuid
        abTestId:
          type: string
          format: uuid
        variantLabel:
          type: string
          example: A
        subject:
          type: string
          nullable: true
        htmlContent:
          type: string
          nullable: true
        sendTime:
          type: string
          format: date-time
          nullable: true
        isWinner:
          type: boolean
      required:
        - id
        - abTestId
        - variantLabel
        - subject
        - htmlContent
        - sendTime
        - isWinner
  securitySchemes:
    apiKey:
      type: apiKey
      in: header
      name: X-API-Key
      description: >-
        An organization API key, prefixed `bk_live_`. Takes precedence over
        `Authorization` when both are sent. The key is bound to one
        organization, and the scopes it was issued with are enforced per
        endpoint.
    apiKeyBearer:
      type: http
      scheme: bearer
      bearerFormat: bk_live_...
      description: >-
        The same organization API key sent as `Authorization: Bearer
        bk_live_...`. Accepted only when the value begins with `bk_` and no
        `X-API-Key` header is present.

````