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

# Upload a file

> Start an upload so the agent can use the file in a task.

Uploads go directly to cloud storage. The API returns an upload target and never receives the bytes. The response's `upload_type` selects the flow and is chosen from the `size_bytes` you declare.

### `upload_type: "single"`

1. `POST /experimental/files` returns a `file_id`, an `upload_url`, and the `fields` to send with the bytes.
2. POST the bytes to `upload_url` as multipart form-data, with every key in `fields` included as a form field. Success returns `204 No Content`.
3. `POST /experimental/files/{file_id}/finalize` with an empty body.

### `upload_type: "multipart"`

1. `POST /experimental/files` returns a `file_id`, an `upload_id`, a `part_size_bytes`, and a `part_count`.
2. Split the file into `part_count` chunks of `part_size_bytes`. The last chunk is the remainder.
3. `POST /experimental/files/{file_id}/parts` with the `upload_id` and the part numbers you want, which returns a PUT URL per part. You can request them in batches.
4. PUT each chunk to its URL and keep the `ETag` response header for that part number.
5. `POST /experimental/files/{file_id}/finalize` with `{ "upload_id": "…", "parts": [{ "part_number": 1, "etag": "…" }, … ] }`.

Once finalized, attach the `file_id` to a task with `file_ids` on `POST /experimental/tasks/{id}/messages`.


## OpenAPI

````yaml api-reference/openapi.json POST /experimental/files
openapi: 3.1.0
info:
  title: Phylo API — V1
  description: Public API for Phylo, the biomedical AI agent platform.
  version: 0.1.0
servers:
  - url: https://api.phylo.bio/v1
    description: >-
      Self-serve platform. Enterprise customers should contact the Phylo team to
      get their API base URL. Learn more at https://phylo.bio/enterprise.
security: []
paths:
  /experimental/files:
    post:
      tags:
        - files
      summary: Upload a file
      description: Start an upload so the agent can use the file in a task.
      operationId: request_upload_experimental_files_post
      requestBody:
        required: true
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/CreateFileRequest'
            examples:
              minimal:
                summary: Minimal — VCF input file
                value:
                  project_id: prj_0126xxQZB9MmSUaTs1MtRAgU
                  filename: patient001_brca1.vcf
                  size_bytes: 4321
              with_mime:
                summary: With mime_type
                value:
                  project_id: prj_0126xxQZB9MmSUaTs1MtRAgU
                  filename: Patient001_BRCA1_variant_report.json
                  size_bytes: 13913
                  mime_type: application/json
      responses:
        '200':
          description: >-
            Upload started. For `upload_type=single`, POST the bytes to
            `upload_url` with `fields`. For `upload_type=multipart`, pass
            `upload_id` to `POST /experimental/files/{file_id}/parts`.
          content:
            application/json:
              schema:
                $ref: '#/components/schemas/UploadIntent'
              examples:
                single:
                  summary: Small file — single POST
                  value:
                    type: upload_intent
                    file_id: file_017jG6PPIYy41dqnVz47lrmo
                    project_id: prj_014OwAG97UY0UfcHlLHQRnKO
                    path: >-
                      orgs/<org>/users/<user>/uploads/projects/proj_6b3606df1c/patient001_brca1.vcf
                    upload_type: single
                    expires_at: '2026-08-12T22:20:08.147475Z'
                    filename: patient001_brca1.vcf
                    size_bytes: 4321
                    mime_type: text/plain
                    upload_url: https://<bucket>.s3.us-west-2.amazonaws.com/
                    fields:
                      Content-Type: text/plain
                      key: >-
                        orgs/<org>/users/<user>/uploads/projects/proj_6b3606df1c/patient001_brca1.vcf
                      x-amz-algorithm: AWS4-HMAC-SHA256
                      x-amz-credential: <credential>/20260812/us-west-2/s3/aws4_request
                      x-amz-date: 20260812T220508Z
                      x-amz-security-token: <token>
                      policy: eyJleHBpcmF0aW9uIjoiMjAyNi0w...
                      x-amz-signature: 5a8d...
                multipart:
                  summary: Large file — multipart upload
                  value:
                    type: upload_intent
                    file_id: file_010kaWC7SjxErybg3OdscqX8
                    project_id: prj_014OwAG97UY0UfcHlLHQRnKO
                    path: >-
                      orgs/<org>/users/<user>/uploads/projects/proj_6b3606df1c/wgs_sample.cram
                    upload_type: multipart
                    expires_at: '2026-08-13T22:06:07.384079Z'
                    filename: wgs_sample.cram
                    size_bytes: 21474836480
                    mime_type: application/octet-stream
                    upload_id: aUU9ZO9qqsHiXssnDqXzfUlAMHYzK537OiMUJrsJrfsCoHXFm...
                    part_size_bytes: 33554432
                    part_count: 640
      security:
        - bearerAuth: []
components:
  schemas:
    CreateFileRequest:
      properties:
        project_id:
          type: string
          title: Project Id
        filename:
          type: string
          title: Filename
        size_bytes:
          type: integer
          title: Size Bytes
        mime_type:
          anyOf:
            - type: string
            - type: 'null'
          title: Mime Type
      additionalProperties: false
      type: object
      required:
        - project_id
        - filename
        - size_bytes
      title: CreateFileRequest
    UploadIntent:
      properties:
        type:
          type: string
          const: upload_intent
          title: Type
          default: upload_intent
        file_id:
          anyOf:
            - type: string
            - type: 'null'
          title: File Id
        project_id:
          type: string
          title: Project Id
        path:
          anyOf:
            - type: string
            - type: 'null'
          title: Path
        upload_type:
          type: string
          enum:
            - single
            - multipart
          title: Upload Type
          default: single
        upload_url:
          anyOf:
            - type: string
            - type: 'null'
          title: Upload Url
        fields:
          additionalProperties: true
          type: object
          title: Fields
        upload_id:
          anyOf:
            - type: string
            - type: 'null'
          title: Upload Id
        part_size_bytes:
          anyOf:
            - type: integer
            - type: 'null'
          title: Part Size Bytes
        part_count:
          anyOf:
            - type: integer
            - type: 'null'
          title: Part Count
        expires_at:
          anyOf:
            - type: string
              format: date-time
            - type: 'null'
          title: Expires At
        filename:
          type: string
          title: Filename
        size_bytes:
          type: integer
          title: Size Bytes
        mime_type:
          anyOf:
            - type: string
            - type: 'null'
          title: Mime Type
      type: object
      required:
        - project_id
        - filename
        - size_bytes
      title: UploadIntent
  securitySchemes:
    bearerAuth:
      type: http
      scheme: bearer
      description: Requires an API key. See the Authentication guide.

````