# Filesystem API
URL: /docs/api/filesystem



Filesystem API [#filesystem-api]

Use the filesystem API when configuring how kernels read and write project files. The package provides constructors for Node.js, in-memory, and any fs-compatible backends, plus bridge utilities for cross-worker filesystem access.

Filesystem Types [#filesystem-types]

<TypeTable
  type={{
  "name": "RuntimeFileSystemBase",
  "description": "Base filesystem interface -- 11 Node.js `fs.promises`-compatible primitives.\nAll paths are absolute. This is the minimal surface that filesystem backends\nmust implement (e.g. fromFsLike, fromMemoryFS, fromNodeFS).",
  "entries": [
    {
      "name": "readFile",
      "description": "Read file as text.\nRead file as binary.",
      "tags": [],
      "type": "{ (path: string, encoding: \"utf8\"): Promise<string>; (path: string): Promise<Uint8Array<ArrayBuffer>>; }",
      "simplifiedType": "function",
      "required": true,
      "deprecated": false
    },
    {
      "name": "writeFile",
      "description": "Write file (text or binary).",
      "tags": [],
      "type": "(path: string, data: Uint8Array<ArrayBuffer> | string) => Promise<void>",
      "simplifiedType": "function",
      "required": true,
      "deprecated": false
    },
    {
      "name": "mkdir",
      "description": "Create directory, optionally recursive.",
      "tags": [],
      "type": "(path: string, options?: { recursive?: boolean; }) => Promise<void>",
      "simplifiedType": "function",
      "required": true,
      "deprecated": false
    },
    {
      "name": "readdir",
      "description": "List directory entries (file/dir names).",
      "tags": [],
      "type": "(path: string) => Promise<string[]>",
      "simplifiedType": "function",
      "required": true,
      "deprecated": false
    },
    {
      "name": "unlink",
      "description": "Delete file.",
      "tags": [],
      "type": "(path: string) => Promise<void>",
      "simplifiedType": "function",
      "required": true,
      "deprecated": false
    },
    {
      "name": "rmdir",
      "description": "Remove an empty directory.",
      "tags": [],
      "type": "(path: string) => Promise<void>",
      "simplifiedType": "function",
      "required": true,
      "deprecated": false
    },
    {
      "name": "rename",
      "description": "Rename / move a file or directory.",
      "tags": [],
      "type": "(oldPath: string, newPath: string) => Promise<void>",
      "simplifiedType": "function",
      "required": true,
      "deprecated": false
    },
    {
      "name": "stat",
      "description": "Get file or directory metadata.",
      "tags": [],
      "type": "(path: string) => Promise<FileStat>",
      "simplifiedType": "function",
      "required": true,
      "deprecated": false
    },
    {
      "name": "lstat",
      "description": "Get file or directory metadata without following symlinks.",
      "tags": [],
      "type": "(path: string) => Promise<FileStat>",
      "simplifiedType": "function",
      "required": true,
      "deprecated": false
    },
    {
      "name": "exists",
      "description": "Check if path exists.",
      "tags": [],
      "type": "(path: string) => Promise<boolean>",
      "simplifiedType": "function",
      "required": true,
      "deprecated": false
    },
    {
      "name": "watch",
      "description": "Subscribe to filesystem change events for the given paths.\nReturns an unsubscribe function. Events are filtered server-side.",
      "tags": [],
      "type": "((request: RuntimeWatchRequest, handler: (event: RuntimeWatchEvent) => void) => () => void) | undefined",
      "simplifiedType": "function",
      "required": false,
      "deprecated": false
    }
  ]
}}
/>

<TypeTable
  type={{
  "name": "RuntimeFileSystem",
  "description": "Enhanced filesystem interface for runtime workers.\nExtends the 11 base primitives with higher-level helper methods that have\ndefault implementations built from the primitives (via `createRuntimeFileSystem`).\nBackends may supply optimized overrides for any of the enhanced methods.",
  "entries": [
    {
      "name": "readFile",
      "description": "Read file as text.\nRead file as binary.",
      "tags": [],
      "type": "{ (path: string, encoding: \"utf8\"): Promise<string>; (path: string): Promise<Uint8Array<ArrayBuffer>>; }",
      "simplifiedType": "function",
      "required": true,
      "deprecated": false
    },
    {
      "name": "writeFile",
      "description": "Write file (text or binary).",
      "tags": [],
      "type": "(path: string, data: Uint8Array<ArrayBuffer> | string) => Promise<void>",
      "simplifiedType": "function",
      "required": true,
      "deprecated": false
    },
    {
      "name": "mkdir",
      "description": "Create directory, optionally recursive.",
      "tags": [],
      "type": "(path: string, options?: { recursive?: boolean; }) => Promise<void>",
      "simplifiedType": "function",
      "required": true,
      "deprecated": false
    },
    {
      "name": "readdir",
      "description": "List directory entries (file/dir names).",
      "tags": [],
      "type": "(path: string) => Promise<string[]>",
      "simplifiedType": "function",
      "required": true,
      "deprecated": false
    },
    {
      "name": "unlink",
      "description": "Delete file.",
      "tags": [],
      "type": "(path: string) => Promise<void>",
      "simplifiedType": "function",
      "required": true,
      "deprecated": false
    },
    {
      "name": "rmdir",
      "description": "Remove an empty directory.",
      "tags": [],
      "type": "(path: string) => Promise<void>",
      "simplifiedType": "function",
      "required": true,
      "deprecated": false
    },
    {
      "name": "rename",
      "description": "Rename / move a file or directory.",
      "tags": [],
      "type": "(oldPath: string, newPath: string) => Promise<void>",
      "simplifiedType": "function",
      "required": true,
      "deprecated": false
    },
    {
      "name": "stat",
      "description": "Get file or directory metadata.",
      "tags": [],
      "type": "(path: string) => Promise<FileStat>",
      "simplifiedType": "function",
      "required": true,
      "deprecated": false
    },
    {
      "name": "lstat",
      "description": "Get file or directory metadata without following symlinks.",
      "tags": [],
      "type": "(path: string) => Promise<FileStat>",
      "simplifiedType": "function",
      "required": true,
      "deprecated": false
    },
    {
      "name": "exists",
      "description": "Check if path exists.",
      "tags": [],
      "type": "(path: string) => Promise<boolean>",
      "simplifiedType": "function",
      "required": true,
      "deprecated": false
    },
    {
      "name": "watch",
      "description": "Subscribe to filesystem change events for the given paths.\nReturns an unsubscribe function. Events are filtered server-side.",
      "tags": [],
      "type": "((request: RuntimeWatchRequest, handler: (event: RuntimeWatchEvent) => void) => () => void) | undefined",
      "simplifiedType": "function",
      "required": false,
      "deprecated": false
    },
    {
      "name": "readFiles",
      "description": "Batch-read multiple files as binary. Default: `Promise.all(paths.map(readFile))`.",
      "tags": [],
      "type": "(paths: string[]) => Promise<Record<string, Uint8Array<ArrayBuffer>>>",
      "simplifiedType": "function",
      "required": true,
      "deprecated": false
    },
    {
      "name": "readdirContents",
      "description": "Read all file contents in a directory (skips subdirectories).",
      "tags": [],
      "type": "(directoryPath: string) => Promise<Record<string, Uint8Array<ArrayBuffer>>>",
      "simplifiedType": "function",
      "required": true,
      "deprecated": false
    },
    {
      "name": "readdirStat",
      "description": "Get stat information for all entries in a directory.",
      "tags": [],
      "type": "(directoryPath: string) => Promise<FileStatEntry[]>",
      "simplifiedType": "function",
      "required": true,
      "deprecated": false
    },
    {
      "name": "ensureDir",
      "description": "Ensure a directory exists, creating parents as needed. Default: `mkdir(path, { recursive: true })`.",
      "tags": [],
      "type": "(path: string) => Promise<void>",
      "simplifiedType": "function",
      "required": true,
      "deprecated": false
    }
  ]
}}
/>

<TypeTable
  type={{
  "name": "FsLike",
  "description": "Minimal interface for any fs-compatible object with a `promises` namespace.\nMatches the shape of `fs` from BrowserFS, memfs, and similar\nlibraries without importing them directly.\nUses `ArrayBufferLike` to accept both `ArrayBuffer` and `SharedArrayBuffer`\n(BrowserFS returns `Buffer<ArrayBufferLike>`).",
  "entries": [
    {
      "name": "promises",
      "description": "",
      "tags": [],
      "type": "{ readFile(path: string, encoding: \"utf8\"): Promise<string>; readFile(path: string): Promise<Uint8Array>; writeFile(path: string, data: Uint8Array | string): Promise<void>; mkdir(path: string, options?: { recursive?: boolean; }): Promise<string | undefined | void>; readdir(path: string): Promise<string[]>; unlink(path: string): Promise<void>; rmdir(path: string): Promise<void>; rename(oldPath: string, newPath: string): Promise<void>; stat(path: string): Promise<NativeStats>; lstat(path: string): Promise<NativeStats>; }",
      "simplifiedType": "object",
      "required": true,
      "deprecated": false
    }
  ]
}}
/>

Constructors [#constructors]

| Function                        | Import Path                  | Description                                               |
| ------------------------------- | ---------------------------- | --------------------------------------------------------- |
| `fromNodeFS(basePath)`          | `@taucad/runtime/filesystem` | Node.js filesystem rooted at `basePath`                   |
| `fromMemoryFS(files?)`          | `@taucad/runtime`            | In-memory Map-backed filesystem, optionally seeded        |
| `fromFsLike(fs, rootPath?)`     | `@taucad/runtime`            | Any fs-compatible object (BrowserFS, memfs, polyfills)    |
| `createRuntimeFileSystem(base)` | `@taucad/runtime/filesystem` | Wrap `RuntimeFileSystemBase` with enhanced helper methods |

Bridge Types [#bridge-types]

<TypeTable
  type={{
  "name": "BridgeHandle",
  "description": "Handle returned by {@link createBridgePort}, providing the client-side MessagePort and a dispose function.",
  "entries": [
    {
      "name": "port",
      "description": "",
      "tags": [],
      "type": "MessagePort",
      "simplifiedType": "object",
      "required": true,
      "deprecated": false
    },
    {
      "name": "dispose",
      "description": "",
      "tags": [],
      "type": "() => void",
      "simplifiedType": "function",
      "required": true,
      "deprecated": false
    }
  ]
}}
/>

<TypeTable
  type={{
  "name": "BridgeServerHandle",
  "description": "Handle returned by {@link createBridgeServer}, providing an event emitter for server-to-client push messages.",
  "entries": [
    {
      "name": "emit",
      "description": "",
      "tags": [],
      "type": "(event: string, data: unknown) => void",
      "simplifiedType": "function",
      "required": true,
      "deprecated": false
    }
  ]
}}
/>

<TypeTable
  type={{
  "name": "FileSystemBridgeOptions",
  "description": "Options for configuring the filesystem bridge message type.",
  "entries": [
    {
      "name": "messageType",
      "description": "",
      "tags": [],
      "type": "string | undefined",
      "simplifiedType": "string",
      "required": false,
      "deprecated": false
    },
    {
      "name": "uiCoalescingWindowMs",
      "description": "Coalescing window for UI-bound fileChanged events (default: 500ms).",
      "tags": [],
      "type": "number | undefined",
      "simplifiedType": "number",
      "required": false,
      "deprecated": false
    },
    {
      "name": "createCoalescer",
      "description": "Factory for creating a change event coalescer. When provided, events\nfrom `changeEventBus` are batched before broadcasting to bridge clients.\nWhen omitted, events pass through without batching.",
      "tags": [],
      "type": "CoalescerFactory | undefined",
      "simplifiedType": "CoalescerFactory",
      "required": false,
      "deprecated": false
    },
    {
      "name": "createThrottledWorker",
      "description": "Factory for creating a throttled event worker. When provided alongside\n`createCoalescer`, coalesced batches flow through the throttled worker\nfor chunked delivery to bridge clients.",
      "tags": [],
      "type": "ThrottledWorkerFactory | undefined",
      "simplifiedType": "ThrottledWorkerFactory",
      "required": false,
      "deprecated": false
    }
  ]
}}
/>

<TypeTable
  type={{
  "name": "ExposeFileSystemHandle",
  "description": "Handle returned by {@link exposeFileSystem} for managing bridge connections and cleanup.",
  "entries": [
    {
      "name": "cleanup",
      "description": "",
      "tags": [],
      "type": "() => void",
      "simplifiedType": "function",
      "required": true,
      "deprecated": false
    },
    {
      "name": "activePorts",
      "description": "",
      "tags": [],
      "type": "Set<MessagePort>",
      "simplifiedType": "object",
      "required": true,
      "deprecated": false
    },
    {
      "name": "serverHandles",
      "description": "",
      "tags": [],
      "type": "Map<MessagePort, BridgeServerHandle>",
      "simplifiedType": "object",
      "required": true,
      "deprecated": false
    }
  ]
}}
/>

Bridge Utilities [#bridge-utilities]

For cross-worker filesystem access, these utilities create MessagePort-based bridges:

| Function                                       | Description                                                          |
| ---------------------------------------------- | -------------------------------------------------------------------- |
| `createBridgePort(handlers)`                   | Create a MessagePort bridge to a filesystem. Returns `BridgeHandle`. |
| `createBridgeServer(handlers, port, options?)` | Serve an object's methods over a MessagePort.                        |
| `createBridgeProxy<T>(port)`                   | Create a Proxy-based client that dispatches calls over MessagePort.  |
| `createBridgeCall(port, method, args)`         | Send a single RPC call over a MessagePort and await the response.    |
| `exposeFileSystem(handlers, options?)`         | Expose a filesystem to incoming bridge connections.                  |
| `createFileSystemBridge(handlers, options?)`   | Create a MessageChannel and transfer a port to a worker.             |
| `catchMessages(port, handler)`                 | Attach an error-handling message listener to a MessagePort.          |
| `extractTransferables(value)`                  | Walk a value and collect ArrayBuffers for transfer.                  |

Usage [#usage]

Node.js Filesystem [#nodejs-filesystem]

```typescript
import { createRuntimeClient } from '@taucad/runtime';
import { fromNodeFS } from '@taucad/runtime/filesystem/node';
import { replicad } from '@taucad/runtime/kernels';
import { esbuild } from '@taucad/runtime/bundler';

const client = createRuntimeClient({
  kernels: [replicad()],
  bundlers: [esbuild()],
  fileSystem: fromNodeFS('/path/to/project'),
});
```

In-Memory Filesystem [#in-memory-filesystem]

```typescript
import { createRuntimeClient, fromMemoryFS } from '@taucad/runtime';
import { replicad } from '@taucad/runtime/kernels';
import { esbuild } from '@taucad/runtime/bundler';

const client = createRuntimeClient({
  kernels: [replicad()],
  bundlers: [esbuild()],
  fileSystem: fromMemoryFS({
    'main.ts': 'export default function main() { return null; }',
  }),
});
```

Filesystem Bridge [#filesystem-bridge]

```typescript @ts-nocheck
import { createBridgePort } from '@taucad/runtime/filesystem';
import { fromNodeFS } from '@taucad/runtime/filesystem/node';

const fileSystem = fromNodeFS('/path/to/project');
const { port, dispose } = createBridgePort(fileSystem);

// Transfer port to a worker for remote filesystem access
worker.postMessage({ fsPort: port }, [port]);

// When done, release resources
dispose();
```

Related [#related]

* [Set Up the Filesystem](../guides/filesystem-setup) -- Practical guide to filesystem configuration
* [Worker Model](../concepts/worker-model) -- How the filesystem is bridged to the worker
* [API: Client](./client) -- `createRuntimeClient` filesystem option
* [API: Types](./types) -- `RuntimeFileSystemBase`, `RuntimeFileSystem`
