Skip to content

feat(ai-sandbox): persist sandbox workspace / filesystem data across lifecycle #1029

Description

@tombeckenham

Summary

Add workspace / filesystem durability for sandboxes so project files (and related disk state) can survive sandbox sleep, restart, and destroy—not just which provider sandbox id to resume.

This is separate from instance placement durability.

Context / related work

Layer What it answers Status
Instance durability (SandboxInstanceStore) Which provider sandbox to resume for a key across replicas #988
Durable agent runs (shared RunRecord / run log) Which run is active and how to reconnect to events #1015 (stacked on #988)
Filesystem / workspace durability What files survive sleep/destroy This issue

Instance resume is necessary but not sufficient: even with a stable sandbox id, container local disk is often ephemeral. Apps need an explicit way to persist and restore workspace contents.

Problem

Today:

  • ensure / resume can reconnect to a provider sandbox when instance records exist (feat(ai-sandbox): SandboxInstanceStore instance durability (BYO) #988).
  • Files written only on the container filesystem are typically lost after sleep, eviction, or destroy().
  • Provider capabilities already surface concepts like snapshots and durableFilesystem, but there is no first-class TanStack AI API for “save workspace” / “restore workspace” that works across providers (or documents Cloudflare-native paths clearly).

Cloudflare Sandbox SDK already offers building blocks (R2 bucket mounts, backup/restore of directories); other providers have snapshots or durable volumes. We need a provider-agnostic product surface (or a clear composition model) so apps don’t invent one-off scripts per vendor.

Goals

  1. Persist workspace state (default /workspace or configured root) across sandbox lifecycle events.
  2. Restore that state on create/resume so the next run continues with the same project files.
  3. Integrate with instance durability when present (e.g. store latestSnapshotId / backup handle on SandboxInstanceRecord or an adjacent artifact store).
  4. Document the two durability layers (instance vs filesystem) so apps wire the right stores.
  5. Prefer provider-native mechanisms where available (snapshots, durable FS, R2 mount, backup/restore), with a clear capability matrix.

Non-goals (for the first cut)

  • Replacing or merging with chat persistence (@tanstack/ai-persistence transcripts / runs / interrupts).
  • Auto-persisting the entire container root (system packages, secrets, etc.).
  • Requiring every provider to implement the same backend (R2-only is fine as a Cloudflare path; others can use snapshots).
  • Shipping a shared Vitest testkit package redesign (orthogonal to this feature).

Design sketch (open for discussion)

Possible shapes (pick / mix during design):

  1. Snapshot API on SandboxHandle / provider

  2. Backup / restore workspace

    • Point-in-time archive of the workspace dir to object storage (Cloudflare-style createBackup / restoreBackup or BYO artifact store)
  3. Mount-backed durable paths

    • Mount R2/S3 (or provider durable volume) under /data or /workspace for live persistence without explicit snapshot
  4. Capability-gated

    • Only expose APIs when capabilities().snapshots or durableFilesystem is true; docs say what to do when neither exists

Suggested dependency order:

#988 instance store (where)  →  this issue (what on disk)

Implementable after #988 lands; can prototype with in-memory instance store for single-process.

Acceptance criteria

  • Documented API for save + restore of workspace (or explicit mount-based durability).
  • At least one provider path fully wired end-to-end (likely Cloudflare: R2 mount and/or backup-restore).
  • Capability matrix updated for providers (snapshots / durableFilesystem / limitations).
  • Integration with instance resume when a store is configured (no stale snapshot id after clear-on-upsert invariants).
  • E2E: write files → tear down / destroy (or simulated sleep) → resume → files still present.
  • Docs distinguish instance durability vs filesystem durability (link from docs/sandbox/durability.md).
  • Secrets never written into snapshots/backups (existing workspace secret rules).

Open questions

  1. Live mount vs explicit snapshot/backup as the default product story?
  2. Should backup handles live in SandboxInstanceRecord, a generation artifact store, or a new small store type?
  3. Scope of first PR: Cloudflare-only vs multi-provider snapshot abstraction?
  4. Interaction with harness project roots and gitignore (exclude node_modules, etc.)?

References

Metadata

Metadata

Assignees

No one assigned

    Labels

    enhancementNew feature or requestpersistenceDurable chat state: @tanstack/ai-persistence, client persistence, adapters, locks

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions