openapi: "3.0.3"

info:
  title: SentryAgent.ai — Tenant Analytics
  version: 1.0.0
  description: |
    Tenant analytics endpoints for the SentryAgent.ai AgentIdP platform.

    Provides usage trend data, agent activity heatmaps, and per-agent usage summaries
    scoped to the authenticated organization (tenant).

    **All endpoints require a valid Bearer JWT.** Data is always scoped to the
    organization identified by the `organization_id` claim in the token.

    **Feature flag:** When `ANALYTICS_ENABLED=false` these routes return 404.

    **Available endpoints:**
    - `GET /analytics/tokens` — Daily token issuance trend (last N days)
    - `GET /analytics/agents/activity` — Agent activity heatmap by day-of-week + hour
    - `GET /analytics/agents` — Per-agent usage summary for the current month

servers:
  - url: http://localhost:3000/api/v1
    description: Local development server
  - url: https://api.sentryagent.ai/v1
    description: Production server

tags:
  - name: Analytics
    description: Tenant-scoped usage analytics and reporting

components:
  securitySchemes:
    BearerAuth:
      type: http
      scheme: bearer
      bearerFormat: JWT
      description: |
        JWT access token obtained via `POST /token`.
        Include as `Authorization: Bearer <token>`.

  schemas:
    TokenTrendDataPoint:
      type: object
      description: Token issuance count for a single calendar day.
      required:
        - date
        - count
      properties:
        date:
          type: string
          format: date
          description: Calendar date (UTC) in `YYYY-MM-DD` format.
          example: "2026-04-01"
        count:
          type: integer
          description: Number of OAuth 2.0 tokens issued on this date.
          minimum: 0
          example: 842

    TokenTrendResponse:
      type: object
      description: Daily token issuance trend for the last N days.
      required:
        - organizationId
        - days
        - data
      properties:
        organizationId:
          type: string
          format: uuid
          description: Organization the analytics data belongs to.
          example: "org-1234-5678-abcd-ef01"
        days:
          type: integer
          description: Number of days included in the trend window.
          example: 30
        data:
          type: array
          description: |
            Array of daily data points ordered by date ascending.
            Days with no token issuances have `count: 0`.
          items:
            $ref: '#/components/schemas/TokenTrendDataPoint'

    ActivityHeatmapCell:
      type: object
      description: |
        A single cell in the agent activity heatmap, identified by
        day-of-week (0 = Sunday) and hour of day (0–23 UTC).
      required:
        - dayOfWeek
        - hour
        - count
      properties:
        dayOfWeek:
          type: integer
          description: Day of week (0 = Sunday, 6 = Saturday).
          minimum: 0
          maximum: 6
          example: 1
        hour:
          type: integer
          description: Hour of day in UTC (0–23).
          minimum: 0
          maximum: 23
          example: 14
        count:
          type: integer
          description: Number of token issuances or API calls in this slot.
          minimum: 0
          example: 217

    AgentActivityResponse:
      type: object
      description: |
        Agent activity heatmap — shows when agents are most active
        by day-of-week and hour (UTC). Useful for identifying peak usage patterns.
      required:
        - organizationId
        - data
      properties:
        organizationId:
          type: string
          format: uuid
          example: "org-1234-5678-abcd-ef01"
        data:
          type: array
          description: |
            Array of heatmap cells. Contains only cells with `count > 0`.
            Maximum 168 cells (7 days × 24 hours).
          items:
            $ref: '#/components/schemas/ActivityHeatmapCell'

    AgentUsageSummary:
      type: object
      description: Per-agent usage summary for the current calendar month.
      required:
        - agentId
        - tokensIssued
        - apiCalls
      properties:
        agentId:
          type: string
          format: uuid
          description: UUID of the agent.
          example: "a1b2c3d4-e5f6-7890-abcd-ef1234567890"
        agentEmail:
          type: string
          format: email
          description: Email identifier of the agent.
          example: "screener-001@sentryagent.ai"
        tokensIssued:
          type: integer
          description: Number of tokens issued for this agent in the current month.
          minimum: 0
          example: 1204
        apiCalls:
          type: integer
          description: Total API calls made by this agent in the current month.
          minimum: 0
          example: 5432
        lastActiveAt:
          type: string
          format: date-time
          nullable: true
          description: Timestamp of the agent's last API activity. Null if no activity this month.
          example: "2026-04-07T08:45:00.000Z"

    AgentSummaryResponse:
      type: object
      description: Per-agent usage summary for the current month, across all agents in the organization.
      required:
        - organizationId
        - month
        - data
      properties:
        organizationId:
          type: string
          format: uuid
          example: "org-1234-5678-abcd-ef01"
        month:
          type: string
          description: Current billing month in `YYYY-MM` format.
          example: "2026-04"
        data:
          type: array
          description: Per-agent usage summaries, ordered by `tokensIssued` descending.
          items:
            $ref: '#/components/schemas/AgentUsageSummary'

    ErrorResponse:
      type: object
      description: Standard error response envelope.
      required:
        - code
        - message
      properties:
        code:
          type: string
          example: "UNAUTHORIZED"
        message:
          type: string
          example: "A valid Bearer token is required to access this resource."
        details:
          type: object
          additionalProperties: true

  responses:
    Unauthorized:
      description: Missing or invalid Bearer token.
      content:
        application/json:
          schema:
            $ref: '#/components/schemas/ErrorResponse'
          example:
            code: "UNAUTHORIZED"
            message: "A valid Bearer token is required to access this resource."

    InternalServerError:
      description: Unexpected server error.
      content:
        application/json:
          schema:
            $ref: '#/components/schemas/ErrorResponse'
          example:
            code: "INTERNAL_SERVER_ERROR"
            message: "An unexpected error occurred. Please try again later."

security:
  - BearerAuth: []

paths:
  /analytics/tokens:
    get:
      operationId: getTokenTrend
      tags:
        - Analytics
      summary: Get daily token issuance trend
      description: |
        Returns a daily breakdown of OAuth 2.0 token issuances for the authenticated
        organization over the last N days.

        The `days` parameter controls the window size (default: 30, max: 90).
        Days with no token activity are included with `count: 0`.

        Data is scoped to the `organization_id` from the Bearer token.
      parameters:
        - name: days
          in: query
          required: false
          description: Number of days to include in the trend window. Default: 30, max: 90.
          schema:
            type: integer
            minimum: 1
            maximum: 90
            default: 30
          example: 30
      responses:
        '200':
          description: Token trend data returned successfully.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/TokenTrendResponse'
              example:
                organizationId: "org-1234-5678-abcd-ef01"
                days: 7
                data:
                  - date: "2026-04-01"
                    count: 842
                  - date: "2026-04-02"
                    count: 967
                  - date: "2026-04-03"
                    count: 0
                  - date: "2026-04-04"
                    count: 1201
                  - date: "2026-04-05"
                    count: 1087
                  - date: "2026-04-06"
                    count: 953
                  - date: "2026-04-07"
                    count: 412
        '400':
          description: Invalid `days` parameter.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
              examples:
                tooLarge:
                  summary: Exceeds maximum
                  value:
                    code: "VALIDATION_ERROR"
                    message: "Query parameter `days` must not exceed 90."
                    details:
                      field: "days"
                      max: 90
                      provided: 120
                invalid:
                  summary: Non-positive integer
                  value:
                    code: "VALIDATION_ERROR"
                    message: "Query parameter `days` must be a positive integer."
                    details:
                      field: "days"
        '401':
          $ref: '#/components/responses/Unauthorized'
        '404':
          description: Analytics feature is not enabled on this instance.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
              example:
                code: "NOT_FOUND"
                message: "Analytics is not enabled on this instance."
        '500':
          $ref: '#/components/responses/InternalServerError'

  /analytics/agents/activity:
    get:
      operationId: getAgentActivity
      tags:
        - Analytics
      summary: Get agent activity heatmap
      description: |
        Returns agent activity aggregated by day-of-week (0 = Sunday) and hour of day (UTC).

        The heatmap shows when agents in the organization are most active,
        based on token issuances and API calls. Only cells with `count > 0` are returned.

        Data is scoped to the `organization_id` from the Bearer token.
        The heatmap covers the last 90 days of activity.
      responses:
        '200':
          description: Agent activity heatmap returned successfully.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/AgentActivityResponse'
              example:
                organizationId: "org-1234-5678-abcd-ef01"
                data:
                  - dayOfWeek: 1
                    hour: 9
                    count: 342
                  - dayOfWeek: 1
                    hour: 14
                    count: 217
                  - dayOfWeek: 2
                    hour: 10
                    count: 189
                  - dayOfWeek: 3
                    hour: 11
                    count: 405
                  - dayOfWeek: 4
                    hour: 14
                    count: 278
                  - dayOfWeek: 5
                    hour: 9
                    count: 121
        '401':
          $ref: '#/components/responses/Unauthorized'
        '404':
          description: Analytics feature is not enabled on this instance.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
              example:
                code: "NOT_FOUND"
                message: "Analytics is not enabled on this instance."
        '500':
          $ref: '#/components/responses/InternalServerError'

  /analytics/agents:
    get:
      operationId: getAgentSummary
      tags:
        - Analytics
      summary: Get per-agent usage summary
      description: |
        Returns per-agent token issuance counts and API call totals for the
        current calendar month, across all agents in the authenticated organization.

        Results are ordered by `tokensIssued` descending (most active agents first).

        Data is scoped to the `organization_id` from the Bearer token.
      responses:
        '200':
          description: Per-agent usage summary returned successfully.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/AgentSummaryResponse'
              example:
                organizationId: "org-1234-5678-abcd-ef01"
                month: "2026-04"
                data:
                  - agentId: "a1b2c3d4-e5f6-7890-abcd-ef1234567890"
                    agentEmail: "screener-001@sentryagent.ai"
                    tokensIssued: 1204
                    apiCalls: 5432
                    lastActiveAt: "2026-04-07T08:45:00.000Z"
                  - agentId: "b2c3d4e5-f6a7-8901-bcde-f12345678901"
                    agentEmail: "classifier-002@sentryagent.ai"
                    tokensIssued: 876
                    apiCalls: 3120
                    lastActiveAt: "2026-04-06T14:30:00.000Z"
                  - agentId: "c3d4e5f6-a7b8-9012-cdef-123456789012"
                    agentEmail: "router-003@sentryagent.ai"
                    tokensIssued: 0
                    apiCalls: 0
                    lastActiveAt: null
        '401':
          $ref: '#/components/responses/Unauthorized'
        '404':
          description: Analytics feature is not enabled on this instance.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
              example:
                code: "NOT_FOUND"
                message: "Analytics is not enabled on this instance."
        '500':
          $ref: '#/components/responses/InternalServerError'
