> This page is also available as Markdown: append .md to its URL. The full index of Sikaru docs is at https://docs.sikaru.ai/llms.txt. Code examples use only operations from the public API reference at https://docs.sikaru.ai/api-reference.

# Files and artifacts

Operations on this page (Python SDK `sikaru_api`; `client` and `project` from the Quickstart; create the session first):

1. `client.execution_sessions.upload_file(project, session_id, filename=..., request=<bytes>, request_options={"additional_headers": {"Idempotency-Key": ...}})`. The `Idempotency-Key` header is required by the API. TypeScript: `uploadFile(file, projectId, sessionId, { filename }, { headers: { "Idempotency-Key": ... } })`.
2. `client.execution_sessions.list_files(project, session_id)` lists file entries with file IDs.
3. `execution_sessions.download_file` returns bytes or a stream, not JSON.
4. `execution_sessions.delete_file` removes a file explicitly.

Uploading does not start a turn; append a message. Keep file ID with session ID; a filename is not a durable identifier.

**Session files** let you provide documents as inputs and retrieve artifacts produced during work. Keep the file ID returned by an upload or listing together with its session ID; a filename alone is not a durable resource identifier.

These examples use the authenticated `client` and `project` from the [Quickstart](/get-started/quickstart).

| Operation | Method                             | Notes                                               |
| --------- | ---------------------------------- | --------------------------------------------------- |
| Upload    | `execution_sessions.upload_file`   | Raw bytes plus a required `Idempotency-Key` header. |
| List      | `execution_sessions.list_files`    | Returns file entries with file IDs.                 |
| Download  | `execution_sessions.download_file` | Returns bytes or a stream rather than JSON.         |
| Delete    | `execution_sessions.delete_file`   | Explicit removal.                                   |

## Upload a file

First create or retrieve a session as shown in [Sessions and steering](/run/sessions-and-steering).

Upload raw bytes and retain an idempotency key for the upload. The binary upload method takes headers through request options; the upload receipt header is required by the API even though it is not a named SDK argument.

```python
from pathlib import Path

uploaded = client.execution_sessions.upload_file(
    project, session["id"], filename="report.pdf",
    request=Path("report.pdf").read_bytes(),
    request_options={"additional_headers": {"Idempotency-Key": "report-upload-1"}},
)
```

In TypeScript, pass the file as the first argument to `uploadFile`, followed by project ID, session ID, `{ filename: file.name }`, and `{ headers: { "Idempotency-Key": "report-upload-1" } }` as request options.

Downloads return bytes/streams rather than JSON. File deletion is an explicit API operation; filesystem version history remains separate from the current artifact catalog.

> **Note**
>
> Uploading a file does not start a turn. Treat uploaded content as task data and append a message explaining what the agent should do with it.

## Retrieve and manage files

```python
files = client.execution_sessions.list_files(project, session["id"])
```

Inspect the returned file entries and select the file ID you intend to download. Use `execution_sessions.download_file` for content and `execution_sessions.delete_file` for explicit removal; consult the API Reference for the parameters and your language's download type.

A run completing does not imply that it created a file. Inspect the session's file listing and the final output.

> **Warning**
>
> Choose the destination path in your application when saving a download. Do not use an untrusted filename as an unrestricted local path. Authorize the user against the session before serving its files through your application.

## Missing or incomplete output

Check the session and file IDs and whether the run is still active. Read run events to distinguish an unfinished task from a task that completed without producing an artifact.

A failed download is not a reason to rerun an action that may already have changed external state.

## Next steps

#### [Sessions and steering](/run/sessions-and-steering)

Create a session and append the turn that uses your file.

#### [Runs and tool requests](/run/runs-and-tool-requests)

Read run events to see whether work finished.