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

# Replace Record Legacy Activity

> Preserves a record's activity from the legacy system. The body carries the
record's whole legacy activity feed, each entry already worded as the
legacy system displayed it, and replaces whatever was preserved on the
record before. Repeating the request leaves the same entries, so a
migration can be rerun. Send an empty `entries` array to clear the record.

The entries appear on the record's Activity tab under **Before migration**,
newest first, below the activity recorded since. They are read-only and are
shown as sent.

An entry is held by one record at a time. When a `sourceId` in the request
is already preserved on another record, the entry moves to this record, and
`movedEntryCount` counts such entries.

To check that every legacy activity row was preserved, add up
`sourceRowCount` across the migrated records and compare it with the legacy
system's row count.

**Required permission:** `<resource>.import` for the path's `{entityType}`
(`event.import`, `exposure.import`, `policy.import`, `quote.import`,
`submission.import`). An entry with `privileged: true` also requires
`note.view-privileged`.




## OpenAPI

````yaml /openapi/generated-external-api.yaml put /api/v1/companies/{companyId}/entities/{entityType}/{entityId}/legacy-activity
openapi: 3.0.3
info:
  title: AI Insurance External API
  description: External API for AI Insurance platform
  version: 1.0.0
  contact:
    email: support@aiinsurance.io
servers:
  - url: https://go.aiinsurance.io
    description: Production
security:
  - ApiKeyAuth: []
paths:
  /api/v1/companies/{companyId}/entities/{entityType}/{entityId}/legacy-activity:
    put:
      tags:
        - Imports
      summary: Replace Record Legacy Activity
      description: >
        Preserves a record's activity from the legacy system. The body carries
        the

        record's whole legacy activity feed, each entry already worded as the

        legacy system displayed it, and replaces whatever was preserved on the

        record before. Repeating the request leaves the same entries, so a

        migration can be rerun. Send an empty `entries` array to clear the
        record.


        The entries appear on the record's Activity tab under **Before
        migration**,

        newest first, below the activity recorded since. They are read-only and
        are

        shown as sent.


        An entry is held by one record at a time. When a `sourceId` in the
        request

        is already preserved on another record, the entry moves to this record,
        and

        `movedEntryCount` counts such entries.


        To check that every legacy activity row was preserved, add up

        `sourceRowCount` across the migrated records and compare it with the
        legacy

        system's row count.


        **Required permission:** `<resource>.import` for the path's
        `{entityType}`

        (`event.import`, `exposure.import`, `policy.import`, `quote.import`,

        `submission.import`). An entry with `privileged: true` also requires

        `note.view-privileged`.
      operationId: replaceRecordLegacyActivity
      parameters:
        - $ref: '#/components/parameters/companyId'
        - name: entityType
          in: path
          required: true
          schema:
            type: string
            enum:
              - event
              - exposure
              - policy
              - quote
              - submission
          description: The type of the record the activity belongs to.
        - $ref: '#/components/parameters/entityIdPath'
      requestBody:
        required: true
        content:
          application/json:
            schema:
              type: object
              required:
                - entries
              properties:
                entries:
                  type: array
                  maxItems: 10000
                  description: The record's legacy activity, in the legacy display order.
                  items:
                    $ref: '#/components/schemas/LegacyActivityEntryInput'
            examples:
              claimFeed:
                summary: Two entries on a claim
                value:
                  entries:
                    - sourceId: 0f7d3c52-6f0b-4a39-9d53-1c7f0c2f6b11
                      sourceRowIds:
                        - 0f7d3c52-6f0b-4a39-9d53-1c7f0c2f6b11
                        - 5b0e9a77-23c1-4f0e-8a64-9a0d1a4f7c22
                      occurredAt: '2024-03-20T15:04:00Z'
                      actorName: Maria Okafor
                      actorEmail: maria.okafor@example.com
                      category: Event Information
                      headline: Edited Claim
                      lines:
                        - label: Date of Loss
                          before: null
                          after: 3/14/2024
                        - label: Policy
                          after:
                            text: PL-2041
                            entityType: policy
                            entityId: 550e8400-e29b-41d4-a716-446655440020
                    - sourceId: 8a1c4e90-7d2b-4c11-b0f3-3e5d6f7a8b33
                      occurredAt: '2023-01-05T09:00:00Z'
                      actorName: Maria Okafor
                      headline: Event Created
      responses:
        '200':
          description: The record's preserved activity was replaced
          content:
            application/json:
              schema:
                type: object
                required:
                  - entryCount
                  - sourceRowCount
                  - movedEntryCount
                properties:
                  entryCount:
                    type: integer
                    description: Entries now preserved on the record.
                  sourceRowCount:
                    type: integer
                    description: Legacy activity rows those entries stand for.
                  movedEntryCount:
                    type: integer
                    description: >-
                      Entries that were preserved on another record and now sit
                      on this one.
              examples:
                replaced:
                  summary: Two entries standing for three legacy rows
                  value:
                    entryCount: 2
                    sourceRowCount: 3
                    movedEntryCount: 0
        '400':
          description: Bad Request - the entries are malformed
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
              examples:
                duplicateSourceId:
                  summary: Two entries share a sourceId
                  value:
                    error:
                      code: ValidationError
                      message: >-
                        entries.1.sourceId: Duplicate sourceId
                        8a1c4e90-7d2b-4c11-b0f3-3e5d6f7a8b33
        '401':
          $ref: '#/components/responses/Unauthorized'
        '403':
          $ref: '#/components/responses/Forbidden'
        '404':
          description: The record does not exist
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ErrorResponse'
              examples:
                recordNotFound:
                  summary: No such record in the company
                  value:
                    error:
                      code: NotFoundError
                      message: Event not found
        '500':
          $ref: '#/components/responses/InternalServerError'
      security:
        - BearerAuth: []
        - ApiKeyAuth: []
components:
  parameters:
    companyId:
      name: companyId
      in: path
      required: true
      schema:
        type: string
        format: uuid
      description: Company identifier
    entityIdPath:
      name: entityId
      in: path
      required: true
      schema:
        type: string
        format: uuid
      description: Entity identifier
  schemas:
    LegacyActivityEntryInput:
      type: object
      additionalProperties: false
      description: >
        One activity entry as the legacy system displayed it. Every text value
        is

        stored and shown as sent; nothing is read through the company's

        configuration.
      required:
        - sourceId
        - occurredAt
        - headline
      properties:
        sourceId:
          type: string
          minLength: 1
          maxLength: 255
          description: |
            The legacy system's id for the entry. Unique within the request, and
            held by one record in the company at a time.
        sourceRowIds:
          type: array
          minItems: 1
          items:
            type: string
            minLength: 1
            maxLength: 255
          description: >
            Every legacy activity row the entry stands for, when the legacy
            system

            displayed several rows as one entry. Defaults to `[sourceId]`.
        occurredAt:
          type: string
          format: date-time
          description: When the activity happened.
        actorName:
          type: string
          nullable: true
          maxLength: 255
          description: The name of the person who acted, as the legacy system showed it.
        actorEmail:
          type: string
          nullable: true
          maxLength: 320
        category:
          type: string
          nullable: true
          maxLength: 255
          description: >-
            The legacy activity filter the entry appeared under, such as
            `Files`.
        headline:
          type: string
          minLength: 1
          description: The entry's heading, such as `Closed Claim`.
        lines:
          type: array
          description: The lines under the heading, in display order.
          items:
            $ref: '#/components/schemas/LegacyActivityLine'
        privileged:
          type: boolean
          default: false
          description: |
            Marks an entry about a privileged note. Only callers holding
            `note.view-privileged` see it, and sending `true` requires that
            permission.
        source:
          description: |
            The stored legacy rows behind the entry, kept as evidence. Any JSON
            value; never displayed.
    ErrorResponse:
      type: object
      description: Standard error response for all external API endpoints
      required:
        - error
      properties:
        error:
          type: object
          required:
            - code
            - message
          properties:
            code:
              type: string
              description: Machine-readable error code
              example: VALIDATION_ERROR
            message:
              type: string
              description: Human-readable error message
              example: 'submissionId: Required field is missing'
            userMessages:
              type: array
              description: >-
                Clean, verbatim-displayable messages — one entry per failure,
                free of error-code tags, field paths, and internal noise.
                Suitable for showing to end users as-is.
              items:
                type: string
              example:
                - Exposures of type 'company' require an address
            details:
              type: array
              description: Additional details for validation errors (field-level errors)
              items:
                type: object
                properties:
                  field:
                    type: string
                    description: The field that caused the error
                    example: submissionId
                  code:
                    type: string
                    description: Stable problem code for this individual validation failure
                    example: BLANK_LIST_ELEMENT
                  reason:
                    type: string
                    description: Stable reason the value violates its canonical contract
                    example: blank-list-element
                  expected:
                    type: string
                    description: The expected canonical value contract
                    example: nonblank trimmed string
                  message:
                    type: string
                    description: Description of the field error
                    example: Required field is missing
    LegacyActivityLine:
      type: object
      additionalProperties: false
      description: >
        One displayed line of a preserved entry. Send a changed value as `label`
        with

        `before` and `after`; leave `before` out when the legacy system showed
        only

        the new value, and send `null` for a side it showed as "none". Send a
        line of

        free text as `text`. `lines` nests further lines under this one, up to
        five

        levels deep.
      properties:
        label:
          type: string
          description: The label the legacy system showed, such as a field's name.
        before:
          $ref: '#/components/schemas/LegacyActivityValue'
        after:
          $ref: '#/components/schemas/LegacyActivityValue'
        text:
          type: string
        lines:
          type: array
          items:
            $ref: '#/components/schemas/LegacyActivityLine'
    LegacyActivityValue:
      description: >
        A value on one side of a change, as the legacy system displayed it:
        plain

        text, or text that links to the record the legacy record became. `null`
        is

        a side the legacy system showed as "none".
      oneOf:
        - type: string
          nullable: true
        - type: object
          additionalProperties: false
          required:
            - text
            - entityType
            - entityId
          properties:
            text:
              type: string
              description: The name the legacy system showed.
            entityType:
              type: string
              enum:
                - policy
                - exposure
                - event
                - quote
                - submission
                - person
                - organization
            entityId:
              type: string
              format: uuid
              description: The record the name links to.
  responses:
    Unauthorized:
      description: Unauthorized - Invalid or missing API key
      content:
        application/json:
          schema:
            $ref: '#/components/schemas/ErrorResponse'
          examples:
            missingApiKey:
              summary: Missing API key
              value:
                error:
                  code: AuthenticationError
                  message: API key authentication required
                  userMessages:
                    - API key authentication required
            invalidApiKey:
              summary: >-
                Invalid API key (e.g. unknown key, or a Bearer token used
                instead of an API key)
              value:
                error:
                  code: AuthenticationError
                  message: Invalid API key
                  userMessages:
                    - Invalid API key
    Forbidden:
      description: Forbidden - Insufficient permissions
      content:
        application/json:
          schema:
            $ref: '#/components/schemas/ErrorResponse'
          examples:
            insufficientPermissions:
              summary: Insufficient permissions
              value:
                error:
                  code: AuthorizationError
                  message: User is not authorized to perform the requested action
                  userMessages:
                    - User is not authorized to perform the requested action
            companyMismatch:
              summary: A valid API key naming another company in the URL
              value:
                error:
                  code: AuthorizationError
                  message: API key is not scoped to the requested company
                  userMessages:
                    - API key is not scoped to the requested company
    InternalServerError:
      description: Internal Server Error - Unexpected error occurred
      content:
        application/json:
          schema:
            $ref: '#/components/schemas/ErrorResponse'
          examples:
            internalError:
              summary: Unexpected server error
              value:
                error:
                  code: UncaughtActionError
                  message: Uncaught error occurred in <actionName>
                  userMessages:
                    - An unexpected error occurred. Please try again later.
  securitySchemes:
    ApiKeyAuth:
      type: apiKey
      in: header
      name: Authorization
      description: >-
        API key authentication. Send your raw API key as the `Authorization`
        header value with NO scheme prefix — `Authorization: YOUR-API-KEY`. Do
        NOT prefix it with `Bearer ` or `ApiKey `, and do not use an `X-API-Key`
        header; those are not accepted.
    BearerAuth:
      type: http
      scheme: bearer
      bearerFormat: JWT
      description: >-
        User-principal OAuth 2.0 Bearer authentication. Send a user-scoped Auth0
        access token (audience = the app API audience) as `Authorization: Bearer
        <jwt>`. The request resolves to the user's identity and is authorized by
        their Role on the `{companyId}` in the path — the same role-based
        permissions the web app enforces. This is the path the MCP connector
        uses to act on a user's behalf; endpoints that accept it list both
        `BearerAuth` and `ApiKeyAuth`.

````

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