Communitygithub.com

lijiajie-git/tpu-trc-quickstart

Aprovisionamiento en un solo comando y mediante IA para TPU gratuitas de Google TRC (TPU Research Cloud): cola, reclama, SSH y verificación de estado, todo desde la CLI. Deamon basado en configuración y mapa de errores probado en campo.

¿Qué es tpu-trc-quickstart?

Este skill permite a un agente de IA (como Claude Code, Cursor o Codex) gestionar completamente el ciclo de vida de una TPU gratuita otorgada por el programa TPU Research Cloud (TRC) de Google Cloud. El agente puede encolar solicitudes de TPU en las zonas adecuadas, monitorear el proceso de asignación (desde `ACCEPTED` hasta `ACTIVE`), manejar errores comunes como `GCE_STOCKOUT` o falta de cuota de IP, y conectarse a la TPU vía SSH una vez activa. También incluye lógica para evitar la creación de recursos duplicados, detectar conflictos con otros usuarios en proyectos compartidos y liberar la TPU correctamente al finalizar. El skill utiliza exclusivamente herramientas de línea de comandos (`gcloud`), por lo que funciona en cualquier entorno donde esté instalado el SDK de Google Cloud. Está optimizado para TRC, pero las técnicas son aplicables a cualquier TPU en GCP. Incluye un mapa de errores probado en campo para diagnosticar fallos comunes, como problemas de cuota, configuración de red (NAT, Private Google Access) y problemas con versiones del runtime.

Compatible con✓Claude Code✓Codex CLI~Cursor
npx skills add lijiajie-git/tpu-trc-quickstart

Preguntar en tu IA favorita

Abre un nuevo chat con esta habilidad de agente ya precargada.

Documentación

TRC TPU todo en uno (edición delegada a IA)

última-verificación: 2026-06-11 (la matriz de comandos / versiones de runtime / quotaId varían con GCP; verifique la fecha de verificación aquí + CHANGELOG.md)

Qué es esto: acabas de recibir una cuota gratuita de TPU de Google TRC (TPU Research Cloud), y quieres saltarte la consola web y los documentos de Google Cloud y que una IA reclame, se conecte y ejecute la TPU por ti directamente desde la línea de comandos. Este archivo es la hoja de instrucciones completa para la IA: cada escollo ha sido probado en campo de antemano.

Cómo usarlo:

  • Usuarios de Claude Code: coloca esta carpeta en ~/.claude/skills/tpu-trc-setup/ y di "configuración TRC TPU" en la conversación para activarlo
  • Codex / otras IAs: pega el texto completo de este archivo en la conversación, o ponlo en un repositorio para que la IA lo lea, luego di "configura la TPU para mí siguiendo esto"

Líneas rojas (tanto la IA como los humanos deben obedecer):

  1. Solo elimina recursos que hayas creado tú mismo: el proyecto puede ser compartido, y eliminar la TPU de otra persona significa eliminar su experimento
  2. La configuración de red (subred / Router / NAT) son recursos compartidos a nivel de proyecto; pregunta al propietario del proyecto antes de cambiarlos
  3. Elimina al terminar: los chips TPU son gratuitos, pero la VM/disco se factura por hora, y un nodo inactivo durante la noche cuesta dinero real
  4. Usa tu propia cuenta de Google en todo momento; nunca le pidas a nadie una contraseña / clave privada / clave de cuenta de servicio

1. [Rellena esto primero] Tu información

Mi correo electrónico de la cuenta de Google:  <TU_CORREO>
Mi ID de proyecto de GCP:                     <TU_ID_DE_PROYECTO>     # el proyecto en el que se inyectó la cuota TRC
Mi rol:                                       <Propietario / Editor>  # Editor es suficiente

[Pega tu correo de aprobación de TRC a continuación] (El asunto suele ser "Welcome to the TPU Research Cloud"):

<pega el texto completo del correo de TRC>

Paso uno de la IA: analiza el correo de TRC anterior y genera una tabla de cuotas antes de comenzar a trabajar:

CampoDónde encontrarlo en el correo
Tipo de TPU (v2/v3/v4/v5e/v6e) + número de chipslista de cuotas en el cuerpo del correo
zona para cada cuotamismo lugar (una cuota es válida solo en la zona nombrada, no se puede cambiar)
bajo demanda vs. interrumpible/spotmismo lugar (spot puede ser interrumpido en cualquier momento)
período de validezgeneralmente 30 días desde la aprobación

Obligaciones de TRC: debes publicar los resultados públicamente (artículo / código abierto / publicación de blog) + dar a Google tu opinión sobre tu experiencia. Para problemas, contacta a [email protected] o al canal #tpu-research-cloud en el Discord de la Comunidad de Desarrolladores de Google.


2. Entorno único (máquina local)

# 2.1 Instala el SDK de Google Cloud (omite si ya está instalado): https://cloud.google.com/sdk/docs/install
gcloud version

# 2.2 Los comandos de cola de TPU se encuentran en el componente alpha: debes instalarlo
gcloud components install alpha

# 2.3 Inicia sesión + configura el proyecto predeterminado
gcloud auth login <TU_CORREO>
gcloud config set project <TU_ID_DE_PROYECTO>
gcloud auth list                       # confirma que la cuenta activa es la tuya
gcloud config get-value project        # confirma que el proyecto es correcto

# 2.4 (opcional) Algunos SDKs de Python necesitan ADC
gcloud auth application-default login

Escollo: en un entorno de ejecución de IA, a menudo gcloud no está en PATH, lo que genera el error gcloud: command not found. Ejecuta esta línea primero y usa $GCLOUD en el resto del archivo:

export GCLOUD=$(which gcloud || echo /opt/homebrew/bin/gcloud)   # ruta común en mac homebrew

3. Escaneo previo al trabajo (evita crear duplicados / eliminar lo de otros)

# Escanea cada zona que aparezca en el correo de TRC
for zone in <zona1> <zona2> <zona3>; do
  echo "=== $zone ==="
  $GCLOUD alpha compute tpus queued-resources list \
    --project=<TU_ID_DE_PROYECTO> --zone=$zone \
    --format="table(name, state.state, tpu.nodeSpec[].node.acceleratorType)" 2>/dev/null
done
  • Ya ACTIVE → salta directamente a la §7 y úsala, no crees una nueva
  • Un recurso con un prefijo de nombre de otra persona → déjalo en paz

4. Verificación previa de la red (solo las TPU grandes con ≥16 hosts necesitan esto, ej. v5e-64 / v6e-64)

Antecedentes: la cuota de IP externa de un proyecto de GCP por región tiene un límite predeterminado de solo 8, mientras que v5e-64 / v6e-64 necesita 16 IPs de host. Crear sin manejar esto fallará con el error IN_USE_ADDRESSES limit (FAILED). Las TPU pequeñas (v4-32 tiene solo 4 hosts / v2-8 v3-8 de un solo host) no necesitan esta sección.

# 4.1 Verifica la cuota de IP actual (confirma si el límite es 8)
$GCLOUD compute project-info describe --project=<TU_ID_DE_PROYECTO> \
  --format="table(quotas.filter(metric:IN_USE_ADDRESSES))"

# 4.2 Solución: crea con IPs internas (--internal-ips, ver §5), que no usa nada de la cuota de IP externa.
#     Requisito A: la subred predeterminada de la región tiene habilitado Private Google Access (para extraer libtpu)
$GCLOUD compute networks subnets update default \
  --region=<REGION> --enable-private-ip-google-access --project=<TU_ID_DE_PROYECTO>

#     Requisito B: la región necesita un Cloud Router + Cloud NAT (para pip install; PGA no cubre PyPI)
$GCLOUD compute routers create my-tpu-router \
  --network=default --region=<REGION> --project=<TU_ID_DE_PROYECTO>
$GCLOUD compute routers nats create my-tpu-nat \
  --router=my-tpu-router --region=<REGION> \
  --auto-allocate-nat-external-ips --nat-all-subnet-ip-ranges \
  --project=<TU_ID_DE_PROYECTO>

⚠️ Los tres comandos en 4.2 son configuraciones compartidas a nivel de proyecto. En un proyecto compartido, primero pregunta al propietario si ya están configurados (configurado una vez = permanente), y no los recrees.

Síntoma oculto de NAT faltante: más adelante, cuando un worker instala dependencias (ej. jax), pip informa Could not find a version that satisfies the requirement jax[tpu] pero el script puede decir "listo" — esto es un fallo silencioso de pip, no un problema de versión; regresa y agrega el NAT.


5. Crear la TPU (cola)

Matriz de comandos

TPU--accelerator-type--runtime-versioncantidad de hosts¿necesita --internal-ips?
v2-8v2-8tpu-ubuntu2204-base1no
v3-8v3-8tpu-ubuntu2204-base1no
v4-32v4-32tpu-ubuntu2204-base4no
v5e-64v5litepod-64v2-alpha-tpuv5-lite16sí
v6e-64v6e-64v2-alpha-tpuv6e16sí

La versión del runtime se actualiza con el tiempo. Cuando encuentres un error de versión: primero verifica con $GCLOUD alpha compute tpus versions list --zone=<ZONA> (⚠️ probado en campo: la lista es incompleta — v2-alpha-tpuv5-lite puede no estar en la lista pero en realidad es utilizable; trata la lista solo como referencia), y si aún no coincide, consulta la documentación oficial (§10).

Spot (úsalo para cuota interrumpible)

$GCLOUD alpha compute tpus queued-resources create <nombre de cola, ej. my-v5e-qr> \
  --node-id=<NOMBRE_VM, ej. my-v5e-vm> \
  --project=<TU_ID_DE_PROYECTO> --zone=<ZONA> \
  --accelerator-type=<de la tabla de arriba> \
  --runtime-version=<de la tabla de arriba> \
  --provisioning-model=SPOT \
  --internal-ips          # agrega solo para TPU con ≥16 hosts como v5e-64/v6e-64

Escollo (dependiente de la versión): en SDKs antiguos, spot debe escribirse como --provisioning-model=SPOT; escribir --spot / --best-effort produce el error STANDARD provisioning model is incompatible with spot requests. En SDKs más nuevos (probado en 562.0.0) --spot funciona, así que cualquiera de los dos está bien. Cuando no estés seguro, usa --provisioning-model=SPOT (reconocido por todas las versiones).

Bajo demanda (úsalo para cuota no interrumpible, la más estable)

$GCLOUD alpha compute tpus queued-resources create <nombre de cola> \
  --node-id=<NOMBRE_VM> \
  --project=<TU_ID_DE_PROYECTO> --zone=<ZONA> \
  --accelerator-type=<de la tabla de arriba> \
  --runtime-version=<de la tabla de arriba> \
  --guaranteed

Estrategia de reclamo

  • Abanico entre zonas: si el mismo tipo de cuota existe en múltiples zonas → encola una solicitud en paralelo en cada zona que tenga cuota (probado en campo: las cuotas por zona en diferentes zonas son mutuamente independientes y no exclusivas; GCP oficialmente también fomenta distribuir spot en múltiples zonas)
  • Sin colas duplicadas en la misma zona: encolar dos solicitudes del mismo tipo en una zona no tiene sentido (mismo grupo de capacidad, no acelera, y choca con los mismos espacios de cuota por zona)
  • Tan pronto como una sea reclamada, cancela inmediatamente las perdedoras restantes: de lo contrario, las perdedoras permanecen en la nube y siguen en cola, y una vez que una se vuelve ACTIVE, la VM comienza a quemar dinero (chips gratuitos ≠ máquina gratuita)
  • Confirma que la zona tiene cuota antes de encolar: una zona sin cuota (verifica la cuota en §4.5 abajo) siempre fallará (FAILED) si se encola — pura pérdida de tiempo
  • Una zona que informa no more capacity → no es un error de comando; cambia de zona, no reintentes rápidamente en la misma zona
  • Para modelos de oferta limitada como v6e, la experiencia dice que son de "un solo espacio" (encola uno a la vez y se llena) — no los distribuyas ampliamente junto con otros modelos al mismo tiempo
  • Después de un reclamo spot, la supervivencia promedio es de unas pocas horas → úsalo tan pronto como lo reclames y respalda los resultados rápidamente

Primero verifica si una zona tiene cuota (evita encolados inútiles; requiere gcloud components install beta)

# Cuota por zona para v5e interrumpible (para otros modelos, intercambia el quotaId correspondiente, ver documentación oficial §10)
$GCLOUD beta quotas info describe TPUV5sPreemptibleLitepodPerProjectPerZoneForTPUAPI \
  --service=tpu.googleapis.com --project=<TU_ID_DE_PROYECTO> \
  --format="yaml(quotaId,dimensionsInfos)"

Lee el valor por zona en dimensionsInfos: '64' = suficiente para un slice de 64 chips / '0' = cero explícito / ausente (details: {}) = esa zona no recibió cuota, encolar siempre fallará (FAILED). (quotaId es una API beta; el ID puede cambiar entre versiones del SDK; si una versión antigua no lo reconoce, primero ejecuta gcloud beta quotas info list para obtener el ID real.)


6. Esperando: la máquina de estados

# Consulta (cada 30s es suficiente, no consultes con demasiada frecuencia)
$GCLOUD alpha compute tpus queued-resources describe <nombre de cola> \
  --project=<TU_ID_DE_PROYECTO> --zone=<ZONA> --format="value(state.state)"
EstadoSignificado¿Se puede eliminar?Qué hacer
ACCEPTEDen la cola✅espera
WAITING_FOR_RESOURCESen cola por capacidad (minutos a horas)✅espera
PROVISIONINGasignando hardware❌ no se puede eliminarespera (probado en campo: puede estancarse 2h+ y aún así tener éxito — esto es normal)
ACTIVElisto✅ve a §7 inmediatamente
SUSPENDEDspot fue interrumpido✅elimina + re-encola (probado en campo: esperar la recuperación automática es esencialmente inútil)
FAILEDcreación fallida✅primero describe para ver la causa raíz, luego decide (clasificación triple a continuación; no re-encoles a ciegas)

Escollo: llamar a delete en el estado PROVISIONING produce DeleteQueuedResource is not supported when state is PROVISIONING; solo puedes esperar a que se vuelva ACTIVE o FAILED.

Clasificación triple de FAILED (decide "re-encolar" vs "detener"; no re-encoles a ciegas)

gcloud alpha compute tpus queued-resources describe <QR> — lee el error y clasifícalo en tres categorías:

CategoríaCriterio (error.message)SignificadoAcción
capacidad (reintentar)code: 8 no more capacity in the zone / GCE_STOCKOUT / ZONE_RESOURCE_POOL_EXHAUSTEDla cuota existe pero la zona está agotada en este momentoelimina + cambia/re-encola, cubre con abanico multizona
estructural (detener)PERMISSION_DENIED ... billing / billingEnabled: false / Limit: 0 / RESOURCE_EXHAUSTED / NO_VALID_BILLING_ACCOUNTcuota no otorgada / facturación desactivada / problema de permisosdetente, no re-encoles (nunca tendrá éxito); verifica la facturación o contacta a TRC/propietario
desconocidocualquier otra cosanunca visto antespor defecto, un solo reintento de capacidad y luego observa

Comandos de autoverificación de facturación/proyecto: $GCLOUD beta billing projects describe <TU_ID_DE_PROYECTO> (mira billingEnabled), $GCLOUD projects describe <TU_ID_DE_PROYECTO>. billingEnabled: false derriba toda la API de TPU, incluso si la cuota todavía está ahí.

Comando de eliminación (úsalo tanto antes de re-encolar como después de terminar):

$GCLOUD alpha compute tpus queued-resources delete <nombre de cola> \
  --project=<TU_ID_DE_PROYECTO> --zone=<ZONA> --force --quiet

Opcional: w

... [truncado para traducción]

Skills relacionados