Happy Coder is no longer used. Node.js was only installed as a
dependency for `npm install -g happy-coder`, so both are removed.
This shrinks the Docker image and simplifies the configuration.
Removed from: Dockerfile, Helm values/schema/templates, serverless
manifests, Makefile, and all documentation.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Install GitHub CLI (gh) via official APT repo and kubeseal via GitHub
Releases binary in the Dockerfile. Add mcp-helm sidecar on port 8088
for AI-assisted Helm chart browsing, with corresponding values, schema,
deployment template, and .mcp.json configuration.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Symlink left the original in ~/.local/bin which triggered a PATH
warning at runtime. Copy the binary and remove the original.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
The npm-installed Claude Code runs via Node.js, which causes remote
control to fail with '/usr/bin/node: bad option: --sdk-url'. The native
binary handles subprocess spawning correctly.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
npm was serving a cached older version even with Docker no-cache.
Clear npm cache and use --prefer-online to force a fresh registry fetch.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
GHA cache was serving stale npm install layers despite cache-bust ARG.
Remove all caching — every build is now fully clean.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Two fixes:
- Move Claude Code npm install below TOOLS_CACHEBUST ARG so it actually
gets refreshed when the cache-bust value changes
- Make GITHUB_REPO env conditional so an empty Helm value no longer
overrides the value provided via the Kubernetes secret (envFrom)
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
The direct GCS binary download approach has been unreliable across
multiple attempts. Revert to the proven npm install method. Node.js
is already required for Happy Coder so there is no extra dependency.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
npm install fails in CI due to native dependency compilation issues.
Download the pre-built binary directly from the official GCS distribution
bucket with SHA256 checksum verification. This approach worked previously
(run #135) and avoids npm entirely — Node.js is only needed for Happy Coder.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
The native binary installer (both direct GCS download and claude.ai/install.sh)
has been unreliable during Docker builds. Revert to the proven npm approach.
Node.js is already required for Happy Coder, so there's no extra dependency.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
The previous native installer approach used a direct GCS bucket download
that was fragile and failing during builds. Switch to the official
install script (claude.ai/install.sh) which handles version discovery,
platform detection, and checksum verification properly.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
The legacy GPG key import and .list format was failing with exit code 100
in CI. Switch to the DEB822 .sources format and install -D key method
per Microsoft's current documentation.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
The native Claude Code installer (and other tools) fetch "latest" at
build time, but Docker layer caching serves stale layers because the
RUN command text never changes. Add TOOLS_CACHEBUST build arg with
github.run_id so every CI run re-downloads fresh tool binaries.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Replace npm-based Claude Code installation with the native binary
installer. Downloads directly from Anthropic's distribution bucket to
/usr/local/bin/claude — no Node.js dependency for Claude Code anymore.
Node.js is retained for Happy Coder only.
Generated with [Claude Code](https://claude.ai/code)
via [Happy](https://happy.engineering)
Co-Authored-By: Claude <noreply@anthropic.com>
Co-Authored-By: Happy <yesreply@happy.engineering>
Implements a complete serverless development container platform:
## Architecture
- Authentik forward auth for authentication/authorization
- NGINX routing proxy extracts GitHub repo from URL path
- Knative Service auto-scales dev container instances from 0
- Dynamic GitHub repo routing via /github/{owner}/{repo}
## Components
- routing-proxy: NGINX-based service for repo extraction and forwarding
- deployment.yaml: Complete K8s manifests (proxy, Knative, ingress, secrets)
- authentik-config.yaml: Authentik application and provider configs
- serverless scripts: Dynamic repo initialization and startup handling
- Comprehensive documentation and Makefile for ops
## Key Features
- Scale to zero when not in use (cost-effective)
- Per-request isolation (each repo gets own container)
- Built-in file manager for upload/download
- Support for private repos via GitHub tokens
- User attribution via Authentik headers
- WebSocket support for VNC connections
Example usage: https://devcontainer.farh.net/github/microsoft/vscode
Generated with [Claude Code](https://claude.ai/code)
via [Happy](https://happy.engineering)
Co-Authored-By: Claude <noreply@anthropic.com>
Co-Authored-By: Happy <yesreply@happy.engineering>
- Install Helm v3.17.1 in Dockerfile for chart development (closes#49)
- Add fileManager toggle using base image's WEB_FILE_MANAGER (closes#11)
- Wire WEB_FILE_MANAGER env vars in deployment template
- Update CLAUDE.md, README.md with new features and values
Generated with [Claude Code](https://claude.ai/code)
via [Happy](https://happy.engineering)
Co-Authored-By: Claude <noreply@anthropic.com>
Co-Authored-By: Happy <yesreply@happy.engineering>
Fixed the Crush AI assistant installation in Dockerfile by replacing the
single-line tar extraction with --strip-components (which was failing)
with a multi-step approach: download to temp, extract, move binary,
and cleanup. This ensures the binary is properly extracted from the
versioned directory structure in the tarball.
Generated with [Claude Code](https://claude.ai/code)
via [Happy](https://happy.engineering)
Co-Authored-By: Claude <noreply@anthropic.com>
Co-Authored-By: Happy <yesreply@happy.engineering>
- Force fresh APT repository data by clearing package cache before update
- Add debugging output to show available and installed versions
- Use --no-install-recommends to avoid unnecessary packages
- Add version validation during build process
- Disable auto-updates in Antigravity settings to prevent container conflicts
This should resolve the "agentSessions service not found" error that prevents
the AI chat window from responding.
Generated with [Claude Code](https://claude.ai/code)
via [Happy](https://happy.engineering)
Co-Authored-By: Claude <noreply@anthropic.com>
Co-Authored-By: Happy <yesreply@happy.engineering>
Install both terminal-based AI coding agents alongside Happy Coder:
- OpenCode (opencode-ai/opencode) - open-source AI coding agent
- Crush (charmbracelet/crush) - OpenCode's active successor by Charm
Both are installed as Go binaries to /usr/local/bin from latest GitHub
releases and available to users via `opencode` and `crush` commands.
Generated with [Claude Code](https://claude.ai/code)
via [Happy](https://happy.engineering)
Co-Authored-By: Claude <noreply@anthropic.com>
Co-Authored-By: Happy <yesreply@happy.engineering>
The jlesage/baseimage-gui sets XDG_CONFIG_HOME=/config/xdg/config at
runtime, so Chrome was writing its profile to /config/xdg/config/google-chrome
which lived on ephemeral storage. This caused Chrome to open as a fresh
install on every pod restart.
Changes:
- Mount the PVC at /config instead of /home (aligns with baseimage-gui convention)
- Move user home directory to /config/userdata (on the PVC)
- Add explicit --user-data-dir for Chrome pointing to PVC path
- Clean up Chrome crash lock files and patch Preferences on startup
to prevent session/cookie loss after unclean pod shutdown
- Update all scripts (sshd, init-repo, cont-init) to use new paths
- Remove unnecessary cont-init-home.sh
Generated with [Claude Code](https://claude.ai/code)
via [Happy](https://happy.engineering)
Co-Authored-By: Claude <noreply@anthropic.com>
Co-Authored-By: Happy <yesreply@happy.engineering>
- Add explicit --user-data-dir flag to Chrome wrapper to ensure profile data
is stored in the persistent home directory
- Add cont-init-home.sh script to properly initialize home directory structure
on container startup with correct permissions
- Ensure Chrome config directory exists before Chrome starts
- Bump chart version to 0.1.13
This fixes the issue where Chrome loses authentication and settings after
pod restarts by explicitly managing where Chrome stores its profile data.
Generated with [Claude Code](https://claude.ai/code)
via [Happy](https://happy.engineering)
Co-Authored-By: Claude <noreply@anthropic.com>
Co-Authored-By: Happy <yesreply@happy.engineering>
- Add `ide` Helm value with options: vscode, antigravity, ssh
- Dockerfile: install Google Antigravity via apt and openssh-server
- scripts/startapp.sh: branch on IDE env var to launch the right app
- scripts/cont-init-sshd.sh: start sshd as root in SSH mode, set up
authorized_keys from SSH_AUTHORIZED_KEYS env var
- chart/templates/deployment.yaml: pass IDE env var, conditional ports
and probes (HTTP for VNC modes, TCP socket for SSH mode)
- chart/templates/service.yaml: expose port 5800 (VNC) or 22 (SSH)
- chart/values.yaml: add ide field with documentation
- README.md: document IDE choice, fix stale happyHomeDir references
- chart/Chart.yaml: bump to 0.1.5
Closes#10
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Chrome requires --no-sandbox and --disable-dev-shm-usage when running
inside a Docker container, otherwise it crashes silently and the OAuth
popup never completes.
- Add a /usr/local/bin/google-chrome wrapper that injects these flags
- Install xdg-utils so xdg-open can resolve browser handlers in VNC
- Set BROWSER env var to the wrapper so Claude Code and xdg-open both
use it when opening the Claude Max login URL
The OAuth callback (to localhost) works fine inside VNC because both
the browser and the Claude Code local auth server share the same
container network namespace.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Happy Coder requires the `claude` CLI to be present but it was never
installed in the image. Add @anthropic-ai/claude-code to the npm
global install step alongside happy-coder.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
baseimage-gui creates the app user (UID 1000) at runtime with
shell=/sbin/nologin and home=/dev/null. VSCode tries to spawn the
user's login shell for terminals, which fails with exit code 1.
Adds a cont-init script that runs as root after baseimage-gui's
adduser step and corrects both the shell and home directory.
Generated with [Claude Code](https://claude.ai/code)
via [Happy](https://happy.engineering)
Co-Authored-By: Claude <noreply@anthropic.com>
Co-Authored-By: Happy <yesreply@happy.engineering>
Changed from incorrect `@happy-sdk/happy-coder` to correct `happy-coder`
package name. The scoped package doesn't exist on npm, causing Docker
build failures.
This fixes the v1.0.0 release Docker build.
Generated with [Claude Code](https://claude.ai/code)
via [Happy](https://happy.engineering)
Co-Authored-By: Claude <noreply@anthropic.com>
Co-Authored-By: Happy <yesreply@happy.engineering>
Add containerized GUI development environment featuring:
- Antigravity IDE (VSCode) accessible via web browser
- Happy Coder AI assistant integration
- Automatic GitHub repository cloning on startup
- Persistent user home directory (ReadWriteMany PVC)
- Secure non-root execution as user claude (UID 1000)
Components:
- Dockerfile based on jlesage/baseimage-gui
- Startup scripts for repo initialization and app launch
- Kubernetes manifests (StatefulSet, ConfigMap, Secrets)
- Makefile for build and deployment automation
- Comprehensive documentation
Features:
- Web-based VNC interface (port 5800)
- GitHub token authentication for private repos
- Happy Coder runs as background service in workspace
- CephFS storage for persistent home directory
- Configurable display resolution and security
Generated with [Claude Code](https://claude.ai/code)
via [Happy](https://happy.engineering)
Co-Authored-By: Claude <noreply@anthropic.com>
Co-Authored-By: Happy <yesreply@happy.engineering>