# Honcho Self-Hosting on ZimaOS — Complete Recipe

## Overview

This reference captures the full Honcho self-hosting saga on ZimaOS (ZimaCube). The built-in memory system works fine, but if you want Honcho as memory backend for Hermes, this documents every pitfall encountered.

## Prerequisites

- ZimaOS (read-only root FS, older Docker buildx)
- Docker available but Compose may need manual installation
- Honcho repo: https://github.com/plastic-labs/honcho

## Step-by-Step (Tested on ZimaOS v1.6.1)

### 1. Clone & Prepare Config

```bash
git clone https://github.com/plastic-labs/honcho.git /DATA/AppData/hermes/projects/honcho
cd /DATA/AppData/hermes/projects/honcho
cp docker-compose.yml.example docker-compose.yml
cp .env.template .env
```

### 2. Edit `.env` — Minimal Required for Ollama Cloud Pro

```
LLM_OPENAI_API_KEY=<your-key>
LLM_BASE_URL=https://ollama.com/v1

# Per-module overrides (global LLM_BASE_URL may not propagate)
DERIVER_MODEL_CONFIG__MODEL=kimi-k2.6
DERIVER_MODEL_CONFIG__OVERRIDES__BASE_URL=https://ollama.com/v1

DIALECTIC_LEVELS__minimal__MODEL_CONFIG__MODEL=kimi-k2.6
DIALECTIC_LEVELS__minimal__MODEL_CONFIG__OVERRIDES__BASE_URL=https://ollama.com/v1
# ... repeat for low, medium, high, max levels

SUMMARY_MODEL_CONFIG__MODEL=kimi-k2.6
SUMMARY_MODEL_CONFIG__OVERRIDES__BASE_URL=https://ollama.com/v1

DREAM_DEDUCTION_MODEL_CONFIG__MODEL=kimi-k2.6
DREAM_DEDUCTION_MODEL_CONFIG__OVERRIDES__BASE_URL=https://ollama.com/v1
DREAM_INDUCTION_MODEL_CONFIG__MODEL=kimi-k2.6
DREAM_INDUCTION_MODEL_CONFIG__OVERRIDES__BASE_URL=https://ollama.com/v1

# Embeddings: defaults to text-embedding-3-small via OpenAI transport.
# If your proxy doesn't support embeddings, Honcho's deriver will fail.
EMBEDDING_MODEL_CONFIG__MODEL=text-embedding-3-small

# Cache
CACHE_ENABLED=true

# Auth
AUTH_USE_AUTH=false
```

### 3. Docker Permissions

```bash
# Add user to docker group (won't take effect until relogin)
sudo usermod -aG docker $USER

# Workaround for same session: use sg + custom DOCKER_CONFIG
export DOCKER_CONFIG=/tmp/docker-config
mkdir -p /tmp/docker-config
sg docker -c "DOCKER_CONFIG=$DOCKER_CONFIG docker ps"
```

### 4. Build the Image

Docker Compose v5 requires buildx ≥ 0.17 — ZimaOS ships older. Use `docker build` directly:

```bash
sg docker -c "DOCKER_CONFIG=/tmp/docker-config docker build -t honcho-api -f Dockerfile ."
```

The same image is used for both `api` and `deriver` containers (different entrypoints).

### 5. Pull Supporting Images

```bash
sg docker -c "DOCKER_CONFIG=/tmp/docker-config docker pull pgvector/pgvector:pg15"
sg docker -c "DOCKER_CONFIG=/tmp/docker-config docker pull redis:8.2"
```

### 6. Create Network

```bash
sg docker -c "DOCKER_CONFIG=/tmp/docker-config docker network create honcho-net"
```

### 7. Start Containers (Manual, no Compose)

```bash
# Postgres
sg docker -c "DOCKER_CONFIG=/tmp/docker-config docker run -d --name honcho-db \
  --network honcho-net \
  -e POSTGRES_DB=postgres -e POSTGRES_USER=postgres -e POSTGRES_PASSWORD=postgres \
  -e POSTGRES_HOST_AUTH_METHOD=trust \
  -v honcho-pgdata:/var/lib/postgresql/data \
  -v $(pwd)/database/init.sql:/docker-entrypoint-initdb.d/init.sql \
  pgvector/pgvector:pg15"

# Redis
sg docker -c "DOCKER_CONFIG=/tmp/docker-config docker run -d --name honcho-redis \
  --network honcho-net \
  -v honcho-redis-data:/data \
  redis:8.2"

# API
sg docker -c "DOCKER_CONFIG=/tmp/docker-config docker run -d --name honcho-api \
  --network honcho-net \
  -p 127.0.0.1:8000:8000 \
  -e DB_CONNECTION_URI=postgresql+psycopg://postgres:postgres@honcho-db:5432/postgres \
  -e CACHE_URL=redis://honcho-redis:6379/0?suppress=true \
  -e CACHE_ENABLED=true \
  --env-file .env \
  honcho-api sh docker/entrypoint.sh"

# Deriver
sg docker -c "DOCKER_CONFIG=/tmp/docker-config docker run -d --name honcho-deriver \
  --network honcho-net \
  -e DB_CONNECTION_URI=postgresql+psycopg://postgres:postgres@honcho-db:5432/postgres \
  -e CACHE_URL=redis://honcho-redis:6379/0?suppress=true \
  -e CACHE_ENABLED=true \
  --env-file .env \
  honcho-api python -m src.deriver"
```

### 8. Verify

```bash
curl http://localhost:8000/health
# Expected: {"status": "healthy"}

docker logs honcho-api
docker logs honcho-deriver
```

## Errors Encountered & Fixes

| Error | Cause | Fix |
|-------|-------|-----|
| `permission denied while trying to connect to docker API` | User not in docker group | `usermod -aG docker` + `sg docker` |
| `mkdir /root/.docker: read-only file system` | ZimaOS root FS is read-only | Set `DOCKER_CONFIG=/tmp/docker-config` |
| `compose build requires buildx 0.17.0 or later` | Docker Compose v5 too new for ZimaOS buildx | Use `docker build` directly |
| Group membership not active | `usermod` only applies on next login | `sg docker -c "..."` for immediate use |

## Hermes Integration

Once Honcho is running:

```bash
hermes config set memory.provider honcho
hermes config set honcho.base_url http://localhost:8000/v3
```

Then `/restart` the gateway or restart Hermes. Verify with `hermes memory status`.

---

## Alternative: Hybrid Native+Container Approach

If the Docker build still fails (even with all workarounds), use containers only for PostgreSQL+pgvector and Redis, then run Honcho API+Deriver natively with `uv`:

### Why this approach wins
- No Docker build needed — `uv sync` installs everything into a local `.venv`
- DB/Redis are the only truly hard-to-reproduce deps, and `docker run` works fine for them
- Native Python process is easier to debug

### 1. Start only the DB/Redis containers

```bash
# Start pgvector (port 5433 to avoid conflict with other Postgres instances)
sg docker -c "DOCKER_CONFIG=/tmp/docker-config docker run -d --name honcho-db \
  -p 127.0.0.1:5433:5432 \
  -e POSTGRES_DB=postgres -e POSTGRES_USER=postgres -e POSTGRES_PASSWORD=postgres \
  -e POSTGRES_HOST_AUTH_METHOD=trust \
  -v honcho-pgdata:/var/lib/postgresql/data \
  --restart unless-stopped \
  pgvector/pgvector:pg15 postgres -c max_connections=200"

# Start Redis (port 6380 to avoid conflicts)
sg docker -c "DOCKER_CONFIG=/tmp/docker-config docker run -d --name honcho-redis \
  -p 127.0.0.1:6380:6379 \
  -v honcho-redis-data:/data \
  --restart unless-stopped \
  redis:8.2"

# Verify
sg docker -c "DOCKER_CONFIG=/tmp/docker-config docker exec honcho-db pg_isready -U postgres"
sg docker -c "DOCKER_CONFIG=/tmp/docker-config docker exec honcho-redis redis-cli ping"

# Enable pgvector extension
sg docker -c "DOCKER_CONFIG=/tmp/docker-config docker exec honcho-db psql -U postgres -c 'CREATE EXTENSION IF NOT EXISTS vector;'"
```

### 2. Set up native Python environment

```bash
# Install uv if needed
python3 -m pip install uv

# Sync Honcho dependencies (creates .venv)
cd /path/to/honcho
uv sync
```

### 3. Point .env at the containers (NOT at docker network hostnames)

```
DB_CONNECTION_URI=postgresql+psycopg://postgres:postgres@localhost:5433/postgres
CACHE_URL=redis://localhost:6380/0?suppress=true
CACHE_ENABLED=true
```

### 4. Start Honcho natively

```bash
# API server (terminal 1)
cd /path/to/honcho && uv run fastapi dev src/main.py --host 0.0.0.0 --port 8000

# Deriver worker (terminal 2)
cd /path/to/honcho && uv run python -m src.deriver
```

### 5. Verify

```bash
curl http://localhost:8000/health
```

### 6. systemd Services (survive reboots)

**⚠️ ZimaOS overlay FS caveat:** The `write_file` tool writes to the overlay upper dir but `systemctl enable` only sees `/etc/systemd/system/`. Use `sudo tee` to write service files:

```bash
sudo tee /etc/systemd/system/honcho-api.service > /dev/null << 'EOF'
[Unit]
Description=Honcho API Server
After=network.target docker.service
Wants=docker.service

[Service]
Type=simple
User=az-a
WorkingDirectory=/DATA/AppData/hermes/projects/honcho
Environment=PATH=/DATA/.local/bin:/usr/local/bin:/usr/bin:/bin
Environment=DB_CONNECTION_URI=postgresql+psycopg://postgres:postgres@localhost:5433/postgres
Environment=CACHE_URL=redis://localhost:6380/0?suppress=true
Environment=CACHE_ENABLED=true
EnvironmentFile=/DATA/AppData/hermes/projects/honcho/.env
ExecStart=/DATA/.local/bin/uv run fastapi run --host 0.0.0.0 --port 8000 src/main.py
Restart=on-failure
RestartSec=5

[Install]
WantedBy=multi-user.target
EOF

sudo tee /etc/systemd/system/honcho-deriver.service > /dev/null << 'EOF'
[Unit]
Description=Honcho Deriver (Background Memory Worker)
After=honcho-api.service
Wants=honcho-api.service

[Service]
Type=simple
User=az-a
WorkingDirectory=/DATA/AppData/hermes/projects/honcho
Environment=PATH=/DATA/.local/bin:/usr/local/bin:/usr/bin:/bin
Environment=DB_CONNECTION_URI=postgresql+psycopg://postgres:postgres@localhost:5433/postgres
Environment=CACHE_URL=redis://localhost:6380/0?suppress=true
Environment=CACHE_ENABLED=true
EnvironmentFile=/DATA/AppData/hermes/projects/honcho/.env
ExecStart=/DATA/.local/bin/uv run python -m src.deriver
Restart=on-failure
RestartSec=5

[Install]
WantedBy=multi-user.target
EOF

sudo systemctl daemon-reload
sudo systemctl enable honcho-api.service honcho-deriver.service
sudo systemctl start honcho-api.service honcho-deriver.service
```

**Key paths:** `uv` lives at `/DATA/.local/bin/uv`. Honcho `.venv` is created by `uv sync` at `honcho/.venv/`.

**Gateway restart note:** After enabling Honcho, restart Hermes gateway with `sudo systemctl restart hermes-gateway.service`. The gateway may stay in `deactivating (stop-sigterm)` for up to 180 seconds (drain timeout) before restarting.
