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

# Correlate any pipeline id across the pipeline

> Top-level alias: GET /admin/api/search/correlate/{id}. Readable by any role.



## OpenAPI

````yaml /openapi.json get /admin/api/projects/{pid}/search/correlate/{id}
openapi: 3.1.0
info:
  title: Hookie API
  version: 1.0.0
  summary: Capture, route and deliver webhooks.
  description: >-
    Hookie exposes three HTTP surfaces.


    **Ingest + streaming** is the public plane. A path-form endpoint URL
    authenticates by its own high-entropy slug — there is no key, token or
    cookie — and an `ik_live_…` ingest key authenticates the `/v1/*` routes.
    Whenever the URL names a dataset the payload is stored whole into it;
    project mapping rules are evaluated on exactly one shape, `POST
    /v1/ingest/{ingest_key}` with no dataset segment.


    **The customer portal API** is a separate, token-authed surface for your end
    customers, scoped to one portal and one customer.


    **The admin API** drives the console. It accepts either a browser session or
    an OAuth bearer token from a connected coding agent — the same routes, the
    same validation, the same audit trail. An agent's authority is its user's
    workspace role narrowed to the scopes granted in the console.


    **A refused agent is told how to proceed.** An agent's grant is one rung of
    a ladder — `hookie:read` < `hookie:write` < `hookie:manage` — and a call
    above it answers 403 with `code: "agent_scope_insufficient"`, the
    `required_scope`, the `granted_scopes` and a `manage_url` to the console
    page where its user widens it. When the user's own role is the limit the
    code is `insufficient_role` and there is no link, because no grant can
    exceed the user; billing, platform admin, managing connected agents and
    destination signing secrets answer `agent_not_permitted` at every scope. A
    human in the console still reads `Insufficient role`.


    **A suspended workspace** (an operator action, for abuse or non-payment)
    answers every surface with 403 and `reason: "workspace_suspended"`: ingest
    (endpoint URLs and ingest keys), `/v1/data` and `/v1/stream` refuse before
    anything is stored or counted, and every admin API write — console, OAuth
    agent or hosted MCP alike — is refused except billing, platform admin,
    connected-agent management and the POST-bodied searches. The customer portal
    API is read-only in the same way: destination writes answer 403
    `workspace_suspended`. Reads keep working. Nothing is sent while it is
    suspended: pending deliveries are paused, workflow runs already under way
    are paused, open `/v1/stream` connections are closed, and cron triggers,
    database sources and WebSocket listeners stop. Reinstating sends the paused
    deliveries, resumes the paused workflow runs where they stopped, and resumes
    the rest; no stored data is lost.


    This document is generated from the request handlers and adversarially
    verified against them.
  contact:
    name: Hookie
    url: https://hookie.ai
  license:
    name: Proprietary
    url: https://hookie.ai/legal/terms
servers:
  - url: https://app.hookie.ai
    description: Production
  - url: https://app.preview.hookie.ai
    description: Preview
security: []
tags:
  - name: Ingest
    description: Send events to Hookie.
  - name: Streaming
    description: Tail events in real time over SSE or WebSocket.
  - name: Portal
    description: Token-authed surface for your end customers.
  - name: Projects
    description: Projects and their settings.
  - name: Routing
    description: Rules, endpoints, datasets and records.
  - name: Delivery
    description: Destinations, deliveries and replay.
  - name: Workflows
    description: Multi-step workflows, triggers and AI agents.
  - name: Observability
    description: Search, correlation, stats and the audit log.
  - name: Workspace
    description: Members, connected agents, SSO and billing.
  - name: Data API
    description: >-
      Read-only access to the datasets and columns a project exposes, with
      per-project keys.
  - name: Broadcast Logs
    description: >-
      Forward a project's logs and traces over OTLP/HTTP (JSON) to Datadog,
      Grafana Cloud, an OpenTelemetry Collector, PostHog or Sentry.
paths:
  /admin/api/projects/{pid}/search/correlate/{id}:
    get:
      tags:
        - Search
      summary: Correlate any pipeline id across the pipeline
      description: >-
        Top-level alias: GET /admin/api/search/correlate/{id}. Readable by any
        role.
      operationId: correlateById
      parameters:
        - name: pid
          in: path
          required: true
          description: Project id (UUID) belonging to the caller workspace.
          schema:
            type: string
        - name: id
          in: path
          required: true
          description: >-
            A record, submission, delivery or AI run id. A record id is resolved
            to its submission; a delivery or AI run id to the record it belongs
            to (a replay's `#replay:<n>` suffix is ignored) and then to its
            submission.
          schema:
            type: string
      responses:
        '200':
          description: >-
            The whole chain: the submission (or null when only records matched),
            every record produced from it, and the deliveries, AI runs and
            workflow runs keyed off those record ids.
          content:
            application/json:
              schema:
                type: object
                required:
                  - correlation_id
                  - submission
                  - records
                  - deliveries
                  - ai_runs
                  - matched
                  - workflow_runs
                properties:
                  correlation_id:
                    type: string
                    description: The resolved submission id.
                  submission:
                    type:
                      - object
                      - 'null'
                    properties:
                      id:
                        type: string
                      received_at:
                        type: string
                        format: date-time
                      source:
                        type:
                          - string
                          - 'null'
                      forward_status:
                        type:
                          - string
                          - 'null'
                      payload:
                        type: string
                        description: Truncated to 2000 characters.
                      request:
                        type:
                          - object
                          - 'null'
                        description: >-
                          The HTTP request the event arrived in (ING-3, #193).
                          null for an event stored before #193, or one that did
                          not arrive over HTTP (a polled database row, a cron or
                          WebSocket trigger). Credentials are never stored:
                          Authorization, Proxy-Authorization, Cookie and any
                          header or query parameter named like a credential
                          (key, api-key, token, secret, password, session, auth)
                          is stored as "[redacted]"; Cloudflare and proxy hop
                          headers (cf-*, x-forwarded-*, x-real-ip,
                          true-client-ip, cdn-loop, host) are dropped.
                        required:
                          - method
                          - headers
                          - query
                          - content_type
                          - source_ip
                        properties:
                          method:
                            type:
                              - string
                              - 'null'
                            example: POST
                          headers:
                            type: object
                            additionalProperties:
                              type: string
                            description: >-
                              Lowercased header names. At most 64 headers, each
                              value cut at 1024 characters, about 8 KB in all.
                            example:
                              x-github-event: push
                              user-agent: GitHub-Hookshot/abc
                              authorization: '[redacted]'
                          query:
                            type:
                              - string
                              - 'null'
                            description: >-
                              The query string without its '?', at most 2048
                              characters.
                            example: topic=orders
                          content_type:
                            type:
                              - string
                              - 'null'
                            description: >-
                              The Content-Type header as sent, parameters
                              included.
                          source_ip:
                            type:
                              - string
                              - 'null'
                            description: CF-Connecting-IP.
                      endpoint_id:
                        type:
                          - string
                          - 'null'
                        description: The endpoint (webhook id) it arrived through (#193).
                      dedup_source:
                        type:
                          - string
                          - 'null'
                        enum:
                          - idempotency-key
                          - standard-webhooks
                          - svix
                          - github
                          - shopify
                          - gitlab
                          - twilio
                          - linear
                          - twitch
                          - atlassian
                          - stripe
                          - slack
                          - null
                        description: >-
                          What its dedup key came from, if it had one (ING-9,
                          #193).
                  records:
                    type: array
                    items:
                      type: object
                      required:
                        - id
                        - dataset
                        - source
                        - received_at
                      properties:
                        id:
                          type: string
                        dataset:
                          type: string
                        source:
                          type:
                            - string
                            - 'null'
                        received_at:
                          type: string
                          format: date-time
                  deliveries:
                    type: array
                    items:
                      type: object
                      required:
                        - id
                        - destination_id
                        - event_id
                        - status
                        - response_code
                        - response_ms
                        - created_at
                        - destination_name
                        - dataset
                        - attempts
                        - next_retry_at
                        - error
                        - updated_at
                      properties:
                        id:
                          type: string
                        destination_id:
                          type: string
                        event_id:
                          type: string
                        status:
                          type: string
                        response_code:
                          type:
                            - integer
                            - 'null'
                        response_ms:
                          type:
                            - integer
                            - 'null'
                        created_at:
                          type: string
                          format: date-time
                        destination_name:
                          type:
                            - string
                            - 'null'
                          description: >-
                            The destination's name; null when it has been
                            deleted.
                        dataset:
                          type: string
                        attempts:
                          type: integer
                        next_retry_at:
                          type:
                            - string
                            - 'null'
                          format: date-time
                        error:
                          type:
                            - string
                            - 'null'
                        updated_at:
                          type:
                            - string
                            - 'null'
                          format: date-time
                  ai_runs:
                    type: array
                    items:
                      type: object
                      required:
                        - id
                        - trigger_id
                        - event_id
                        - status
                        - model
                        - created_at
                        - finished_at
                      properties:
                        id:
                          type: string
                        trigger_id:
                          type:
                            - string
                            - 'null'
                        event_id:
                          type:
                            - string
                            - 'null'
                        status:
                          type: string
                        model:
                          type:
                            - string
                            - 'null'
                        created_at:
                          type: string
                          format: date-time
                        finished_at:
                          type:
                            - string
                            - 'null'
                          format: date-time
                  matched:
                    type: string
                    enum:
                      - record
                      - submission
                      - delivery
                      - ai_run
                    description: Which kind of id was looked up.
                  workflow_runs:
                    type: array
                    description: >-
                      Workflow runs these records started (a run's
                      correlation_id is its entry record's id), oldest first, at
                      most 100 (#196).
                    items:
                      type: object
                      required:
                        - id
                        - workflow_id
                        - workflow_name
                        - state
                        - record_id
                        - created_at
                      properties:
                        id:
                          type: string
                        workflow_id:
                          type: string
                        workflow_name:
                          type:
                            - string
                            - 'null'
                        state:
                          type: string
                        record_id:
                          type: string
                        created_at:
                          type: string
        '400':
          description: correlation id required (the id path segment is missing).
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Error'
        '401':
          description: >-
            Not signed in, or the agent bearer token is invalid, unknown or
            revoked.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Error'
        '403':
          description: >-
            Email domain not allowed for the workspace, or an agent token
            granted no Hookie scope.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Error'
        '404':
          description: >-
            No record, submission, delivery or AI run with that id in this
            project.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Error'
        '405':
          description: Method not allowed - correlate is GET only.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Error'
        '500':
          description: Internal error.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Error'
      security:
        - session: []
        - bearerAuth: []
components:
  schemas:
    Error:
      type: object
      required:
        - error
      properties:
        error:
          type: string
          description: Human-readable reason.
        retry_after:
          type: integer
          description: Seconds to wait. Present on 429.
        upgrade_url:
          type: string
          format: uri
          description: Present only on a monthly-quota 429.
        reason:
          type: string
          description: >-
            Machine-readable reason, where the status alone is ambiguous.
            `workspace_suspended` (403): the workspace is suspended;
            `delivery_allowance_exhausted` (429): a replay was refused because
            the monthly delivery allowance is used. `endpoint_disabled` (503):
            the endpoint is switched off; `handshake_failed`: a provider
            URL-verification challenge could not be answered (#193).
        code:
          type: string
          enum:
            - agent_scope_insufficient
            - insufficient_role
            - agent_not_permitted
          description: >-
            Present on a 403 to an OAuth-connected agent.
            `agent_scope_insufficient`: the agent's grant is below what the call
            needs, and widening it would let the call through (see
            `required_scope` and `manage_url`). `insufficient_role`: the user's
            OWN workspace role does not allow the call, so no grant can — a
            workspace owner or admin has to change the role.
            `agent_not_permitted`: no connected agent may do this at any scope
            (billing, platform admin, managing connected agents, a destination's
            signing secret).
        required_scope:
          type: string
          enum:
            - hookie:read
            - hookie:write
            - hookie:manage
          description: 'With `code`: the scope the refused call needs.'
        granted_scopes:
          type: array
          items:
            type: string
          description: 'With `code`: the scopes the agent''s grant holds now.'
        manage_url:
          type: string
          format: uri
          description: >-
            With `code: "agent_scope_insufficient"` only: the console's Settings
            → Connected agents page, opened on this agent
            (`…/#/settings/agents?client=<client_id>`), where its user widens
            the grant. The change applies on the agent's next request.
  securitySchemes:
    session:
      type: apiKey
      in: cookie
      name: hookie_session
      description: >-
        The console's sealed session cookie, set by WorkOS AuthKit. Mutating
        requests also require the `X-Requested-With` CSRF header.
    bearerAuth:
      type: http
      scheme: bearer
      bearerFormat: JWT
      description: >-
        An OAuth 2.1 access token from a connected agent, audienced at the
        `/mcp` resource URI. The agent acts as its user, with that user's role
        narrowed to the granted `hookie:*` scopes. No CSRF header is required —
        a bearer token is not ambient credentials.

````