Lección 01 · 8 en la ruta · 7 min de lectura · Nivel 0
01 — Lee tu barra: qué te está diciendo Claude Code en cada turno
Mirar las dos líneas de la barra de estado y saber, en un vistazo, cuatro cosas: cuánto contexto te queda antes de que la sesión se degrade, si la caché sigue caliente, si tu trabajo está a salvo (commit, push, HANDOFF)…
Objetivo
Mirar las dos líneas de la barra de estado y saber, en un vistazo, cuatro cosas: cuánto contexto te queda antes de que la sesión se degrade, si la caché sigue caliente, si tu trabajo está a salvo (commit, push, HANDOFF) y qué deberías hacer ahora. Al final de la lección puedes leer cualquier estado de la barra sin abrir la leyenda.
Pruébala en vivo: el simulador de la barra mueve contexto, caché,
cuota, git, HANDOFF y modelo, y muestra la salida real de statusline.sh para cada combinación.
Toca un sector y abre su fila de la leyenda: es esta lección hecha interactiva.
Quién lo hace: tú. La barra la dibuja home/.claude/statusline.sh en cada turno; tú solo
la lees.
Por qué: una barra que no miente
Claude Code le pasa a la barra un JSON en cada turno (modelo, tokens, costo, cuota, caché). Lo fácil es pintar esos números tal cual. El problema es que un número que no llegó y un número que vale cero se ven igual, y se actúa distinto sobre cada uno. Por eso la barra tiene una sola regla de fondo:
Un campo que falta o no se puede leer se pinta
⚠en ámbar, nunca0.
La segunda regla es que ningún umbral vive en el script. Los 150k y 300k del contexto, el
90 % de la cuota, los 5 minutos de la caché: todo está en rules/thresholds.json. Si ese
archivo no se puede leer, la barra dice ⚠ umbrales y deja de colorear. Un umbral que no puedes
leer no es lo mismo que un umbral que no se cruzó.
Pasos
Los números son los de la leyenda completa, statusline.es.md. Aquí van
por grupos, en el orden en que conviene mirarlos.
Paso 1 — Modelo y contexto (#1–#5, línea 1)
Opus 5.5 ·high @mac ▓▓▓▓▓▓▓▓▓░░░░░░┋░░░░ 180k/400k · 18% of 1M
- #1 y #2: modelo y nivel de esfuerzo.
@macdice en qué máquina corre la sesión; por Remote-SSH todas las ventanas se ven iguales. - #3, la barra: va de 0 hasta donde dispara el auto-compact. El
┋marca la banda roja (context-red, 300k): ahí deberías haber cortado. Es un medidor de riesgo, no de gasolina. - #4: tokens usados / techo del auto-compact. Verde por debajo de 150k, ámbar entre 150k y
300k, rojo desde 300k (con
⚠detrás). - #5: el porcentaje de la ventana real. Está para contexto, no para decidir: la calidad cae a un tamaño absoluto, y 60 % de 1M es el doble de la banda roja.
Paso 2 — Costo y tiempo (#6–#7)
$7.10 · 90m. El costo es la cifra que Claude Code calcula para la sesión, no una factura. Los
minutos cuentan desde que abriste la sesión: a partir de 8 h, con el contexto en ámbar, la pista
te propone cortar.
Paso 3 — Caché (#10–#12): una palabra y un número
La caché de prompt guarda tu contexto una hora. Mientras está caliente, cada turno lee lo guardado a precio de lectura; cuando expira, el siguiente turno paga escribirlo todo de nuevo. La barra lo dice en un solo lugar de la línea 1:
| Lo que ves | Qué significa |
|---|---|
⚡ caliente · 42m (verde) | Faltan 42 minutos para que expire la última escritura (expires_at) |
⚡ enfriando · 4m (ámbar) | Quedan 5 minutos o menos (cache-cooling). La pista dice qué hacer |
❄ fría · próximo turno reescribe (cian) | Ya expiró: el próximo mensaje paga reescribir todo el contexto |
El acierto de caché (#11, hit 79%) pasa a la línea 2 y solo aparece cuando informa: por
debajo de 85 % (cache-hit-ok). En rojo bajo 60 % (cache-cold), y entonces la pista nombra la
causa que trae el JSON (model_changed, effort_changed…). #12 son los fallos de caché.
Paso 4 — Cuota del plan (#8–#9, línea 2)
5h 41% 7d 87%: cuánto llevas gastado de la ventana de 5 horas y de la semanal. Si
rate_limits todavía no existe (antes de la primera llamada), el sector queda en blanco: eso no
es un error, es “todavía no hay dato”.
Paso 5 — Git (#13–#14)
+213/-15 ⎇ main ↑1 ↓0 ●2 ?1: líneas añadidas/quitadas en la sesión, rama, commits sin
pushear (↑) y sin traer (↓), archivos modificados (●) y sin seguimiento (?). ⊘ en vez de
↑↓ quiere decir que la rama no tiene upstream. ↑1 se pone ámbar cuando el commit más viejo
sin pushear lleva más de 2 h.
Paso 6 — HANDOFF (#15)
HANDOFF.md es la memoria de la sesión. ✓HANDOFF en verde: nada se movió después de
escribirlo. ⚠HANDOFF 14:05 ·2f ·1c ·0s: lo escribiste a las 14:05 y desde entonces hay 2
archivos más nuevos que él, 1 commit y 0 sesiones nuevas. En rojo con más de 20 archivos o 2
sesiones. Un ? en un contador quiere decir “no se pudo calcular”, nunca cero.
Paso 7 — La pista (#18) y lo que queda (#16–#17)
El texto magenta al final es una sola sugerencia: la del umbral de mayor prioridad que se
cumple ahora. El orden lo da priority en thresholds.json: cuota → contexto rojo → caché
enfriando → hit bajo → sesión larga → commits sin push. Nunca muestra dos: una barra con dos
consejos ya no se lee de un vistazo. #17 es el nombre de la sesión; #16 (⚠ umbrales) solo
aparece si thresholds.json falta o está roto.
Qué salió mal de verdad
❄true%/0y un “sin HANDOFF” falso (2.1.275). Claude Code quitó.permission_modedel JSON. El script leía 17 campos separados por tabulador, y conIFS=$'\t'un campo vacío colapsa: todo se corrió un lugar.hitrecibiótrue, el directorio recibió un número y git falló. Arreglo: separador\x1f, centinela por campo y control de cantidad de campos.❄96% /59mse contradecía. Un acierto alto junto a un copo, y un TTL que no respondía la pregunta real (“¿cuánto me queda si no mando nada?”). De ahí sale el rediseño del Paso 3 (2026-10-15): el estado es una palabra, el número son minutos y el hit solo aparece si importa.$12,00en vez de$12.35. Con localees_ES,printf '%.2f'lee y escribe con coma. La barra fijaLC_NUMERIC=Cy conserva tuLC_CTYPEpara los glifos.- “hace 50 min” durante horas. La barra solo se redibuja con eventos de la sesión, así que una edad se congela. El HANDOFF muestra ahora la hora a la que se escribió.
Cómo verificar
bash tests/statusline_test.sh # golden files + invariantes: 67 casos
bash home/.claude/statusline.sh < tests/fixtures/cache-cooling.json
La segunda línea pinta el estado “enfriando” desde una captura real saneada (2.1.300). Prueba a
cambiar cache-cooling a 60 en rules/thresholds.json y vuelve a correrla: la misma caché pasa
a “enfriando” sin tocar el script.
Autoevaluación
- La barra muestra
⚠mdonde suele ir el tiempo. ¿Es una sesión recién abierta o el JSON cambió de forma? - Ves
412k/967ken verde. ¿Puede ser? ¿Qué te dice eso dethresholds.json? ⚡ caliente · 3mno existe: ¿qué ves en su lugar y por qué?- Tienes
❄ fría · próximo turno reescribecon 380k de contexto. ¿Sigues o haces/handoffy/clear? ¿Qué cambia en el costo del primer turno entre una opción y la otra? ⚠HANDOFF 09:12 ·0f ·0c ·?s: ¿está al día el HANDOFF?
Respuestas
- Ninguna de las dos se puede descartar con ese dato solo, pero
⚠dice “faltó o no se pudo leer”. En una sesión nueva el tiempo sí llega; si persiste, re-captura el payload (statusline-internals.md). - No con los umbrales del kit: 412k pasa los 300k de
context-red. Si está verde, alguien movió el número conCC_CTX_RED_K; unthresholds.jsonilegible la dejaría sin color y diría⚠ umbrales. ⚡ enfriando · 3men ámbar, porque 3 ≤cache-cooling(5), y la pista te propone un turno corto o un/handoff.- El primer turno reescribe el contexto en los dos casos, pero tras
/clearse reescribe uno mucho más chico. Con 380k (zona roja) lo correcto es/handoffy luego/clear. - No se sabe:
?ses “no se pudo contar las sesiones”, no cero. Por eso no sale✓HANDOFF.