ADR-0012 — dai upgrade (self-update del CLI)
- Estado: aceptado
- Fecha: 2026-07-12
- Decide: lead / arquitecto de la metodología
Contexto
dai tiene dos cosas versionadas e independientes: el CLI (el paquete npm global, una copia por dev) y el scaffold del repo (.dai/, skills, .dai/VERSION, compartido y commiteado). El drift entre ambos ya se detecta (versionDrift, ADR-0010) y dai doctor/dai version imprimen el estado.
Pero actualizar el CLI era manual: cuando el detector veía el CLI atrasado, imprimía el texto npm i -g @dforce2055/dai para que el dev lo copiara y corriera a mano. No había comando. Fricción repetida, y un detector que empujaba a algo que no existía como acción de dai.
Escenario típico: un dev vuelve el lunes con el CLI en v0.2.0 y ya salió v0.5.0. Tiene que actualizar su CLI (y después traer el repo con git pull, que el mantenedor ya sincronizó).
Decisión
Agregamos dai upgrade (alias update): self-update del CLI global a la última versión publicada en el registry.
- Scope: solo el CLI. Corre
npm i -g <name>@latest(el<name>sale depackage.json, robusto si cambia el scope).--checksolo informa;--dry-runmuestra el comando sin correrlo. - NO toca el repo. Tras actualizar, reporta el drift del scaffold (
reportDrift) pero no corredai sync. Elsyncqueda como acto explícito del mantenedor: un dev con CLI viejo que sincronizara degradaría el.dai/del repo, y sincronizar desde cada máquina genera commits en conflicto. - El núcleo es puro y testeado (
planUpgradeenlib/semver.mjs): decideup-to-date | ahead | upgrade. El I/O (npm view/npm i -g) es la cáscara del comando, no se unit-testea (mismo criterio que elfetch).
Consecuencias
- Más fácil: un comando cierra el loop de "CLI atrasado" en vez de copiar un hint. La separación de roles queda nítida:
upgrade= tu CLI (self-update),sync= el repo (mantenedor, commiteado). - Se acepta pagar: depende del registry (es online; en redes cerradas —ADR-0006— falla con mensaje claro y fallback al
npm i -gmanual). Asume npm como package manager del global (no pnpm/yarn/volta/asdf); si el install falla, deriva al comando manual. No auto-sincroniza el repo (a propósito).
Alternativas consideradas
- Auto-correr
dai synctras el upgrade — descartado: un dev degradaría el repo con un CLI viejo y sincronizar desde cada máquina genera conflictos. Elsynces del mantenedor. - Pinnear dai como devDependency por-repo (sin global → sin drift, alineado en
npm install) — descartado como default: dai se diseñó global y zero-dep para redes cerradas (ADR-0006), y no todos los repos son npm. Queda como opción del consumidor, no del método. - No hacer nada (dejar el hint manual) — descartado: fricción repetida sobre una acción que el propio detector ya recomendaba.