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

# Create campaign

> Create or resolve a campaign from external source data

## Overview

Submit campaign source data keyed by `reference_id`. Requires a valid Bearer token from [`POST /auth/token`](/api-reference/endpoint/auth).

* If a campaign already exists for `reference_id`, the API returns **200** with `campaign_link`.
* If no campaign exists, the server stores context (including optional AI extraction), creates the campaign, and returns **201** with `campaign_link` and `campaign_id`.

Use `campaign_id` with [`GET /campaign`](/api-reference/endpoint/campaign/get) to fetch the campaign, its stats, and an app link.

## Request

### Headers

* `Authorization: Bearer {jwt_token}` (required — obtained using your issued partner credentials)
* `Content-Type: application/json`

### Body Parameters

<ParamField path="source" type="object" required>
  Container for campaign source metadata for your client
</ParamField>

<ParamField path="source.material" type="string[]" required>
  Image URLs for the campaign (at least one required)
</ParamField>

<ParamField path="source.name" type="string" required>
  Campaign display name (for example property address)
</ParamField>

<ParamField path="source.reference_id" type="string" required>
  Your stable external id for this campaign
</ParamField>

<ParamField path="source.target_url" type="string" required>
  Landing page URL (URI)
</ParamField>

### Example Request

```bash theme={null}
curl -X POST "https://app.targeter.tech/api/campaign" \
  -H "Authorization: Bearer YOUR_JWT_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{
    "source": {
      "material": [
        "https://example.com/image1.jpg"
      ],
      "name": "Majorstuenveien 14",
      "reference_id": "CLIENT-PROP-123456",
      "target_url": "https://client-website.no/property/123"
    }
  }'
```

## Response

### Success (201 — new campaign)

<ResponseField name="campaign_link" type="string">
  URL to the campaign in the Targeter app
</ResponseField>

<ResponseField name="campaign_id" type="string">
  Campaign id (hashed id, same encoding as in app URLs)
</ResponseField>

```json theme={null}
{
    "campaign_link": "https://app.targeter.tech/campaigns/AbC123xyz",
    "campaign_id": "AbC123xyz"
}
```

### Success (200 — existing campaign)

<ResponseField name="campaign_link" type="string">
  URL to the existing campaign in the Targeter app
</ResponseField>

```json theme={null}
{
    "campaign_link": "https://app.targeter.tech/campaigns/AbC123xyz"
}
```

## Error Responses

### 400 - Invalid request payload

```json theme={null}
{
    "error": "Missing required field: source.reference_id: Reference ID is required"
}
```

Validation errors on auth may include a `details` array with `path` and `message` per field.

### 401 - Unauthorized

Missing `Authorization` header, or invalid or expired token.

```json theme={null}
{
    "error": "Missing or invalid Authorization header"
}
```

```json theme={null}
{
    "error": "Invalid or expired token"
}
```

### 500 - Server Error

```json theme={null}
{
    "error": "Unexpected server error. Please try again later."
}
```

## Partner Usage Examples

### Real Estate Campaign for Client

```json theme={null}
{
    "source": {
        "material": [
            "https://example.com/property-photo.jpg"
        ],
        "name": "Ivan Bjørndals Gate 9",
        "reference_id": "123-456-789",
        "target_url": "https://megler.no/eiendom/123"
    }
}
```

### Marketing Campaign for Client

```json theme={null}
{
    "source": {
        "material": [
            "https://example.com/campaign-hero.jpg"
        ],
        "name": "Sommerkampanje Torshov",
        "reference_id": "TORSHOV-SUMMER-01012025-123",
        "target_url": "https://megler.no/kontor/torshov"
    }
}
```

## Partner Best Practices

* **Unique Reference IDs**: Use unique, meaningful reference IDs from your system to avoid conflicts
* **Client Landing Pages**: Verify that client target URLs are working and relevant
* **Image URLs**: Provide publicly accessible image URLs in `material`
* **Error Handling**: Always check response status codes and handle errors appropriately
* **Client Consent**: Ensure you have proper authorization to create campaigns on behalf of your clients


## OpenAPI

````yaml POST /campaign
openapi: 3.1.0
info:
  title: Targeter REST API
  description: >-
    Partner-facing HTTP API for Targeter: obtain a JWT and create or resolve
    campaigns from external systems.
  version: 1.2.0
  contact:
    name: Targeter API Support
servers:
  - url: https://app.targeter.tech/api
    description: >-
      Targeter platform instance (your base URL is provided with your
      credentials)
security:
  - BearerAuth: []
paths:
  /campaign:
    post:
      tags:
        - Campaigns
      summary: Create or resolve campaign from external source
      description: >
        Submit campaign source data keyed by `reference_id`. Requires a valid
        Bearer token from `/auth/token`.


        - If a campaign already exists for `reference_id`, returns **200** with
        `campaign_link`.

        - If no campaign exists, the server stores context, creates the
        campaign, and returns **201** with `campaign_link` and `campaign_id`
        when creation succeeds.
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required:
                - source
              properties:
                source:
                  type: object
                  description: Campaign source metadata for the client
                  required:
                    - material
                    - name
                    - reference_id
                    - target_url
                  properties:
                    material:
                      type: array
                      description: Image URLs for the campaign (at least one required)
                      minItems: 1
                      items:
                        type: string
                        format: uri
                      example:
                        - https://example.com/image1.jpg
                    name:
                      type: string
                      description: Campaign display name (e.g. property address)
                      example: Majorstuenveien 14
                    reference_id:
                      type: string
                      description: Your stable external id for this campaign
                      example: CLIENT-PROP-123456
                    target_url:
                      type: string
                      format: uri
                      description: Landing page URL
                      example: https://client-website.no/property/123
            example:
              source:
                material:
                  - https://example.com/image1.jpg
                name: Majorstuenveien 14
                reference_id: CLIENT-PROP-123456
                target_url: https://client-website.no/property/123
      responses:
        '200':
          description: Campaign already exists for the given reference_id
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/CampaignCreateExistingResponse'
        '201':
          description: New campaign created
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/CampaignCreateResponse'
        '400':
          description: Invalid request payload
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Error'
              example:
                error: >-
                  Missing required field: source.reference_id: Reference ID is
                  required
        '401':
          description: Missing Authorization header, or invalid or expired token
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Error'
              examples:
                missingHeader:
                  value:
                    error: Missing or invalid Authorization header
                invalidToken:
                  value:
                    error: Invalid or expired token
        '500':
          description: Internal server error
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Error'
              example:
                error: Unexpected server error. Please try again later.
components:
  schemas:
    CampaignCreateExistingResponse:
      type: object
      required:
        - campaign_link
      properties:
        campaign_link:
          type: string
          format: uri
          description: URL to the existing campaign in the Targeter app
          example: https://app.targeter.tech/campaigns/AbC123xyz
    CampaignCreateResponse:
      type: object
      required:
        - campaign_link
        - campaign_id
      properties:
        campaign_link:
          type: string
          format: uri
          description: URL to the campaign in the Targeter app
          example: https://app.targeter.tech/campaigns/AbC123xyz
        campaign_id:
          type: string
          description: Campaign id (hashed id, same encoding as in app URLs)
          example: AbC123xyz
    Error:
      type: object
      properties:
        error:
          type: string
          description: Error message
          example: Missing required field
        details:
          type: array
          description: Validation issues (Zod), when returned by the server
          items:
            type: object
            properties:
              path:
                type: array
                items:
                  type: string
                example:
                  - source
                  - reference_id
              message:
                type: string
                example: Reference ID is required
            required:
              - message
      required:
        - error
  securitySchemes:
    BearerAuth:
      type: http
      scheme: bearer
      bearerFormat: JWT
      description: >-
        Use `Authorization: Bearer <token>`. Obtain the token from `POST
        /auth/token`.

````