From 7b32f5bc2fac0315fb0f1b71e95b644a00a51e1d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Andr=C3=A9=20Padez?= Date: Thu, 13 Aug 2026 11:56:16 +0000 Subject: [PATCH] don't provision rootless docker for new members MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Commented out at the call site in provisionOsAccount, with the import. The code in os-user-docker.ts stays and is now unreferenced — turning it back on is uncommenting two blocks. Only affects NEW accounts. Members provisioned before this keep their daemon, and deprovisionOsAccount still tears one down, which is what those accounts need. Verified: transpiles. tsgo has still not run in this tree (node_modules is empty). Co-Authored-By: Claude Opus 5 --- src/servers/api/users/provision-os.ts | 43 +++++++++++++-------------- 1 file changed, 21 insertions(+), 22 deletions(-) diff --git a/src/servers/api/users/provision-os.ts b/src/servers/api/users/provision-os.ts index efea4295..90bd473f 100644 --- a/src/servers/api/users/provision-os.ts +++ b/src/servers/api/users/provision-os.ts @@ -3,7 +3,8 @@ import { ensureOsUser, osUserHome } from '@@/os-user'; import { provisionSshAccess } from '@@/os-user-ssh'; import { seedShellConfig } from '@@/os-user-shell'; import { provisionClaudeCli } from '@@/os-user-claude'; -import { provisionRootlessDocker } from '@@/os-user-docker'; +// Disabled 2026-08-13 — see the commented-out step in provisionOsAccount below. +// import { provisionRootlessDocker } from '@@/os-user-docker'; import { provisionUserDirs } from '@@/data-path'; // Giving an account its Linux side: the directory skeleton, the Linux user, the confinement, the keys. @@ -77,18 +78,24 @@ export async function provisionOsAccount(params: { // cannot do it for them and must not try, because the alternative is lending them the owner's credential. const claude = await provisionClaudeCli({ email: params.email, osUser: account.osUser }); - // Their own rootless Docker daemon. Last, and the most tolerant of failure: a host without the uidmap - // package or a kernel that will not do rootless still gets a perfectly good account, minus containers. + // ── Rootless Docker: DISABLED 2026-08-13, code kept ── // - // Provisioned for every member rather than behind a toggle, because "can I run a database to develop - // against" should not be an administrative request. The cost — one daemon and one image cache per member — - // is real and is written down in os-user-docker.ts. - const docker = await provisionRootlessDocker({ - osUser: account.osUser, - uid: account.uid, - gid: account.gid, - home: osUserHome(params.email), - }); + // Every member got their own rootless daemon, unconditionally, on the argument that "can I run a database + // to develop against" should not be an administrative request. The cost is the counter-argument and it is + // per member, not per install: one daemon, one image cache, one subuid range — see os-user-docker.ts. + // + // Turned off at the call rather than deleted, so turning it back on is uncommenting this block and the + // import. `os-user-docker.ts` is otherwise unreferenced now; nothing else calls it. + // + // Note this only stops NEW accounts. An account provisioned before today keeps its daemon, and + // `deprovisionOsAccount` still cleans one up, which is what an existing member needs. + // + // const docker = await provisionRootlessDocker({ + // osUser: account.osUser, + // uid: account.uid, + // gid: account.gid, + // home: osUserHome(params.email), + // }); // The Linux account is recorded either way: it exists, it is confined, and a member's terminal can run as // it. Only the keys are missing, and that is what the error says. @@ -98,17 +105,9 @@ export async function provisionOsAccount(params: { // Reported in order of consequence, not in order of execution: no keys matters more than a plain prompt, // which matters more than no containers. Only one is surfaced because the UI shows one line — the rest are // in the log. - for (const step of [claude, shell, docker] as const) { + for (const step of [claude, shell] as const) { if (!step.ok) console.warn(`[users] ${params.email}: ${step.error}`); } - const error = !ssh.ok - ? ssh.error - : !claude.ok - ? claude.error - : !shell.ok - ? shell.error - : !docker.ok - ? docker.error - : null; + const error = !ssh.ok ? ssh.error : !claude.ok ? claude.error : !shell.ok ? shell.error : null; return { osUser: account.osUser, sshPublicKey, error }; }