FWS – pip-installable embedded process supervisor with PTY/pipe/dtach back ends

I’m releasing *Framework Shells* (`fws`): a standalone Python package for orchestrating long-running background processes (“shells”) with *PTY*, *pipes*, and *dtach* backends.

This is meant for environments where you don’t want to stand up a full supervisor stack (or don’t have one): quick multi-service prototypes, dev environments, constrained userlands, etc.

### What it does

* Spawn/manage shells with:

  * **PTY**: interactive terminal sessions (resize, input, stream)
  * **Pipes**: stdin/stdout/stderr streams (good for daemons/LSPs)
  * **dtach**: persistent sessions you can attach/detach to (survives manager restarts)
* *Runtime isolation* (the big feature): shells are namespaced by `~/.cache/framework_shells/runtimes/<repo_fingerprint>/<runtime_id>/...` so two clones of the same repo can run concurrently without cross-adoption or cross-control. * *Control surfaces*: CLI + optional FastAPI/WS UI for listing, logs, and lifecycle actions. * Optional *hooks* for host integration (external registries/telemetry).

### CLI quickstart

```bash # list shells fws list

# run a one-off shell (no spec) fws run --backend pty --label demo -- bash -l -i

# apply a YAML shellspec (recommended) fws up shells.yaml

# terminate shells fws down

# attach to a dtach-backed shell fws attach <shell_id>

# show managed shells + procfs descendants fws tree --depth 4 ```

### Shellspec example

```yaml version: "1" shells: worker: backend: proc cwd: ${ctx:PROJECT_ROOT} subgroups: ["worker", "project:${ctx:APP_ID}"] command: ["python", "-m", "your_module.worker", "--port", "${free_port}"] ```

### Isolation + security model (simple by default)

* `FRAMEWORK_SHELLS_SECRET` derives the `runtime_id` (namespace) and API tokens. * If the secret is set, mutating API endpoints require:

  * `Authorization: Bearer <token>` (or `X-Framework-Key`).
* If the secret is unset, auth is disabled (dev mode).

Hard limit: if two runtimes share the same OS user/UID, the OS may still allow signaling each other’s processes. The guarantee is: no cross-count/adopt/control *through the library’s control plane*.

### Real-world usage

I use this as the substrate of a full dev environment where “apps are shells” (terminals, IDE + LSP, agent/MCP, aria2 RPC, file explorer, llama.cpp runner, etc.). Repo:

```text https://github.com/mrsurge/termux-extensions-2 ```

### Feedback I want

* Does the secret/fingerprint/runtime isolation contract feel right? * Any obvious foot-guns in the default API/CLI? * Expectations vs systemd/supervisord/tmux/dtach: where would you use this?

github.com/mrsurge/framework-shells

pip install "framework-shells @ git+https://github.com/mrsurge/framework-shells@main"

```bash fws --help ```

2 points | by mrsurge 15 hours ago

0 comments