openapi: 3.0.3
info:
  title: Outbound Secure Operations API
  description: |
    Backend API service for querying and managing DynamoDB campaign data.
    
    ## Features
    - Stage-based table routing (dev, staging, prod)
    - Environment-based access control
    - API key authentication
    - Safe data purging for test records only
    
    ## Security
    All endpoints (except /api/hello and /api/debug) require API key authentication via the `x-api-key` header.
  version: 1.0.0
  contact:
    name: API Support
    url: https://github.com/dream-lab-ai/outbound-secure-operations

servers:
  - url: https://outbound-secure-operations.pamws.com
    description: Production deployment (main branch)
  - url: https://development.d3pjd0kqoz06yo.amplifyapp.com
    description: Development deployment (development branch)
  - url: http://localhost:3000
    description: Local development server

tags:
  - name: health
    description: Health check and debugging endpoints
  - name: campaigns
    description: Campaign and data query operations
  - name: purge
    description: Data purging operations (test data only)

paths:
  /api/hello:
    get:
      tags:
        - health
      summary: Health check
      description: Simple endpoint to verify the API is running. No authentication required.
      responses:
        '200':
          description: API is healthy
          content:
            application/json:
              schema:
                type: object
                properties:
                  message:
                    type: string
                    example: "Hello World"
                  timestamp:
                    type: string
                    format: date-time
                    example: "2025-11-13T05:30:00.000Z"
                  status:
                    type: string
                    example: "success"

  /api/debug:
    get:
      tags:
        - health
      summary: Environment debug info
      description: Returns environment configuration without exposing secrets. Useful for debugging deployment issues.
      responses:
        '200':
          description: Environment configuration info
          content:
            application/json:
              schema:
                type: object
                properties:
                  message:
                    type: string
                    example: "Environment debug info"
                  timestamp:
                    type: string
                    format: date-time
                  hasApiKey:
                    type: boolean
                    description: Whether API_KEY environment variable is set
                  hasEnvironment:
                    type: boolean
                    description: Whether ENVIRONMENT variable is set
                  environment:
                    type: string
                    example: "dev"
                  hasDynamoDbRegion:
                    type: boolean
                  dynamoDbRegion:
                    type: string
                    example: "us-east-1"
                  hasDynamoDbAccessKey:
                    type: boolean
                  hasDynamoDbSecretKey:
                    type: boolean
                  nodeEnv:
                    type: string
                    example: "production"
                  availableEnvVars:
                    type: array
                    items:
                      type: string
                    description: List of all environment variable names (no values)

  /api/campaigns:
    get:
      tags:
        - campaigns
      summary: Query campaigns and data
      description: |
        Query campaigns and related data from DynamoDB. Supports two modes:
        1. **List mode** - Returns all records for a clientOrgId (optionally filtered by type)
        2. **Detail mode** - Returns full campaign details including conversations and tasks (when campaignId is provided)
      security:
        - ApiKeyAuth: []
      parameters:
        - name: stage
          in: query
          required: true
          schema:
            type: string
            example: "dev"
          description: |
            Target stage determines the DynamoDB table (`Outbound-prototype-{stage}`).
            Access is controlled by ENVIRONMENT setting:
            - Dev environment can access any stage EXCEPT prod
            - Prod environment can ONLY access prod
        - name: clientOrgId
          in: query
          required: true
          schema:
            type: string
            example: "E2E_XTIME_f6919e98"
          description: Client organization ID to query
        - name: type
          in: query
          required: false
          schema:
            type: string
            enum: [CAMPAIGN, SCHEDULED_CAMPAIGN, TASK, POINTER, CLIENT, USER]
            example: "CAMPAIGN"
          description: Filter by record type prefix
        - name: campaignId
          in: query
          required: false
          schema:
            type: string
            example: "CAMPAIGN#RETENTION#NA#2025-11-05T18:28:22.371Z"
          description: Get full campaign details including conversations and tasks
      responses:
        '200':
          description: Successful query
          content:
            application/json:
              schema:
                oneOf:
                  - $ref: '#/components/schemas/ListResponse'
                  - $ref: '#/components/schemas/DetailResponse'
        '400':
          description: Bad request - missing required parameters
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Error'
        '401':
          description: Unauthorized - missing or invalid API key
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Error'
        '403':
          description: Forbidden - stage access denied
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/StageAccessError'
        '500':
          description: Internal server error
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Error'

  /api/purge:
    delete:
      tags:
        - purge
      summary: Purge all data for a clientOrgId
      description: |
        **⚠️ WARNING:** Deletes ALL data for a clientOrgId including:
        - All campaigns
        - All conversations (SMS, VOICE, and EMAIL)
        - All tasks
        - All scheduled campaigns
        - All pointer records
        
        **Note:** USER records are NOT deleted (would require table scan which is not permitted by IAM policy)
        
        **Safety checks:**
        1. Stage must be accessible based on environment
        2. clientOrgId MUST contain "OUTBOUND" (case-insensitive)
      security:
        - ApiKeyAuth: []
      parameters:
        - name: stage
          in: query
          required: true
          schema:
            type: string
            example: "dev"
          description: Target stage (determines table to purge from)
        - name: clientOrgId
          in: query
          required: true
          schema:
            type: string
            example: "HAROUN_OUTBOUND_NON_INTEGRATION"
          description: Client organization ID - MUST contain "OUTBOUND" to allow purging
      responses:
        '200':
          description: Data purged successfully
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/PurgeResponse'
        '400':
          description: Bad request - missing required parameters
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Error'
        '401':
          description: Unauthorized - missing or invalid API key
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Error'
        '403':
          description: Forbidden - stage access denied or non-OUTBOUND clientOrgId
          content:
            application/json:
              schema:
                oneOf:
                  - $ref: '#/components/schemas/StageAccessError'
                  - $ref: '#/components/schemas/PurgeNotAllowedError'
        '500':
          description: Internal server error
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Error'

components:
  securitySchemes:
    ApiKeyAuth:
      type: apiKey
      in: header
      name: x-api-key
      description: API key for authentication

  schemas:
    ListResponse:
      type: object
      required:
        - success
        - count
        - items
      properties:
        success:
          type: boolean
          example: true
        count:
          type: number
          example: 14
        items:
          type: array
          items:
            type: object
            description: DynamoDB record with PK, SK, and various attributes
        lastEvaluatedKey:
          type: object
          nullable: true
          description: Pagination key for fetching next page

    DetailResponse:
      type: object
      required:
        - success
        - campaign
        - conversations
        - tasks
      properties:
        success:
          type: boolean
          example: true
        campaign:
          type: object
          description: Campaign record with full details
          properties:
            campaignId:
              type: string
              example: "CAMPAIGN#RETENTION#NA#2025-11-05T18:28:22.371Z"
            status:
              type: string
              example: "ACTIVE"
            campaignType:
              type: string
              example: "RETENTION"
            modality:
              type: string
              example: "VOICE"
            customers:
              type: array
              items:
                type: object
        conversations:
          type: object
          properties:
            SMS:
              type: object
              properties:
                count:
                  type: number
                  example: 5
                items:
                  type: array
                  items:
                    type: object
                    description: SMS conversation record
            VOICE:
              type: object
              properties:
                count:
                  type: number
                  example: 2
                items:
                  type: array
                  items:
                    type: object
                    description: VOICE conversation record
            EMAIL:
              type: object
              properties:
                count:
                  type: number
                  example: 0
                items:
                  type: array
                  items:
                    type: object
                    description: EMAIL conversation record
            total:
              type: number
              example: 7
        tasks:
          type: object
          properties:
            count:
              type: number
              example: 1
            items:
              type: array
              items:
                type: object
                description: Task record

    PurgeResponse:
      type: object
      required:
        - success
        - message
        - stage
        - tableName
        - clientOrgId
        - summary
        - deletedItems
      properties:
        success:
          type: boolean
          example: true
        message:
          type: string
          example: "All data purged successfully"
        stage:
          type: string
          example: "dev"
        tableName:
          type: string
          example: "Outbound-prototype-dev"
        clientOrgId:
          type: string
          example: "OUTBOUND_TEST_12345"
        summary:
          type: object
          properties:
            totalDeleted:
              type: number
              example: 47
            gsiRecords:
              type: number
              example: 40
            conversations:
              type: number
              example: 7
            campaigns:
              type: number
              example: 3
        deletedItems:
          type: array
          items:
            type: object
            properties:
              PK:
                type: string
              SK:
                type: string

    Error:
      type: object
      required:
        - error
      properties:
        error:
          type: string
          example: "Bad request"
        message:
          type: string
          example: "clientOrgId query parameter is required"
        details:
          type: string
          description: Additional error details (for 500 errors)

    StageAccessError:
      type: object
      required:
        - error
        - message
        - stage
      properties:
        error:
          type: string
          example: "Stage access denied"
        message:
          type: string
          example: "Development environment cannot access 'prod' stage"
        stage:
          type: string
          example: "prod"

    PurgeNotAllowedError:
      type: object
      required:
        - error
        - message
        - clientOrgId
      properties:
        error:
          type: string
          example: "Purge not allowed"
        message:
          type: string
          example: "Can only purge test data (clientOrgId must contain \"OUTBOUND\")"
        clientOrgId:
          type: string
          example: "PRODUCTION_CLIENT_123"

security:
  - ApiKeyAuth: []

