# OMOS bundled skills How the five skills bundled with [oh-my-opencode-slim](https://github.com/alvinunreal/oh-my-opencode-slim) (OMOS) are deployed in this image, why the mechanism changed, and how to keep them up to date. ## TL;DR - OMOS bundles five skills: `clonedeps`, `codemap`, `deepwork`, `oh-my-opencode-slim`, `simplify`. - They are **symlinked from the image** into `~/.agents/skills/` on every container start by `entrypoint-user.sh` (gated by `OMOS_SKILLS`, default `true`). - **To update them, pull a newer image and recreate the container** — no installer run, no config reset: ```bash docker compose pull docker compose up -d --force-recreate ``` ## Why it works this way The skills ship inside the OMOS npm package, baked into the image at `/usr/lib/node_modules/oh-my-opencode-slim/src/skills//`. On start the entrypoint creates one absolute symlink per skill into `~/.agents/skills/` — the same flat directory the [skillset](#relationship-to-skillset) deploy uses and which opencode scans (directly and via the `~/.claude/skills` pointer). Because the symlink target lives in the **image**, not in a volume, the skill content tracks whatever image you run. Pull a newer `*-omos` image and the skills update on the next container start. `~/.agents/skills/` is itself an ephemeral container-layer directory rebuilt from scratch on every start, so the reconcile is idempotent and self-healing. The symlinks are **absolute** (unlike skillset's relative links): the target is always inside the container at a fixed `/usr` path, so there is no host/container path divergence to guard against. ## The old mechanism (and the trap it created) Previously the OMOS *installer* (`oh-my-opencode-slim install --skills=yes`) **copied** the skills into `~/.config/opencode/skills/` — but only on the very first container start, gated by the absence of `oh-my-opencode-slim.json`. That directory is the persistent `devbox-opencode-config` named volume. The consequence: once the config existed, the installer was skipped forever, so the copied skills **froze** at whatever the image shipped on first run. Pulling a newer image did nothing (the copies lived in the volume, not the image). The only refresh path was `OMOS_RESET=true`, which runs `install --reset` and **also overwrites your hand-tuned `opencode.jsonc`** (model choices, agent config). Updating skills meant clobbering unrelated config — a bad trade. The installer has no skills-only refresh flag (`--skills=yes|no` is all-or- nothing within a full install; `--reset` overwrites everything), so the fix was to stop using the installer for skills entirely. The two `install` invocations in `entrypoint-user.sh` now pass `--skills=no`; the installer manages only the agent config (`oh-my-opencode-slim.json`). ## One-time migration of frozen copies Existing volumes still contain the old frozen real directories under `~/.config/opencode/skills/`. Because opencode prefers a name found there over the same name in `~/.agents/skills/`, those stale copies would *shadow* the fresh image-sourced symlinks. On the first start after upgrading, the entrypoint **backs each of them up — never deletes** — to `~/.config/opencode/skills/.bak.` and writes a marker at `~/.config/opencode/.omos-skills-migrated` so the migration runs exactly once. Only real directories are touched; any symlink in that directory is left alone. If everything looks right after a few sessions, the backups are safe to remove: ```bash rm -rf ~/.config/opencode/skills/*.bak.* ``` ## Relationship to skillset The [skillset](https://gitea.jordbo.se/joakimp/skillset) repo deploys its own version-controlled skills into `~/.agents/skills/` via `deploy-skills.sh --bootstrap --prune-stale`, which the entrypoint runs on every start — *before* the OMOS reconcile. If a skill name exists in both, **OMOS wins**: the reconcile uses `ln -sfn`, which replaces any existing symlink. Today the only overlap is `simplify` (the OMOS copy is richer — it bundles `codemap.md` and a `README.md`), so `simplify` was removed from the skillset repo and the image copy owns the name. ## Configuration | Variable | Default | Effect | |---|---|---| | `OMOS_SKILLS` | `true` | Symlink the bundled skills into `~/.agents/skills/` on each start. Set `false` to deploy no skills from the image. | `OMOS_SKILLS` is **independent of `ENABLE_OMOS`**: the skills are useful to plain opencode even when the multi-agent orchestration config is not enabled. The reconcile is additionally gated on the bundled-skills source being present, so it is automatically a no-op on the non-OMOS (`base`) image variant. ## Troubleshooting - **A skill didn't update after `docker compose pull`.** Make sure you recreated the container (`docker compose up -d --force-recreate`); a plain restart reuses the old container layer. Confirm the link target — `readlink ~/.agents/skills/deepwork` should point under `/usr/lib/node_modules/oh-my-opencode-slim/src/skills/`. - **A skill disappeared.** If OMOS upstream restructured its package the symlink target may no longer exist. The build-time smoke test asserts the source path, so this should be caught in CI; if you hit it at runtime, look for a dangling link in `ls -l ~/.agents/skills/`. - **I want a frozen copy back.** It's at `~/.config/opencode/skills/.bak.` until you delete it.