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

# Create a memory agent

> Creates a managed memory agent. The returned agent_id owns a global memory index. Create a separate agent when complete memory isolation is required.




## OpenAPI

````yaml /openapi.yaml post /v1/agents
openapi: 3.0.3
info:
  title: Priors API
  description: >
    Priors gives you memory agents. An agent learns from the observations you
    send it and answers from what it learned.


    You call this API from your own backend with a partner API key. The key
    identifies your organization, which owns every agent, thread, observation,
    source, and memory it creates. Another organization receives 404 for those
    identifiers. Send `X-SP-End-User` alongside the key to act for one named
    person on your side.
  version: 0.1.0
servers:
  - url: https://app.sapientpriors.com/api
    description: Production
security:
  - partnerKey: []
tags:
  - name: Agents
    description: Create, read, update, and delete memory agents.
  - name: Threads
    description: 'Conversations under an agent: create them, teach them, and ask them.'
  - name: Sources
    description: Files an agent learned from, and the citations that point back to them.
  - name: Authentication
    description: What your key resolves to, and the limits that apply to it.
  - name: Billing
    description: Your organization's credits and charges.
paths:
  /v1/agents:
    post:
      tags:
        - Agents
      summary: Create a memory agent
      description: >
        Creates a managed memory agent. The returned agent_id owns a global
        memory index. Create a separate agent when complete memory isolation is
        required.
      operationId: create_agent
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/CreateAgentRequest'
            examples:
              container_learning_agent:
                summary: One agent for one of your customers
                value:
                  agent_config:
                    role: Household finance assistant
                    objective: >-
                      Answer questions about this household of accounts,
                      payments and statements.
      responses:
        '202':
          description: Agent reserved; dependency initialization continues asynchronously
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/AgentResponse'
              examples:
                created:
                  value:
                    agent_id: agent_01JZ8X9K6AS3V8SGP0Q9A2P4FH
                    status: initializing
                    agent_config:
                      role: Household finance assistant
                      objective: >-
                        Answer questions about this household of accounts,
                        payments and statements.
                    created_at: '2026-07-16T12:00:00Z'
                    updated_at: '2026-07-16T12:00:00Z'
                    expires_at: null
        '400':
          $ref: '#/components/responses/BadRequest'
        '401':
          $ref: '#/components/responses/Unauthorized'
        '403':
          $ref: '#/components/responses/Forbidden'
components:
  schemas:
    CreateAgentRequest:
      type: object
      required:
        - agent_config
      properties:
        agent_config:
          $ref: '#/components/schemas/AgentConfig'
        ttl_seconds:
          $ref: '#/components/schemas/TtlSeconds'
        visibility:
          $ref: '#/components/schemas/AgentVisibility'
      additionalProperties: false
    AgentResponse:
      type: object
      required:
        - agent_id
        - status
        - created_at
        - updated_at
        - access
      properties:
        agent_id:
          $ref: '#/components/schemas/AgentId'
          description: Unique identifier for the managed memory agent.
        status:
          type: string
          enum:
            - initializing
            - ready
            - failed
            - deleting
            - deleted
        agent_config:
          $ref: '#/components/schemas/AgentConfig'
        created_at:
          type: string
          format: date-time
        updated_at:
          type: string
          format: date-time
        expires_at:
          type: string
          format: date-time
          nullable: true
          description: |
            Always null today: agents do not expire on their own.
        resumed_from_turn:
          type: integer
          minimum: 0
          default: 0
          description: >
            How many turns were already learned into the memory index this agent
            restored from. It is 0 for a new agent. You cannot work this out
            yourself, because the index is on our side. A client that resumes a
            backfill reads it to know how many observations to skip.
        visibility:
          $ref: '#/components/schemas/AgentVisibility'
        access:
          $ref: '#/components/schemas/AgentAccess'
        threads:
          type: array
          description: >
            The threads on this agent that the caller reaches, newest first.
            With `X-SP-End-User`, that is the threads that person created and no
            others, which is how you list one person's conversations. Without
            the header your key is the organization, so it is every thread on
            the agent.
          items:
            $ref: '#/components/schemas/ThreadResponse'
      additionalProperties: false
    AgentConfig:
      type: object
      required:
        - role
        - objective
      properties:
        role:
          type: string
          minLength: 1
          maxLength: 200
          description: Short description of the memory agent's role.
        objective:
          type: string
          minLength: 1
          maxLength: 2000
          description: Primary learning objective this memory agent supports.
        metadata:
          $ref: '#/components/schemas/Metadata'
      additionalProperties: false
    TtlSeconds:
      type: integer
      minimum: 0
      maximum: 2592000
      description: >
        Reserved for a future idle-expiry policy. Stored and returned, but
        agents do not expire today. Capped at 2592000 (30 days).
    AgentVisibility:
      type: string
      enum:
        - external
      default: external
      description: >
        The surface an agent sits on. `external` is the only one an API key
        reaches, and the only one it can create, so you can leave this field out
        and receive it. The agent belongs to your organization rather than to
        any person, and it appears in no directory.
    AgentId:
      type: string
      pattern: ^agent_[0-9A-HJKMNP-TV-Z]{26}$
      description: Server-generated agent identifier.
    AgentAccess:
      type: string
      enum:
        - owner
      description: >
        Your relationship to the agent. An agent your key created is always
        `owner`.
    ThreadResponse:
      type: object
      required:
        - agent_id
        - thread_id
        - status
        - created_at
        - updated_at
      properties:
        agent_id:
          $ref: '#/components/schemas/AgentId'
        thread_id:
          $ref: '#/components/schemas/ThreadId'
          description: Server-generated thread identifier.
        status:
          type: string
          enum:
            - provisioning
            - ready
            - deleting
            - deleted
        title:
          type: string
        metadata:
          $ref: '#/components/schemas/Metadata'
        created_at:
          type: string
          format: date-time
        updated_at:
          type: string
          format: date-time
        messages:
          type: array
          nullable: true
          description: >-
            Up to the 200 most recent persisted messages; present when reading
            one thread.
          items:
            $ref: '#/components/schemas/ThreadMessageResponse'
      additionalProperties: false
    ErrorResponse:
      type: object
      required:
        - error
        - code
        - request_id
      properties:
        error:
          type: string
        code:
          type: string
          description: >
            Machine-readable condition. Branch on this rather than on the status
            where the two differ. All three of these can arrive as a 5xx and
            they want different handling: `service_unavailable` (503) is a
            dependency outage worth retrying, `service_not_configured` (503) is
            the same transport failure that retrying will NEVER clear because a
            feature is not switched on for your organization, and
            `internal_error` (500) is a defect that will fail the same way
            again. Known values: invalid_request, unauthorized, forbidden,
            payment_required, not_found, agent_not_found, thread_not_found,
            conflict, agent_quota_exceeded, duplicate_upload_in_progress,
            document_already_ingested, document_uploaded_elsewhere,
            agent_not_ready, payload_too_large, rate_limit_exceeded,
            service_unavailable, service_not_configured,
            answer_model_unavailable, internal_error, and the document codes an
            upload can return (unsupported_document, document_needs_ocr,
            encrypted_document, malformed_document, empty_document,
            document_too_large, document_too_complex, document_too_many_turns,
            document_too_many_pages, document_too_large_for_ocr,
            document_pages_unexpected, document_service_unavailable, ocr_busy,
            ocr_failed, ingestion_failed).


            answer_model_unavailable is a narrower `service_unavailable` (503):
            the model that writes the visible reply could not be reached after
            retries. It is worth its own code because it is the one dependency
            whose outage a caller may want to word differently -- the turn
            produced no answer at all, and retrying shortly is the right advice.


            agent_not_found and thread_not_found are narrower `not_found`s, sent
            so a client can tell WHICH resource vanished and recover accordingly
            without matching on the English message. Treat any unrecognised
            value as the status code's default meaning rather than rejecting the
            response.
        request_id:
          type: string
          description: >
            Server-issued identifier for this request. Include it when reporting
            a problem so the call can be correlated with server logs.
        details:
          type: string
          description: |
            Present on a 429. Names which control refused the request:
              `user`                    Your per-subject window, counted against `X-SP-End-User`.
              `organization`            Your organization's ceiling, across every key you hold.
              `capacity`                The service is at capacity. Retry.
              `ingestion-organization`  Too much of your own document work is already running.
              `ingestion-capacity`      As above, service-wide.
      additionalProperties: false
    Metadata:
      type: object
      description: >
        Opaque caller-defined metadata. Bounded to keep payloads predictable: at
        most 50 keys.
      maxProperties: 50
      additionalProperties: true
    ThreadId:
      type: string
      pattern: ^thread_[0-9A-HJKMNP-TV-Z]{26}$
      description: Server-generated thread identifier.
    ThreadMessageResponse:
      type: object
      required:
        - speaker
        - text
        - timestamp
        - source_ids
      properties:
        speaker:
          type: string
        text:
          type: string
        timestamp:
          type: string
        source_ids:
          type: array
          items:
            type: string
      additionalProperties: false
  responses:
    BadRequest:
      description: >
        The request is not one this route can act on, and sending it again
        unchanged does not help. Usually the payload: a field missing, or a
        value out of range.


        It is also the credential and the headers around it, and each of these
        is refused rather than ignored: `X-SP-End-User` sent empty, or longer
        than 255 characters; and a key on a request that carries
        `Sec-Fetch-Site`, which only a browser sets.


        `code` is `invalid_request` throughout. `error` says which of these it
        was.
      content:
        application/json:
          schema:
            $ref: '#/components/schemas/ErrorResponse'
    Unauthorized:
      description: Missing or invalid credentials
      content:
        application/json:
          schema:
            $ref: '#/components/schemas/ErrorResponse'
    Forbidden:
      description: |
        The credential is valid but may not take this action.
      content:
        application/json:
          schema:
            $ref: '#/components/schemas/ErrorResponse'
  securitySchemes:
    partnerKey:
      type: http
      scheme: bearer
      description: >
        Your API key, shaped `sp_<key_id>_<secret>`, sent as `Authorization:
        Bearer sp_...`. It identifies your organization, not a person. Your
        organization owns the agents, holds the credit, and is billed. Every key
        your organization holds reaches the same things, so you rotate a key by
        minting the new one, deploying it, and revoking the old one.


        Keep the key on your server. A request that carries a `Sec-Fetch-Site`
        header is refused with 400, because only a browser sets that header.
        Priors sends no CORS headers, so a browser blocks the call before it
        leaves the page. The secret is shown once when the key is minted and is
        stored only as a hash. A lost secret is replaced, never recovered.


        An administrator of your organization mints and revokes keys in the
        Priors application, under Settings. There is no endpoint for it: a key
        reaches your whole organization, so issuing one is an act of
        administration.

````

This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.