Skip to content

Production-ready system for running multiple isolated code-server workspaces.

License

Notifications You must be signed in to change notification settings

bufferring/codex-workspaces

Repository files navigation

β–ˆβ–ˆβ•—   β–ˆβ–ˆβ•—β–ˆβ–ˆβ–ˆβ•—   β–ˆβ–ˆβ•—β–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ•—β–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ•— β–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ•—      β–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ•— β–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ•— β–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ•— β–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ•—β–ˆβ–ˆβ•—  β–ˆβ–ˆβ•—
β–ˆβ–ˆβ•‘   β–ˆβ–ˆβ•‘β–ˆβ–ˆβ–ˆβ–ˆβ•—  β–ˆβ–ˆβ•‘β–ˆβ–ˆβ•”β•β•β•β•β•β–ˆβ–ˆβ•”β•β•β•β•β•β–ˆβ–ˆβ•”β•β•β–ˆβ–ˆβ•—    β–ˆβ–ˆβ•”β•β•β•β•β•β–ˆβ–ˆβ•”β•β•β•β–ˆβ–ˆβ•—β–ˆβ–ˆβ•”β•β•β–ˆβ–ˆβ•—β–ˆβ–ˆβ•”β•β•β•β•β•β•šβ–ˆβ–ˆβ•—β–ˆβ–ˆβ•”β•
β–ˆβ–ˆβ•‘   β–ˆβ–ˆβ•‘β–ˆβ–ˆβ•”β–ˆβ–ˆβ•— β–ˆβ–ˆβ•‘β–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ•—  β–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ•—  β–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ•‘    β–ˆβ–ˆβ•‘     β–ˆβ–ˆβ•‘   β–ˆβ–ˆβ•‘β–ˆβ–ˆβ•‘  β–ˆβ–ˆβ•‘β–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ•—   β•šβ–ˆβ–ˆβ–ˆβ•”β• 
β–ˆβ–ˆβ•‘   β–ˆβ–ˆβ•‘β–ˆβ–ˆβ•‘β•šβ–ˆβ–ˆβ•—β–ˆβ–ˆβ•‘β–ˆβ–ˆβ•”β•β•β•  β–ˆβ–ˆβ•”β•β•β•  β–ˆβ–ˆβ•”β•β•β–ˆβ–ˆβ•‘    β–ˆβ–ˆβ•‘     β–ˆβ–ˆβ•‘   β–ˆβ–ˆβ•‘β–ˆβ–ˆβ•‘  β–ˆβ–ˆβ•‘β–ˆβ–ˆβ•”β•β•β•   β–ˆβ–ˆβ•”β–ˆβ–ˆβ•— 
β•šβ–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ•”β•β–ˆβ–ˆβ•‘ β•šβ–ˆβ–ˆβ–ˆβ–ˆβ•‘β–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ•—β–ˆβ–ˆβ•‘     β–ˆβ–ˆβ•‘  β–ˆβ–ˆβ•‘    β•šβ–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ•—β•šβ–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ•”β•β–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ•”β•β–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ–ˆβ•—β–ˆβ–ˆβ•”β• β–ˆβ–ˆβ•—
 β•šβ•β•β•β•β•β• β•šβ•β•  β•šβ•β•β•β•β•šβ•β•β•β•β•β•β•β•šβ•β•     β•šβ•β•  β•šβ•β•     β•šβ•β•β•β•β•β• β•šβ•β•β•β•β•β• β•šβ•β•β•β•β•β• β•šβ•β•β•β•β•β•β•β•šβ•β•  β•šβ•β•
**Version:** v3.0.0 (Security-Enhanced)  
    Tailscale β€’ Nginx β€’ code-server β€’ Multi-user
**Breaking changes:** Unix user isolation added in v3.0.0
==================================================

UNEFA Codex - Dockerized Code-Server Workspace System

Version Shell License Platform Docker

Languages: πŸ‡¬πŸ‡§ English | πŸ‡ͺπŸ‡Έ EspaΓ±ol

A production-ready system for running multiple isolated code-server workspaces using Docker, Nginx, and Tailscale.

πŸ—οΈ Architecture

β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”
β”‚                         HOST SYSTEM                          β”‚
β”‚                                                               β”‚
β”‚  β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”         β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”   β”‚
β”‚  β”‚   Tailscale  │────────▢│          Nginx              β”‚   β”‚
β”‚  β”‚    Funnel    β”‚         β”‚      (Port 80)              β”‚   β”‚
β”‚  β”‚  (Public)    β”‚         β”‚                             β”‚   β”‚
β”‚  β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜         β”‚  / β†’ Landing Page           β”‚   β”‚
β”‚                           β”‚  /user1/ β†’ 127.0.0.1:8081   β”‚   β”‚
β”‚                           β”‚  /user2/ β†’ 127.0.0.1:8082   β”‚   β”‚
β”‚                           β”‚  ...                         β”‚   β”‚
β”‚                           β”‚  /user20/ β†’ 127.0.0.1:8100  β”‚   β”‚
β”‚                           β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜   β”‚
β”‚                                      β”‚                       β”‚
β”‚                                      β–Ό                       β”‚
β”‚  β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚
β”‚  β”‚         DOCKER CONTAINER (codex-workspaces)            β”‚ β”‚
β”‚  β”‚                                                         β”‚ β”‚
β”‚  β”‚  β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”  β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”       β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”        β”‚ β”‚
β”‚  β”‚  β”‚ user1    β”‚  β”‚ user2    β”‚  ...  β”‚ user20   β”‚        β”‚ β”‚
β”‚  β”‚  β”‚ :8081    β”‚  β”‚ :8082    β”‚       β”‚ :8100    β”‚        β”‚ β”‚
β”‚  β”‚  β”‚code-     β”‚  β”‚code-     β”‚       β”‚code-     β”‚        β”‚ β”‚
β”‚  β”‚  β”‚server    β”‚  β”‚server    β”‚       β”‚server    β”‚        β”‚ β”‚
β”‚  β”‚  β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜  β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜       β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜        β”‚ β”‚
β”‚  β”‚                                                         β”‚ β”‚
β”‚  β”‚  All workspaces running in ONE container               β”‚ β”‚
β”‚  β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β”‚
β”‚                           β”‚                                  β”‚
β”‚                           β–Ό                                  β”‚
β”‚  β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚
β”‚  β”‚       ~/codex/users/ (Persistent Storage)              β”‚ β”‚
β”‚  β”‚                                                         β”‚ β”‚
β”‚  β”‚  user1/  user2/  user3/  ...  user20/                  β”‚ β”‚
β”‚  β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β”‚
β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜

Components: Nginx (reverse proxy) + Tailscale (public exposure) on host β†’ Docker container with code-server instances β†’ Persistent storage


πŸš€ Quick Start

Prerequisites

  • Docker, Nginx, Tailscale (authenticated)
  • curl, unzip
  • Ubuntu 22.04 LTS recommended

Installation

chmod +x codex-setup.sh
sudo ./codex-setup.sh

You will be asked to choose:

  1. Full Setup (Tailscale Public Access): Public URL via Tailscale funnel (https://app.ts.net)
  2. Local Network Setup (LAN only): LAN access only via server IP (http://192.168.x.x)
  3. Uninstall (Delete everything): Remove Codex services, data, and configs

Usage Modes

Option 1: Full Setup (Tailscale Public Access)

  • Secure HTTPS endpoint through Tailscale funnel
  • Accessible from anywhere with your Tailscale auth
  • Prompts for myapp.ts.net-style domain

Option 2: Local Network Setup (LAN only)

  • Standard HTTP served on the LAN only
  • Detects server IP automatically (you can override)
  • No Tailscale or public internet required; access via http://<SERVER-IP>/

Option 3: Uninstall (Delete everything)

  • Stops systemd services and removes Docker container/image
  • Removes Nginx config, workspace data, and supporting files
  • Requires typing YES to confirm irreversible deletion

Non-Interactive Setup (CI/CD)

export CODEX_NUM_USERS=15
export CODEX_DOMAIN="myapp.ts.net"
sudo -E ./codex-setup.sh

πŸ’» Pre-installed Languages

Language Version Tools
Python 3.10+ pip, venv, pipenv, poetry, black, flake8
Node.js 22.12.0 LTS (NVM) Bun (preferred), npm, yarn, pnpm, TypeScript, ESLint, Prettier, nodemon
Node.js (Next) 24.x Current Available via NVM (nvm use 24)
Go 1.25.5 go mod, go build, go test
Rust Latest (rustup) cargo, rustc
C++ GCC toolchain g++, make, build-essential
C# .NET SDK 8.0 dotnet CLI, new console/web templates

Also included: Git, build-essential, gcc/g++, wget, curl, code-server, NVM profile hooks, .NET workload manager

Supported projects: React, Vue, Flask, Django, Express, FastAPI, REST APIs, CLI tools, data science, and more


πŸ” Workspace Credentials

  • Workspace 1: user1 / user1-pass
  • Workspace 2: user2 / user2-pass
  • ...and so on

πŸ›‘οΈ Security & Isolation

Unix User Isolation:

  • Each workspace runs as dedicated Linux user (user1-user30)
  • No root access inside workspaces
  • Users can VIEW other workspaces (read-only) but CANNOT DELETE files outside their own

Permissions:

  • Own workspace: Full read/write/delete
  • Other workspaces: Read-only
  • System files: Read-only

Test it:

docker exec -it codex-workspaces su - user1
whoami  # Shows: user1
rm /bin/ls  # Permission denied

πŸŽ›οΈ Management

View Status

systemctl status codex-workspaces
docker ps | grep codex

Restart Services

sudo systemctl restart codex-workspaces

View Logs

docker logs -f codex-workspaces
journalctl -xeu codex-workspaces

Full Uninstall

sudo ./codex-setup.sh
# Choose option 3: Uninstall (Delete everything)
# Type 'YES' to confirm

What gets removed:

  • All workspace data
  • Docker container & image
  • Nginx configs
  • Systemd services
  • Tailscale funnel

πŸ”§ Configuration

Edit variables before installation or use environment variables:

CODEX_NUM_USERS=25        # Number of workspaces (1-30)
CODEX_DOMAIN="app.ts.net" # Your Tailscale domain

To change configuration: Re-run setup script with new values. Cleanup is automatic.


πŸ› Troubleshooting

Issue Solution
Container not running sudo systemctl restart codex-workspaces
502 Bad Gateway Check if container is up: docker ps
Port conflicts Verify ports 8081-81XX are available
File permission errors Workspaces run as Unix users (by design)

Check logs:

docker logs --tail 50 codex-workspaces
journalctl -xeu codex-workspaces --no-pager -n 50

πŸ“Š Compatibility

Component Requirement
OS Ubuntu 22.04 LTS
Docker 20.10+
Nginx 1.18+
Tailscale Any recent version

Version: v3.0.0 (Security-Enhanced)
Release: December 2025

Upgrading from v1.x

# Backup data (optional)
sudo cp -r ~/codex/users ~/codex-backup

# Run setup (automatic cleanup)
sudo ./codex-setup.sh

Breaking changes: Unix user isolation added in v3.0.0


πŸ“‚ Repository Layout

codex-workspaces/
β”œβ”€β”€ codex-setup.sh          # Main installer/orchestrator script
β”œβ”€β”€ src/                    # React + Tailwind UI for the desktop companion
β”œβ”€β”€ public/                 # Static assets (workspaces.json, manifest, icons)
β”œβ”€β”€ src-tauri/              # Tauri Rust backend and bundle config
β”œβ”€β”€ dist/                   # Vite build output (generated)
β”œβ”€β”€ node_modules/           # Project dependencies (generated)
β”œβ”€β”€ package.json            # Vite/Tauri workspace manifest
β”œβ”€β”€ tailwind.config.js      # Tailwind design tokens
β”œβ”€β”€ vite.config.ts          # Vite + PWA configuration
β”œβ”€β”€ README.md               # EN docs
└── README.es.md            # ES docs

Provisioned Host Layout

Once codex-setup.sh runs it provisions the server under ~/codex/:

~/codex/
β”œβ”€β”€ landing/                # Workspace selector served by Nginx
β”œβ”€β”€ users/                  # user1 … userN home directories
└── docker/                 # Auto-generated Dockerfile and startup scripts

πŸ–₯️ Desktop Companion App

The bundled desktop assistant streamlines running codex-setup.sh and opening workspaces.

Requirements

  • Bun (preferred) or Node.js 18+ with npm available
  • Rust toolchain + cargo install tauri-cli

Install Dependencies

bun install

Development

# Launch Vite + Tauri together
bun run tauri:dev

# Browser-only preview (optional)
bun run dev

The UI defaults to the repository copy of codex-setup.sh. Update the path field in the app if you relocate it.

Build Desktop Packages

# Compile production assets
bun run build

# Produce Linux bundles (AppImage, deb, rpm) and the raw binary
bun run tauri:build

# Produce only the raw Linux executable (no AppImage/deb/rpm)
bun run tauri build --bundles none

Executables live under src-tauri/target/release/.


🌐 Network & Ports

  • Nginx: Port 80 (host)
  • Code-server: Ports 8081-81XX (inside container, using --network host)
  • Tailscale: HTTPS via funnel

πŸ“– Additional Resources

Main Script:

  • codex-setup.sh - Multi-mode: Full (1), Cleanup (2), or Local (3)

Usage:

sudo ./codex-setup.sh
# Option 1: Full Setup (Tailscale)
# Option 2: Local Network Mode (LAN only)
# Option 3: Uninstall (Delete everything)

All configuration via interactive prompts or environment variables (CODEX_NUM_USERS, CODEX_DOMAIN).


πŸ“œ License

MIT License - Copyright (c) 2025 Buffer Ring Organization

See LICENSE for details.

πŸ‘₯ Credits

Developed by BufferRing
Website: bufferring.org

Community Project: This is an open-source educational tool made freely available to students and teachers. It is not officially endorsed by or affiliated with any institution or government entity.

About

Production-ready system for running multiple isolated code-server workspaces.

Resources

License

Stars

Watchers

Forks

Packages

No packages published