paperclipai/paperclip · error

Workspace uploads require a platform with confined file open

Error message

Workspace uploads require a platform with confined file opens; use an authorized artifact reference

What it means

On platforms other than darwin and linux, openRunnerApiWorkspaceFile throws "Workspace uploads require a platform with confined file opens". Confined workspace uploads rely on platform primitives (macOS O_NOFOLLOW_ANY, Linux openat-style /proc/self/fd directory links); any other OS cannot guarantee symlink-race-free opens, so the function fails closed and directs callers to use an authorized artifact reference instead.

Source

Thrown at server/src/services/native-runtime/runner-api-files.ts:14

import { constants } from "node:fs";
import { open, type FileHandle } from "node:fs/promises";
import { isAbsolute } from "node:path";

/** Open a previously authorized canonical path without following raced symlinks. */
export async function openRunnerApiWorkspaceFile(path: string): Promise<FileHandle> {
  if (!isAbsolute(path)) throw new Error("Workspace file must have a canonical absolute path");
  if (process.platform === "darwin") {
    // Darwin sys/fcntl.h: O_NOFOLLOW_ANY rejects symlinks at every component.
    // Node does not expose this flag in fs.constants. Unsupported kernels fail
    // closed instead of falling back to a pathname check followed by open.
    return open(path, constants.O_RDONLY | constants.O_NONBLOCK | 0x20000000);
  }
  if (process.platform !== "linux") throw new Error("Workspace uploads require a platform with confined file opens; use an authorized artifact reference");
  const parts = path.split("/").filter(Boolean);
  if (!parts.length || parts.some(part => part === "." || part === "..")) throw new Error("Invalid canonical workspace path");
  let directory = await open("/", constants.O_RDONLY | constants.O_DIRECTORY);
  try {
    for (const part of parts.slice(0, -1)) {
      // Linux magic descriptor links provide openat-style directory confinement.
      const next = await open(`/proc/self/fd/${directory.fd}/${part}`, constants.O_RDONLY | constants.O_DIRECTORY | constants.O_NOFOLLOW);
      await directory.close();
      directory = next;
    }
    return await open(`/proc/self/fd/${directory.fd}/${parts.at(-1)}`, constants.O_RDONLY | constants.O_NONBLOCK | constants.O_NOFOLLOW);
  } finally { await directory.close(); }
}

View on GitHub (pinned to 01ad858492)

Solutions

  1. Run the Paperclip server on Linux or macOS, where confined file opens are supported.
  2. On Windows, use WSL2 (the process then reports linux) or a Linux container for the server.
  3. Instead of a raw workspace path upload, attach the file as an authorized artifact reference, which is platform-independent.
  4. If this is a legitimate deployment target, upstream platform support with an equivalent confined-open primitive before enabling workspace uploads there.

Example fix

// before (unsupported)
// server running on win32; openRunnerApiWorkspaceFile('C:\\workspace\\f.txt') throws
// after
// run server under WSL2/Linux and pass a POSIX absolute path, or upload via artifact reference
await openRunnerApiWorkspaceFile("/workspace/f.txt"); // on linux
Defensive patterns

Strategy: validation

Validate before calling

const SUPPORTED = new Set(["darwin", "linux"]);
if (!SUPPORTED.has(process.platform)) {
  throw new Error(`workspace uploads unsupported on ${process.platform}; use artifact references or run the server on Linux/macOS`);
}

Type guard

function supportsConfinedOpens(p: NodeJS.Platform): boolean { return p === "darwin" || p === "linux"; }

Try / catch

try {
  const handle = await openRunnerApiWorkspaceFile(path);
} catch (err) {
  if (err instanceof Error && err.message.startsWith("Workspace uploads require a platform")) {
    // fall back to uploading via an authorized artifact reference instead of a workspace path
  } else throw err;
}

Prevention

When it happens

Trigger: A workspace file upload through the runner API is attempted while process.platform is not "darwin" or "linux" — e.g. running the Paperclip server natively on Windows or FreeBSD, or inside an emulator reporting an exotic platform value.

Common situations: Development on Windows host without WSL; running the server in a FreeBSD/Alpine-musl container with an unusual platform string; deploying the native-runtime to an unsupported OS.

Understand the failure class

Background: "unsupported platform" / "not supported on this platform" errors: what they mean and how to fix them — this error's family across 47 libraries.

Related errors


AI-assisted analysis of paperclipai/paperclip@01ad858492 (2026-09-10). Data as JSON: /api/errors/0e6207d5aef84e09. Report an issue: GitHub.