This is the multi-page printable view of this section. Click here to print.

Return to the regular view of this page.

Module: VIBE

Deploy an AI coding sandbox with Pigsty: Code-Server, JupyterLab, Node.js, and Claude Code.

The VIBE module provides a browser-based dev environment with Code-Server, JupyterLab, Node.js, and Claude Code, and can work with JUICE shared storage and PGSQL database capabilities.

VIBE depends on NODE and INFRA:

  • NODE provides base software and Python uv environment
  • INFRA provides Nginx reverse proxy, Grafana and portal entry

Components

ComponentDescriptionLocal PortAccess Path
Code-ServerVS Code in browser8443/code/
JupyterLabInteractive notebooks8888/jupyter/
Node.jsRuntime and npm-CLI
Claude CodeCLI + observability config-CLI / Grafana

Notes:

  • Code-Server listens on 127.0.0.1:8443, exposed via Nginx
  • JupyterLab listens on 0.0.0.0:8888, base path /jupyter/
  • Module default is jupyter_enabled: false, while conf/vibe.yml template explicitly enables Jupyter

Quick Start

./configure -c vibe
./deploy.yml        # NODE + INFRA + PGSQL
./juice.yml         # optional shared storage
./vibe.yml          # VIBE

Default entry points (via infra_portal.home):

  • Code-Server: https://<domain>/code/
  • JupyterLab: https://<domain>/jupyter/
  • Claude Dashboard: https://<domain>/ui/d/claude-code

Features

  • Unified workspace: vibe_data as root for Code-Server and Jupyter
  • Optional shared storage: work with JUICE for multi-node sharing
  • Observability: Claude Code OpenTelemetry integrates with VictoriaMetrics/VictoriaLogs
  • Composable: enable Code/Jupyter/Node.js/Claude as needed

Documentation

1 - Configuration

VIBE module configuration for Code-Server, JupyterLab, Node.js, and Claude Code.

VIBE supports enabling components on demand and exposes services via a unified workspace and Nginx portal.


Overview

ComponentEnable ParamDefaultDescription
Code-Servercode_enabledEnabledVS Code in browser
JupyterLabjupyter_enabledDisabledNotebook / terminal / editor
Node.jsnodejs_enabledEnabledNode.js runtime and npm
Claude Codeclaude_enabledEnabledCLI config and observability

Note: module default is jupyter_enabled: false, while conf/vibe.yml explicitly sets it to true.

Config usually lives in cluster vars, and can be overridden at instance level:

all:
  children:
    infra:
      hosts:
        10.10.10.10:
          vibe_data: /fs
          code_enabled: true
          jupyter_enabled: true
          claude_enabled: true

Workspace

vibe_data is the unified workspace for VIBE:

  • Code-Server default open directory
  • JupyterLab root_dir
  • Claude Code working dir
  • CLAUDE.md / AGENTS.md context files

The vibe_dir task creates the directory and context files, owned by node_user.

vibe_data: /fs

Code-Server

code_enabled: true
code_port: 8443
code_data: /data/code
code_password: Vibe.Coding
code_gallery: openvsx

Notes:

  • Service listens on 127.0.0.1:<code_port> (default 8443), accessed via Nginx /code/
  • Config file: code_data/code-server/config.yaml (default /data/code/code-server/config.yaml)
  • Env file: /etc/default/code, used to configure extension marketplace

Extension marketplace:

  • code_gallery: microsoft uses Microsoft marketplace
  • When region=china, Open VSX defaults to Tsinghua mirror

JupyterLab

jupyter_enabled: true
jupyter_port: 8888
jupyter_data: /data/jupyter
jupyter_password: Vibe.Coding
jupyter_venv: /data/venv

Notes:

  • Service listens on 0.0.0.0:<jupyter_port> (default 8888), base path /jupyter/
  • Config file: jupyter_data/jupyter_config.py (default /data/jupyter/jupyter_config.py)
  • Login token: c.IdentityProvider.token
  • Venv is not created automatically, use node_uv_env in NODE module beforehand

Create venv example:

uv venv /data/venv

Node.js

nodejs_enabled: true
nodejs_registry: ''
npm_packages:
  - '@anthropic-ai/claude-code'
  - happy-coder

Notes:

  • When nodejs_registry is empty and region=china, default registry is https://registry.npmmirror.com
  • npm_packages are installed via npm install -g and available globally
  • @anthropic-ai/claude-code is installed by default, so manual Claude CLI install is usually unnecessary

Claude Code

claude task only writes configuration (claude_config). By default, Claude CLI is installed by the nodejs task through npm_packages (including @anthropic-ai/claude-code).

claude_enabled: true
claude_env:
  ANTHROPIC_API_KEY: sk-ant-xxx

If nodejs_enabled is disabled or npm_packages is emptied, install Claude CLI manually.

Generated files:

  • ~/.claude.json
  • ~/.claude/settings.json

claude_env is merged with default OpenTelemetry env vars, sending telemetry to VictoriaMetrics / VictoriaLogs.


Nginx Portal

VIBE exposes services through infra_portal. By default, home domain includes /code/ and /jupyter/ paths.

For dedicated domains:

infra_portal:
  code: { domain: code.pigsty, endpoint: "127.0.0.1:8443", websocket: true }
  jupyter: { domain: jupyter.pigsty, endpoint: "127.0.0.1:8888", websocket: true }

2 - Parameters

VIBE module parameters (16 total).

VIBE module has 16 parameters, grouped as:

  • Common
  • Code-Server
  • JupyterLab
  • Node.js
  • Claude Code

Overview

ParameterTypeLevelDefaultDescription
vibe_datapathC/fsWorkspace dir
code_enabledboolCtrueEnable Code-Server
code_portportC8443Code-Server port
code_datapathC/data/codeCode-Server data dir
code_passwordstringCVibe.CodingCode-Server password
code_galleryenumCopenvsxExtension marketplace
jupyter_enabledboolCfalseEnable JupyterLab
jupyter_portportC8888JupyterLab port
jupyter_datapathC/data/jupyterJupyterLab data dir
jupyter_passwordstringCVibe.CodingJupyterLab token
jupyter_venvpathC/data/venvPython venv path
nodejs_enabledboolCtrueEnable Node.js
nodejs_registryurlC''npm registry mirror
npm_packagesstring[]C['@anthropic-ai/claude-code','happy-coder']Global npm packages
claude_enabledboolCtrueEnable Claude config
claude_envdictC{}Claude env vars

Default Parameters

Defined in roles/vibe/defaults/main.yml:

vibe_data: /fs

code_enabled: true
code_port: 8443
code_data: /data/code
code_password: Vibe.Coding
code_gallery: 'openvsx'

jupyter_enabled: false
jupyter_port: 8888
jupyter_data: /data/jupyter
jupyter_password: Vibe.Coding
jupyter_venv: /data/venv

nodejs_enabled: true
nodejs_registry: ''
npm_packages: [ '@anthropic-ai/claude-code' , 'happy-coder' ]

claude_enabled: true
claude_env: {}

Common

vibe_data

Workspace dir: default root for Code-Server and JupyterLab, and location for CLAUDE.md / AGENTS.md.


Code-Server

code_enabled

Enable Code-Server.

code_port

Listen port, bound to 127.0.0.1, forwarded by Nginx /code/.

code_data

Data dir, config file at code_data/code-server/config.yaml (default /data/code/code-server/config.yaml).

code_password

Login password, must be changed in production.

Extension marketplace: openvsx / microsoft. When region=china and openvsx, Tsinghua mirror is used.


JupyterLab

jupyter_enabled

Enable JupyterLab. Module default is false; conf/vibe.yml explicitly sets it to true to enable a full sandbox.

jupyter_port

Listen port, default 0.0.0.0:8888.

jupyter_data

Data dir, config file at jupyter_data/jupyter_config.py (default /data/jupyter/jupyter_config.py).

jupyter_password

Access token written to c.IdentityProvider.token.

jupyter_venv

Python venv path for JupyterLab, must be created beforehand (usually by NODE module).


Node.js

nodejs_enabled

Enable Node.js.

nodejs_registry

npm registry mirror; when empty and region=china, defaults to https://registry.npmmirror.com.

npm_packages

Global npm packages, tagged nodejs_pkg. Defaults include @anthropic-ai/claude-code and happy-coder.


Claude Code

claude_enabled

Enable Claude Code config task (claude_config). Claude CLI is installed by nodejs_pkg based on npm_packages by default.

claude_env

Extra env vars merged into default OpenTelemetry config.

Default env vars include:

  • CLAUDE_CODE_ENABLE_TELEMETRY=1
  • CLAUDE_CODE_EXPERIMENTAL_AGENT_TEAMS=1
  • OTEL_METRICS_EXPORTER=otlp
  • OTEL_LOGS_EXPORTER=otlp
  • OTEL_EXPORTER_OTLP_METRICS_ENDPOINT=http://127.0.0.1:8428/opentelemetry/v1/metrics
  • OTEL_EXPORTER_OTLP_LOGS_ENDPOINT=http://127.0.0.1:9428/insert/opentelemetry/v1/logs

3 - Playbook

VIBE module Ansible playbook guide.

VIBE module provides vibe.yml playbook to deploy Code-Server, JupyterLab, Node.js and Claude Code config.

vibe.yml includes only node_id and vibe roles, it does not include node/infra. Run deploy.yml first, or explicitly run node.yml and infra.yml.


vibe.yml

vibe.yml:

- name: VIBE
  hosts: all
  become: true
  gather_facts: no
  roles:
    - { role: node_id, tags: id }
    - { role: vibe,    tags: vibe }

Task Structure

vibe
├── vibe_dir          # create workspace and context files
├── code              # Code-Server
│   ├── code_install
│   ├── code_dir
│   ├── code_config
│   └── code_launch
├── jupyter           # JupyterLab
│   ├── jupyter_install
│   ├── jupyter_dir
│   ├── jupyter_config
│   └── jupyter_launch
├── nodejs            # Node.js runtime
│   ├── nodejs_install
│   ├── nodejs_config
│   └── nodejs_pkg
└── claude            # Claude Code config
    └── claude_config

Notes:

  • jupyter_install uses uv pip, it does not create venv
  • claude_config only writes ~/.claude config
  • Claude CLI is installed by nodejs_pkg via npm_packages (includes @anthropic-ai/claude-code by default)

Common Commands

Full deploy:

./vibe.yml -l <host>

Component-level:

./vibe.yml -l <host> -t code
./vibe.yml -l <host> -t jupyter
./vibe.yml -l <host> -t nodejs
./vibe.yml -l <host> -t claude

Config updates:

./vibe.yml -l <host> -t code_config,code_launch
./vibe.yml -l <host> -t jupyter_config,jupyter_launch
./vibe.yml -l <host> -t claude_config

Disable components:

./vibe.yml -l <host> -e code_enabled=false
./vibe.yml -l <host> -e jupyter_enabled=false
./vibe.yml -l <host> -e nodejs_enabled=false
./vibe.yml -l <host> -e claude_enabled=false

Deployment Order

./deploy.yml      # NODE + INFRA + PGSQL
./juice.yml       # optional shared storage
./vibe.yml        # VIBE

Idempotency

vibe.yml is idempotent. Re-run after config changes.

4 - Administration

VIBE module operations and common admin tasks.

Service Management

systemctl status code-server
systemctl restart code-server
systemctl status jupyter
systemctl restart jupyter

Logs:

journalctl -u code-server -f
journalctl -u jupyter -f

Workspace and Context

vibe_dir creates these under vibe_data:

  • CLAUDE.md
  • AGENTS.md (symlink to CLAUDE.md)

Default locations (adjustable via vibe_data):

/fs/CLAUDE.md
/fs/AGENTS.md

Password and Auth

Code-Server

Edit config:

vi /data/code/code-server/config.yaml
systemctl restart code-server

Or via Ansible:

./vibe.yml -l <host> -e code_password='NewPassword' -t code_config,code_launch

JupyterLab

Config file: /data/jupyter/jupyter_config.py

Field: c.IdentityProvider.token

vi /data/jupyter/jupyter_config.py
systemctl restart jupyter

Code-Server Extensions

code-server --install-extension ms-python.python
code-server --list-extensions
code-server --uninstall-extension ms-python.python

Switch extension marketplace:

code_gallery: microsoft

Redeploy:

./vibe.yml -l <host> -t code_config,code_launch

JupyterLab Environment

VIBE does not create venv automatically, ensure jupyter_venv exists:

uv venv /data/venv

Install/upgrade JupyterLab:

uv pip install --python /data/venv/bin/python jupyterlab ipykernel
systemctl restart jupyter

Install extensions (in venv):

source /data/venv/bin/activate
pip install jupyterlab-git
systemctl restart jupyter

Claude Code

The claude_config subtask only writes config files. Claude CLI is installed globally by nodejs_pkg through npm_packages (which includes @anthropic-ai/claude-code by default).

which claude
claude --version

Config files:

  • ~/.claude.json
  • ~/.claude/settings.json

Update config:

./vibe.yml -l <host> -t claude_config

Reinstall/install Claude CLI:

./vibe.yml -l <host> -t nodejs_pkg
# or install manually
npm install -g @anthropic-ai/claude-code

To configure for another user, run as that user or copy the files manually.


File Locations

ComponentKey Files
Code-Server/data/code/code-server/config.yaml
Code-Server/etc/default/code
Code-Server/etc/systemd/system/code-server.service
JupyterLab/data/jupyter/jupyter_config.py
JupyterLab/etc/default/jupyter
JupyterLab/etc/systemd/system/jupyter.service
Claude Code~/.claude.json / ~/.claude/settings.json

Troubleshooting

Port checks:

ss -tlnp | grep 8443
ss -tlnp | grep 8888

Nginx entry:

nginx -t
systemctl status nginx

5 - Monitoring

VIBE monitoring, focusing on Claude Code observability.

VIBE monitoring mainly focuses on Claude Code OpenTelemetry data. Code-Server and JupyterLab do not expose Prometheus metrics; use systemd and logs for health checks.


Claude Code Observability

VIBE writes default OpenTelemetry env vars into ~/.claude/settings.json:

{
  "env": {
    "CLAUDE_CODE_ENABLE_TELEMETRY": 1,
    "CLAUDE_CODE_EXPERIMENTAL_AGENT_TEAMS": 1,
    "OTEL_LOG_USER_PROMPTS": 1,
    "OTEL_METRICS_EXPORTER": "otlp",
    "OTEL_LOGS_EXPORTER": "otlp",
    "OTEL_EXPORTER_OTLP_PROTOCOL": "http/protobuf",
    "OTEL_EXPORTER_OTLP_METRICS_ENDPOINT": "http://127.0.0.1:8428/opentelemetry/v1/metrics",
    "OTEL_EXPORTER_OTLP_LOGS_ENDPOINT": "http://127.0.0.1:9428/insert/opentelemetry/v1/logs",
    "OTEL_RESOURCE_ATTRIBUTES": "ip=<host>,job=claude"
  }
}

claude_env is merged with the defaults, and can be used for API keys or custom endpoints.


Grafana Dashboard

Grafana includes claude-code dashboard by default:

  • Portal: https://<domain>/ui/d/claude-code
  • Direct: http://<ip>:3000/d/claude-code

Runtime Checks

systemctl status code-server
systemctl status jupyter
journalctl -u code-server -f
journalctl -u jupyter -f

Port checks:

ss -tlnp | grep 8443
ss -tlnp | grep 8888

Claude Logs Query

Via VictoriaLogs:

curl -G 'http://127.0.0.1:9428/select/logsql/query' \
  --data-urlencode 'query=job:claude'

6 - FAQ

VIBE module frequently asked questions.

Deployment

code-server package not found

Ensure NODE and repo config are in place:

yum repolist    # EL
apt update      # Debian/Ubuntu
./infra.yml -t repo

JupyterLab installation failed

jupyter_venv must exist:

uv venv /data/venv
./vibe.yml -l <host> -t jupyter

Access

Cannot access /code/ or /jupyter/

  1. Check service status
  2. Check port listening
  3. Check Nginx config
systemctl status code-server
systemctl status jupyter
ss -tlnp | grep 8443
ss -tlnp | grep 8888
nginx -t

WebSocket connection fails

Ensure Nginx enables WebSocket (default is enabled). If using custom infra_portal, set websocket: true.


Password and Token

Change Code-Server password

./vibe.yml -l <host> -e code_password='NewPass' -t code_config,code_launch

Change JupyterLab token

./vibe.yml -l <host> -e jupyter_password='NewToken' -t jupyter_config,jupyter_launch

Claude Code

CLI not found

First check whether nodejs_pkg completed (@anthropic-ai/claude-code is installed by default):

which claude
npm list -g --depth=0 | grep '@anthropic-ai/claude-code'
./vibe.yml -l <host> -t nodejs_pkg

If nodejs_enabled is disabled or npm_packages is overridden, install manually:

npm install -g @anthropic-ai/claude-code

API key not set

export ANTHROPIC_API_KEY=sk-ant-xxx
# or set in claude_env

Telemetry not showing

Check local VictoriaMetrics/VictoriaLogs:

curl http://127.0.0.1:8428/api/v1/status/buildinfo
curl http://127.0.0.1:9428/select/logsql/stats_query

Ensure OTEL endpoints in ~/.claude/settings.json are correct.


Extensions and Plugins

Code-Server extension install fails

  • Check network
  • Try switching code_gallery
  • Or install VSIX manually
code-server --install-extension /path/to/extension.vsix

JupyterLab extension install fails

source /data/venv/bin/activate
pip install jupyterlab-git
systemctl restart jupyter