# Files (/docs/sdk/files)



`client.files` manages files inside a live sandbox. All paths resolve
inside `/workspace`; relative paths are interpreted from there, and paths
that escape the workspace through `..` segments are rejected with
`path_outside_workspace`.

Direct reads and writes are capped at 256 KB. For larger files, use
`downloadUrl` to fetch content, or run a command inside the sandbox to
produce the file and export it as an [artifact](/docs/sdk/artifacts).

Every method on a [`SandboxHandle`](/docs/sdk) is also available without
the `sandboxId` argument, for example `sandbox.files.read("notes.txt")`.

## read [#read]

Read a file's content as a string.

```ts
read(
  sandboxId: `sbx_${string}`,
  path: string,
  input?: { encoding?: "utf8" | "base64" },
): Promise<string>
```

| Field      | Type                 | Default  | Description                      |
| ---------- | -------------------- | -------- | -------------------------------- |
| `encoding` | `"utf8" \| "base64"` | `"utf8"` | Use `base64` for binary content. |

```ts
const content = await client.files.read(sandbox.id, "results.json");
```

Error codes: `file_not_found`, `path_is_directory`, `file_too_large`
(over 256 KB — use `downloadUrl`), `path_outside_workspace`,
`invalid_file_encoding`.

## write [#write]

Write content to a file and get back its `FileStat`.

```ts
write(
  sandboxId: `sbx_${string}`,
  path: string,
  content: string,
  input?: {
    createParents?: boolean;
    encoding?: "utf8" | "base64";
    overwrite?: boolean;
  },
): Promise<FileStat>
```

| Field           | Type                 | Default  | Description                                                                                |
| --------------- | -------------------- | -------- | ------------------------------------------------------------------------------------------ |
| `createParents` | `boolean`            | `false`  | Create missing parent directories.                                                         |
| `encoding`      | `"utf8" \| "base64"` | `"utf8"` | Encoding of `content`.                                                                     |
| `overwrite`     | `boolean`            | `true`   | Replace an existing file. With `false`, an existing file fails with `file_already_exists`. |

```ts
await client.files.write(sandbox.id, "data/input.csv", csv, {
  createParents: true,
});
```

Error codes: `file_too_large`, `file_already_exists`,
`parent_directory_not_found`, `path_is_directory`,
`path_outside_workspace`.

## delete [#delete]

Delete a file or an empty directory. There's no recursive delete; a
non-empty directory fails with `directory_not_empty`.

```ts
delete(sandboxId: `sbx_${string}`, path: string): Promise<void>
```

```ts
await client.files.delete(sandbox.id, "tmp/scratch.txt");
```

Error codes: `file_not_found`, `directory_not_empty`,
`path_outside_workspace`.

## list [#list]

List directory entries. Defaults to `/workspace`.

```ts
list(sandboxId: `sbx_${string}`, path?: string): Promise<ListFilesResponse>
```

```ts
const entries = await client.files.list(sandbox.id, "data");
for (const entry of entries.data) {
  console.log(entry.type, entry.path, entry.sizeBytes);
}
```

Error codes: `file_not_found`, `path_not_directory`,
`path_outside_workspace`.

## stat [#stat]

Fetch metadata for a single file or directory.

```ts
stat(sandboxId: `sbx_${string}`, path: string): Promise<FileStat>
```

```ts
const stat = await client.files.stat(sandbox.id, "results.json");
console.log(stat.sizeBytes, stat.modifiedAt);
```

Error codes: `file_not_found`, `path_outside_workspace`.

## mkdir [#mkdir]

Create a directory.

```ts
mkdir(
  sandboxId: `sbx_${string}`,
  path: string,
  input?: { parents?: boolean },
): Promise<FileStat>
```

| Field     | Type      | Default | Description                              |
| --------- | --------- | ------- | ---------------------------------------- |
| `parents` | `boolean` | `false` | Create missing intermediate directories. |

```ts
await client.files.mkdir(sandbox.id, "data/raw", { parents: true });
```

Error codes: `file_already_exists`, `parent_directory_not_found`,
`path_outside_workspace`.

## move [#move]

Move or rename a file or directory.

```ts
move(
  sandboxId: `sbx_${string}`,
  from: string,
  to: string,
  input?: { overwrite?: boolean },
): Promise<FileStat>
```

| Field       | Type      | Default | Description                      |
| ----------- | --------- | ------- | -------------------------------- |
| `overwrite` | `boolean` | `false` | Replace an existing destination. |

```ts
await client.files.move(sandbox.id, "draft.md", "final.md");
```

Error codes: `file_not_found`, `file_already_exists`,
`path_outside_workspace`.

## downloadUrl [#downloadurl]

Get a short-lived signed URL for downloading a file of any size. The URL
is fetched with `GET` and authenticated with your API key
(`authMode: "api_key"`).

```ts
downloadUrl(
  sandboxId: `sbx_${string}`,
  path: string,
): Promise<{ url: string; method: "GET"; authMode: "api_key" }>
```

```ts
const { url } = await client.files.downloadUrl(sandbox.id, "build.tar.gz");
```

Error codes: `file_not_found`, `path_is_directory`,
`path_outside_workspace`.

## FileEntry and FileStat [#fileentry-and-filestat]

`FileStat` is `{ path, type: "file" | "directory", sizeBytes, modifiedAt? }`.
`FileEntry` is a `FileStat` plus a required `name` for each directory entry.

<Callout type="warn" title="Warning">
  The workspace is destroyed with the sandbox. Export files you need to keep as
  [artifacts](/docs/sdk/artifacts) before the sandbox expires.
</Callout>

## Next steps [#next-steps]

* [Artifacts](/docs/sdk/artifacts) — durable exports from the workspace.
* [Commands](/docs/sdk/commands) — generate files by running processes.
* [Files concept](/docs/concepts/files) — workspace rules in depth.
