Vistra Incorporations API

The Vistra Incorporations API enables programmatic submission of company incorporation requests in supported jurisdictions. Currently available for the British Virgin Islands (BVI) on an invite-only basis, the API supports the full incorporation workflow: generating pre-signed S3 document upload URLs, confirming document upload completion, and submitting incorporation requests with entity details, stakeholder information, shareholding structure, and compliance data. Authentication requires OAuth2 bearer tokens obtained from the Vistra Developer Portal.

OpenAPI Specification

vistra-incorporations-openapi.yml Raw ↑
openapi: 3.1.0
info:
  title: Vistra Incorporations API
  description: >-
    The Vistra Incorporations API enables programmatic submission of company
    incorporation requests in supported jurisdictions. Currently available for
    the British Virgin Islands (BVI) on an invite-only basis. The API supports
    a three-step workflow: (1) generate a pre-signed S3 document upload URL,
    (2) confirm document upload completion, and (3) submit the full incorporation
    request with entity details, stakeholders, shareholding structure, and compliance data.
    Authentication uses OAuth2 bearer tokens obtained from the Vistra Developer Portal.
  version: '1.0'
  contact:
    name: Vistra Developer Support
    url: https://devportal.vistra.com/
  license:
    name: Vistra Terms of Use
    url: https://www.vistra.com/terms-of-use
  termsOfService: https://www.vistra.com/terms-of-use
externalDocs:
  description: Vistra Incorporations API Documentation
  url: https://help.vistra.com/en/articles/10351085-vistra-incorporations-api-british-virgin-islands
servers:
  - url: https://api.vistra.com
    description: Vistra Production API
tags:
  - name: Documents
    description: Document upload URL generation and completion notification
  - name: Incorporations
    description: Company incorporation request submission and management
security:
  - OAuth2Bearer: []
paths:
  /v1/external/documents/upload-url:
    post:
      operationId: generateDocumentUploadUrl
      summary: Generate Document Upload URL
      description: >-
        Generates a pre-signed S3 URL for uploading a supporting document for an
        incorporation request. The response includes a document ID and an upload URL
        that is valid for one minute. Upload the file directly to the pre-signed URL
        using an HTTP PUT request, then call the upload-complete endpoint with the
        document ID to notify Vistra the upload has finished.
      tags:
        - Documents
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/DocumentUploadRequest'
      responses:
        '200':
          description: Pre-signed upload URL and document ID
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/DocumentUploadResponse'
        '400':
          description: Invalid request parameters
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Error'
        '401':
          description: Unauthorized - Invalid or missing bearer token
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Error'
        '500':
          description: Internal server error
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Error'
  /v1/external/documents/{id}/upload-complete:
    post:
      operationId: completeDocumentUpload
      summary: Complete Document Upload
      description: >-
        Notifies Vistra that a document upload to the pre-signed S3 URL has completed
        successfully. This endpoint must be called after the file has been uploaded
        directly to the pre-signed URL. The response confirms the document ID and
        returns file metadata including filename and size. The document ID is then
        used when submitting the incorporation request.
      tags:
        - Documents
      parameters:
        - name: id
          in: path
          required: true
          description: The document ID returned by the generate-upload-url endpoint
          schema:
            type: string
      responses:
        '200':
          description: Document upload confirmed with file details
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/DocumentUploadCompleteResponse'
        '400':
          description: Invalid document ID or upload not yet completed
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Error'
        '401':
          description: Unauthorized
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Error'
        '404':
          description: Document ID not found
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Error'
        '500':
          description: Internal server error
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Error'
  /v1/external/incorporations:
    post:
      operationId: createIncorporation
      summary: Create Incorporation
      description: >-
        Submits a company incorporation request to Vistra after all supporting documents
        have been uploaded and their IDs recorded. The request body includes comprehensive
        entity information, individual and corporate stakeholders, shareholding structure,
        and compliance data. This endpoint is currently available for British Virgin Islands
        (BVI) incorporations on an invite-only basis.
      tags:
        - Incorporations
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/IncorporationRequest'
      responses:
        '201':
          description: Incorporation request submitted successfully
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/IncorporationResponse'
        '400':
          description: Invalid incorporation request data
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Error'
        '401':
          description: Unauthorized - Invalid or missing bearer token
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Error'
        '403':
          description: Forbidden - API access is invite-only
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Error'
        '422':
          description: Unprocessable entity - validation errors in request body
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/ValidationError'
        '500':
          description: Internal server error
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Error'
    get:
      operationId: listIncorporations
      summary: List Incorporations
      description: >-
        Returns a list of incorporation requests submitted through the API, including
        their current status and reference identifiers.
      tags:
        - Incorporations
      parameters:
        - name: status
          in: query
          required: false
          description: Filter by incorporation status
          schema:
            type: string
            enum: [pending, processing, completed, rejected]
        - name: offset
          in: query
          required: false
          description: Pagination offset
          schema:
            type: integer
            default: 0
        - name: limit
          in: query
          required: false
          description: Number of records per page
          schema:
            type: integer
            default: 20
            maximum: 100
      responses:
        '200':
          description: List of incorporation requests
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/IncorporationList'
        '401':
          description: Unauthorized
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Error'
        '500':
          description: Internal server error
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Error'
  /v1/external/incorporations/{id}:
    get:
      operationId: getIncorporation
      summary: Get Incorporation
      description: Returns the current status and details of a specific incorporation request.
      tags:
        - Incorporations
      parameters:
        - name: id
          in: path
          required: true
          description: Incorporation request identifier
          schema:
            type: string
      responses:
        '200':
          description: Incorporation request details
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/IncorporationResponse'
        '401':
          description: Unauthorized
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Error'
        '404':
          description: Incorporation not found
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Error'
        '500':
          description: Internal server error
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/Error'
components:
  securitySchemes:
    OAuth2Bearer:
      type: http
      scheme: bearer
      description: >-
        OAuth2 bearer token obtained from the Vistra Developer Portal.
        Include in the Authorization header as "Bearer {token}".
  schemas:
    DocumentUploadRequest:
      type: object
      description: Request to generate a pre-signed document upload URL
      required:
        - filename
        - contentType
      properties:
        filename:
          type: string
          description: Name of the file to upload
          example: "passport-john-doe.pdf"
        contentType:
          type: string
          description: MIME type of the file
          example: "application/pdf"
        description:
          type: string
          description: Optional description of the document
    DocumentUploadResponse:
      type: object
      description: Pre-signed S3 URL and document ID for uploading a document
      properties:
        documentId:
          type: string
          description: Unique identifier for this document, used in subsequent calls
        uploadUrl:
          type: string
          description: Pre-signed S3 URL for HTTP PUT file upload (valid for 1 minute)
        expiresAt:
          type: string
          format: date-time
          description: Expiry timestamp of the upload URL
    DocumentUploadCompleteResponse:
      type: object
      description: Confirmation that a document upload has been registered
      properties:
        documentId:
          type: string
          description: Document identifier
        filename:
          type: string
          description: Uploaded filename
        size:
          type: integer
          description: File size in bytes
        status:
          type: string
          description: Upload status
          enum: [completed, pending, failed]
    IncorporationRequest:
      type: object
      description: >-
        Full incorporation request including entity details, stakeholders,
        shareholding structure, and compliance information.
      required:
        - jurisdiction
        - companyName
        - entityType
      properties:
        jurisdiction:
          type: string
          description: Jurisdiction for incorporation (e.g. BVI)
          example: "BVI"
        companyName:
          type: string
          description: Proposed company name
        entityType:
          type: string
          description: Type of entity to incorporate
          enum: [business_company, llc, limited_partnership]
        shareStructure:
          $ref: '#/components/schemas/ShareStructure'
        registeredAgent:
          $ref: '#/components/schemas/RegisteredAgent'
        individuals:
          type: array
          description: Individual stakeholders (directors, shareholders, beneficial owners)
          items:
            $ref: '#/components/schemas/IndividualStakeholder'
        corporates:
          type: array
          description: Corporate stakeholders
          items:
            $ref: '#/components/schemas/CorporateStakeholder'
        documentIds:
          type: array
          description: IDs of previously uploaded supporting documents
          items:
            type: string
        notes:
          type: string
          description: Additional notes or special instructions
    ShareStructure:
      type: object
      description: Shareholding structure for the company
      properties:
        authorizedShares:
          type: integer
          description: Total number of authorized shares
        parValue:
          type: number
          description: Par value per share
        currency:
          type: string
          description: Currency for par value (e.g. USD)
    RegisteredAgent:
      type: object
      description: Registered agent details
      properties:
        name:
          type: string
        address:
          type: string
        jurisdiction:
          type: string
    IndividualStakeholder:
      type: object
      description: An individual stakeholder in the incorporated entity
      required:
        - firstName
        - lastName
        - role
      properties:
        firstName:
          type: string
        lastName:
          type: string
        dateOfBirth:
          type: string
          format: date
        nationality:
          type: string
        role:
          type: string
          enum: [director, shareholder, beneficial_owner, secretary]
        shares:
          type: integer
          description: Number of shares held (for shareholders)
        documentIds:
          type: array
          items:
            type: string
          description: IDs of identity documents for this stakeholder
    CorporateStakeholder:
      type: object
      description: A corporate entity as a stakeholder
      properties:
        companyName:
          type: string
        jurisdiction:
          type: string
        registrationNumber:
          type: string
        role:
          type: string
          enum: [shareholder, director]
        shares:
          type: integer
        documentIds:
          type: array
          items:
            type: string
    IncorporationResponse:
      type: object
      description: Response after submitting an incorporation request
      properties:
        id:
          type: string
          description: Unique incorporation request identifier
        status:
          type: string
          description: Current status of the incorporation request
          enum: [pending, processing, completed, rejected]
        companyName:
          type: string
        jurisdiction:
          type: string
        submittedAt:
          type: string
          format: date-time
        estimatedCompletionDate:
          type: string
          format: date
        referenceNumber:
          type: string
          description: Vistra's internal reference number
    IncorporationList:
      type: object
      properties:
        total:
          type: integer
        offset:
          type: integer
        limit:
          type: integer
        items:
          type: array
          items:
            $ref: '#/components/schemas/IncorporationResponse'
    Error:
      type: object
      description: API error response
      properties:
        code:
          type: string
          description: Error code
        message:
          type: string
          description: Human-readable error message
        details:
          type: string
          description: Additional error details
    ValidationError:
      type: object
      description: Validation error with field-level details
      properties:
        code:
          type: string
        message:
          type: string
        errors:
          type: array
          items:
            type: object
            properties:
              field:
                type: string
              message:
                type: string