Módulo 2: Mental Models para AI Code

Trust Calibration por Tipo de Tarea

Trust Calibration por Tipo de Tarea

Descripción de la cápsula

Ya sabes cómo supervisar (Managing an Intern) y cuándo pausar (Circuit Breaker). Ahora necesitas la herramienta más accionable de las tres: cuánto confiar. Trust Calibration convierte "creo que está bien" en "para este tipo de tarea, mi confianza es del 40%, así que reviso lógica y edge cases." Es la diferencia entre intuición y proceso.

En el módulo 1 viste una tabla preliminar de confianza por tipo de tarea. Esta cápsula la expande significativamente: vas a construir una tabla detallada con 15 tipos de tarea, entender los factores que suben y bajan tu confianza, y aprender a actualizar tu calibración con experiencia. Trust Calibration es el modelo que puedes aplicar literalmente mañana en tu trabajo.

La clave: Trust Calibration no es un número exacto. Es un rango que guía tu comportamiento. "70% de confianza" no significa que 7 de cada 10 veces el código es correcto. Significa que tu nivel de revisión corresponde a una tarea de riesgo moderado donde una revisión enfocada es suficiente.


Trust Calibration como Proceso Estructurado

No es intuición — es proceso

La mayoría de developers calibra por intuición: "se ve bien" o "algo no me gusta". La intuición tiene dos problemas:

Problema 1: La intuición es inconsistente
├── Lunes por la mañana (descansado): "Voy a revisar todo"
├── Viernes a las 6 PM (cansado): "Se ve bien, acepto"
└── El riesgo del código no cambió. Tu calibración sí.

Problema 2: La intuición no es comunicable
├── "¿Por qué aceptaste este código sin revisión?"
├── "No sé, se veía bien"
└── No puedes enseñar ni defender "se veía bien"

Trust Calibration reemplaza intuición con proceso:

Proceso de Trust Calibration:
1. Identificar el tipo de tarea
2. Consultar tu tabla de confianza base
3. Ajustar por factores contextuales
4. Definir profundidad de revisión según resultado
5. Documentar y actualizar con experiencia

El modelo mental

Piensa en Trust Calibration como un termómetro de confianza:

100% ─── Confianza total (no existe para AI code)
 90% ─── Revisión visual (boilerplate, formateo)
 80% ─── Revisión rápida (config, docs)
 70% ─── Revisión enfocada (CRUD, utilidades)
 60% ─── Revisión detallada (lógica media)
 50% ─── Revisión cuidadosa (tests, queries)
 40% ─── Revisión exhaustiva (lógica de negocio)
 30% ─── Revisión línea por línea (data pipelines)
 20% ─── Desconfianza activa (regex, concurrencia)
 10% ─── Verificación contra documentación (auth, crypto)
  0% ─── No confíes, escribe tú (no existe tampoco)

Tu posición en el termómetro determina tu comportamiento: cuánto tiempo dedicas, qué tan profundo revisas, y qué herramientas usas para verificar.


La Tabla de Trust Calibration

Tabla completa: 15 tipos de tarea

#Tipo de tareaConfianza baseProfundidad de revisiónQué verificar
1README / documentación85-90%Visual rápidaQue la información sea correcta y no engañosa
2Boilerplate (setup, config inicial)80-90%Visual rápidaVersiones de dependencias, paths correctos
3Dockerfiles / CI config75-85%RápidaImagen base, secrets no hardcoded, stages
4Modelos de datos (Pydantic, ORM)70-80%EnfocadaCampos correctos, tipos apropiados, validaciones
5CRUD endpoints60-70%EnfocadaValidaciones, error handling, status codes
6Funciones de utilidad60-70%EnfocadaEdge cases, naming, tipos de retorno
7Tests unitarios50-60%DetalladaQue testen lo correcto, no solo que pasen
8Queries SQL / ORM40-55%DetalladaSQL injection, N+1, lógica del query, índices
9Error handling / logging50-60%DetalladaQue no exponga info sensible, que capture lo necesario
10Lógica de negocio25-40%ExhaustivaQue haga lo que el negocio necesita, valores correctos
11Integraciones externas (APIs)30-45%ExhaustivaAPI correcta, manejo de errores, retry logic, timeouts
12Data pipelines / ETL25-40%ExhaustivaTransformaciones correctas, manejo de datos null/inválidos
13Regex patterns15-25%Línea por líneaProbar con inputs edge case, false positives/negatives
14Auth / Security / Crypto10-20%Línea por línea + docsContra documentación oficial, cada decisión de seguridad
15Procesamiento financiero10-20%Línea por línea + testsCada cálculo, precision (Decimal), compliance

Cómo leer la tabla

Confianza 80-90%: "Probablemente está bien"
→ Revisión visual de 1-3 minutos
→ Si algo salta a la vista, profundiza
→ Si no, acepta

Confianza 60-70%: "Está bien si las partes clave están bien"
→ Revisión de 5-10 minutos enfocada en lógica y edge cases
→ No cada línea, pero sí las funciones principales

Confianza 40-55%: "Necesito verificar"
→ Revisión de 10-20 minutos
→ Verifica lógica, prueba con inputs edge case
→ Compara contra documentación si aplica

Confianza 10-30%: "Asumo que hay problemas hasta probar lo contrario"
→ Revisión de 20-40 minutos
→ Lee cada línea, verifica contra docs oficiales
→ Escribe tests para cada escenario
→ Pregúntate "¿cómo podría fallar esto?"

Factores que Ajustan tu Calibración

Factores que AUMENTAN confianza

Tu confianza base sube cuando estas condiciones están presentes:

+10-15%: Tests existentes que cubren el escenario
  → Si hay tests que verifican la lógica, tu revisión
    puede ser menos exhaustiva. Los tests hacen parte
    del trabajo de verificación.

+5-10%: Dominio que conoces bien
  → Si conoces el dominio, detectas errores más rápido.
    Tu revisión rápida es más efectiva que la revisión
    exhaustiva de alguien que no conoce el dominio.

+5-10%: Patrón estándar bien documentado
  → Si el código sigue un patrón que has visto 100 veces
    (ej: CRUD FastAPI estándar), la probabilidad de error
    es menor.

+5%: Código corto y simple (< 30 líneas, flujo lineal)
  → Menos líneas = menos superficie de error.
    Pero no confundas corto con seguro (3 líneas de
    SQL injection son peores que 300 de CRUD).

+5-10%: Claude Code tiene buen track record en esta tarea
  → Si las últimas 5 veces que pediste CRUD endpoints
    el resultado fue correcto, tu calibración sube.

Factores que DISMINUYEN confianza

Tu confianza base baja cuando estas condiciones están presentes:

-10-20%: No hay tests
  → Sin tests, eres la única línea de defensa.
    Tu revisión debe ser más exhaustiva.

-10-15%: Dominio que no conoces
  → Si no conoces el dominio, errores sutiles pueden
    pasar desapercibidos. Una función de cálculo de
    impuestos puede "verse bien" pero tener los
    porcentajes equivocados.

-10-15%: Código con state mutable o side effects
  → Side effects (modifica DB, envía emails, llama APIs)
    son difíciles de verificar visualmente. Necesitas
    ejecutar o escribir tests.

-5-10%: Prompt fue vago o ambiguo
  → Si tu prompt no fue específico, Claude Code tuvo
    que "adivinar" tu intención. Más probabilidad de
    que adivinó mal.

-10-20%: Seguridad o compliance involucrado
  → Cualquier cosa que toque auth, encryption, PII,
    o regulaciones requiere desconfianza activa.

-5-10%: Código complejo (múltiples branches, async, concurrencia)
  → Complejidad alta = más superficie de error.
    AI es especialmente impredecible con concurrencia.

-10-15%: Integración con API que cambió recientemente
  → Claude Code puede generar código para versiones
    anteriores de una API. Si la API cambió, el código
    puede usar endpoints que ya no existen.

Ejemplo: Ajustando calibración

Tarea: Generar un endpoint CRUD para productos

Confianza base (tabla): 65%

Ajustes:
  +10%: Conozco bien FastAPI (dominio familiar)
  +5%:  Es un patrón estándar (CRUD simple)
  -10%: No hay tests todavía
  -5%:  Mi prompt fue genérico ("genera CRUD de productos")

Confianza ajustada: 65 + 10 + 5 - 10 - 5 = 65%

→ Se mantuvo similar. Revisión enfocada de 5-8 minutos.
→ Verificar: validaciones, error handling, status codes.
Tarea: Generar middleware de rate limiting

Confianza base (tabla): 35% (lógica de negocio + seguridad)

Ajustes:
  -15%: No conozco bien rate limiting algorithms
  -10%: No hay tests
  -10%: Tiene implicaciones de seguridad (DoS protection)
  +5%:  Código relativamente corto

Confianza ajustada: 35 - 15 - 10 - 10 + 5 = 5%

→ Muy baja. Revisar cada línea.
→ Verificar contra documentación de rate limiting.
→ Escribir tests antes de aceptar.
→ Considerar usar una librería probada en vez de custom.

Trust Debt: Cuando No Calibras

Qué es Trust Debt

Trust Debt es el concepto de que cuando under-calibras (confías de más), los problemas se acumulan silenciosamente, como technical debt. No ves el costo inmediatamente, pero se manifiesta eventualmente.

Trust Debt en acción:

Semana 1: Aceptas endpoint de búsqueda sin revisar queries
  → Confianza: "70% — es CRUD"
  → Realidad: queries sin parameterizar (SQL injection)

Semana 2: Aceptas endpoint de filtros sin revisar
  → Se basa en el endpoint de semana 1
  → Misma vulnerabilidad, ahora en 2 endpoints

Semana 3: Aceptas feature de "búsqueda avanzada"
  → Se basa en los 2 endpoints anteriores
  → Ahora hay 3 endpoints con SQL injection

Semana 6: Auditoría de seguridad
  → Encuentran SQL injection en 3 endpoints
  → El fix requiere cambiar 3 archivos + 2 de tests
  → 3 días de trabajo + review + QA
  → El costo de "no revisar queries" se acumuló

Cómo evitar Trust Debt

1. Calibra en el momento, no "después"
   → "Lo reviso mañana" = Trust Debt
   → Revisa en el checkpoint o documenta que falta revisión

2. No heredes calibración de otros
   → Si un compañero dice "esto está bien", verifica tú
   → Tu calibración es personal

3. Actualiza tu tabla con experiencia
   → Si descubres que Claude Code consistentemente genera
     queries sin parameterizar, baja tu confianza en
     "Queries SQL" de 45% a 30%

4. Paga Trust Debt periódicamente
   → Cada semana, dedica 30 minutos a revisar código AI
     que aceptaste rápido durante la semana
   → Busca los patrones que tu calibración no cubrió

Actualizando tu Calibración

Track record: cómo mejorar tu tabla

Tu tabla de calibración no es estática. Se actualiza basándose en tu experiencia:

Proceso de actualización:

1. Genera código con Claude Code
2. Aplica tu calibración actual
3. Revisa según el nivel de confianza
4. ¿Encontraste problemas que tu calibración no predijo?

Si SÍ encontraste problemas inesperados:
  → Baja tu confianza base para ese tipo de tarea
  → Agrega el tipo de problema a "qué verificar"
  → Ejemplo: "CRUD siempre me salió bien, pero hoy encontré
    que no manejaba soft delete. Bajo de 70% a 65% y agrego
    'verificar delete behavior' a mi checklist"

Si NO encontraste problemas:
  → Mantén tu calibración (no subas prematuramente)
  → Después de 5-10 experiences sin problemas, sube 5%
  → Ejemplo: "Las últimas 8 veces que generé modelos Pydantic,
    todo estuvo correcto. Subo de 75% a 80%"

Registro de calibración

Lleva un registro simple para rastrear tu calibración:

Fecha | Tipo de tarea | Confianza usada | Problemas encontrados | Ajuste
------|---------------|-----------------|----------------------|-------
03/10 | CRUD endpoint | 70% | Faltaba validación de email | -5%
03/11 | Auth JWT | 15% | Token no expiraba | Mantener 15%
03/12 | Modelo Pydantic | 80% | Ninguno | Mantener 80%
03/13 | SQL query | 45% | N+1 en join | -5%
03/14 | Dockerfile | 85% | Ninguno | Mantener 85%

Después de 20-30 entries, tu tabla de calibración refleja tu experiencia real con Claude Code, no valores teóricos.


Trust Calibration en Acción

Ejemplo completo: Calibrando un módulo nuevo

Le pides a Claude Code que genere un módulo completo de gestión de suscripciones. Genera 4 archivos. Calibras cada uno:

Archivo 1: models.py

from pydantic import BaseModel, Field
from typing import Optional
from datetime import datetime
from enum import Enum
from decimal import Decimal

class SubscriptionPlan(str, Enum):
    FREE = "free"
    BASIC = "basic"
    PRO = "pro"
    ENTERPRISE = "enterprise"

class PlanPricing(BaseModel):
    plan: SubscriptionPlan
    monthly_price: Decimal
    annual_price: Decimal
    max_users: int
    features: list[str]

class SubscriptionCreate(BaseModel):
    plan: SubscriptionPlan
    billing_cycle: str = Field(..., pattern="^(monthly|annual)$")
    payment_method_id: str

class Subscription(BaseModel):
    id: str
    user_id: str
    plan: SubscriptionPlan
    billing_cycle: str
    status: str = "active"
    current_period_start: datetime
    current_period_end: datetime
    created_at: datetime
Calibración de models.py:
├── Tipo: Modelos de datos → Confianza base: 75%
├── Ajustes:
│   ├── +5%: Conozco bien Pydantic
│   ├── +5%: Patrón estándar
│   └── Sin ajustes negativos
├── Confianza final: 85%
├── Profundidad: Revisión rápida (2-3 min)
└── Qué verifico:
    ├── ✅ Usa Enum para plan → Correcto
    ├── ✅ Usa Decimal para precios → Correcto
    ├── ✅ billing_cycle validado con regex → Correcto
    ├── ✅ Campos razonables para suscripción
    └── → PASS

Archivo 2: pricing_service.py

from decimal import Decimal
from models import SubscriptionPlan, PlanPricing

PRICING = {
    SubscriptionPlan.FREE: PlanPricing(
        plan=SubscriptionPlan.FREE,
        monthly_price=Decimal("0.00"),
        annual_price=Decimal("0.00"),
        max_users=1,
        features=["basic_access"],
    ),
    SubscriptionPlan.BASIC: PlanPricing(
        plan=SubscriptionPlan.BASIC,
        monthly_price=Decimal("9.99"),
        annual_price=Decimal("99.00"),
        max_users=5,
        features=["basic_access", "email_support", "api_access"],
    ),
    SubscriptionPlan.PRO: PlanPricing(
        plan=SubscriptionPlan.PRO,
        monthly_price=Decimal("29.99"),
        annual_price=Decimal("299.00"),
        max_users=25,
        features=["basic_access", "email_support", "api_access",
                   "priority_support", "advanced_analytics"],
    ),
    SubscriptionPlan.ENTERPRISE: PlanPricing(
        plan=SubscriptionPlan.ENTERPRISE,
        monthly_price=Decimal("99.99"),
        annual_price=Decimal("999.00"),
        max_users=100,
        features=["basic_access", "email_support", "api_access",
                   "priority_support", "advanced_analytics",
                   "custom_integrations", "sla"],
    ),
}

def get_price(plan: SubscriptionPlan, billing_cycle: str) -> Decimal:
    pricing = PRICING[plan]
    if billing_cycle == "annual":
        return pricing.annual_price
    return pricing.monthly_price

def calculate_proration(
    old_plan: SubscriptionPlan,
    new_plan: SubscriptionPlan,
    days_remaining: int,
    billing_cycle: str,
) -> Decimal:
    old_daily = get_price(old_plan, billing_cycle) / Decimal("30")
    new_daily = get_price(new_plan, billing_cycle) / Decimal("30")
    difference = new_daily - old_daily
    return (difference * Decimal(str(days_remaining))).quantize(Decimal("0.01"))
Calibración de pricing_service.py:
├── Tipo: Lógica de negocio financiera → Confianza base: 25%
├── Ajustes:
│   ├── -10%: Los precios son inventados (no los de MI negocio)
│   ├── -5%:  Cálculos de prorrateo son complejos
│   ├── +5%:  Usa Decimal correctamente
│   └── -10%: No hay tests
├── Confianza final: 5%
├── Profundidad: Revisión línea por línea (15-20 min)
└── Qué verifico:
    ├── ⚠️ Precios son placeholder — DEBO reemplazar con los reales
    ├── ⚠️ Prorrateo asume 30 días por mes (no correcto para todos los meses)
    ├── ⚠️ ¿Qué pasa con downgrade? difference sería negativa → ¿refund?
    ├── ⚠️ features son strings — deberían ser Enum para validación
    ├── ⚠️ No maneja el caso de annual billing con prorrateo
    │   (¿divide entre 30 o entre 365?)
    └── → NEEDS EDIT — los cálculos financieros necesitan corrección

Archivo 3: subscription_service.py

from datetime import datetime, timedelta
from typing import Optional
from models import Subscription, SubscriptionCreate, SubscriptionPlan
from pricing_service import get_price, calculate_proration
import uuid

subscriptions_db: dict = {}

class SubscriptionService:
    def create(self, user_id: str, data: SubscriptionCreate) -> Subscription:
        if any(
            s.user_id == user_id and s.status == "active"
            for s in subscriptions_db.values()
        ):
            raise ValueError("User already has an active subscription")

        now = datetime.utcnow()
        period_days = 365 if data.billing_cycle == "annual" else 30

        sub = Subscription(
            id=str(uuid.uuid4()),
            user_id=user_id,
            plan=data.plan,
            billing_cycle=data.billing_cycle,
            current_period_start=now,
            current_period_end=now + timedelta(days=period_days),
            created_at=now,
        )
        subscriptions_db[sub.id] = sub
        return sub

    def cancel(self, subscription_id: str) -> Subscription:
        sub = subscriptions_db.get(subscription_id)
        if not sub:
            raise ValueError("Subscription not found")
        sub.status = "cancelled"
        return sub

    def upgrade(
        self, subscription_id: str, new_plan: SubscriptionPlan
    ) -> dict:
        sub = subscriptions_db.get(subscription_id)
        if not sub:
            raise ValueError("Subscription not found")

        days_remaining = (sub.current_period_end - datetime.utcnow()).days
        proration = calculate_proration(
            sub.plan, new_plan, days_remaining, sub.billing_cycle,
        )

        sub.plan = new_plan
        return {
            "subscription": sub,
            "proration_charge": float(proration),
        }
Calibración de subscription_service.py:
├── Tipo: Lógica de negocio → Confianza base: 30%
├── Ajustes:
│   ├── -10%: Depende de pricing_service (que tiene issues)
│   ├── -5%:  Lógica de upgrade/cancel tiene implicaciones financieras
│   ├── -10%: No hay tests
│   └── +5%:  Estructura clara y legible
├── Confianza final: 10%
├── Profundidad: Línea por línea (20+ min)
└── Qué verifico:
    ├── ⚠️ cancel() no hace refund ni calcula periodo restante
    ├── ⚠️ upgrade() cobra prorrateo pero no registra el cargo
    ├── ⚠️ No hay downgrade (solo upgrade)
    ├── ⚠️ No verifica que new_plan sea diferente de current plan
    ├── ⚠️ In-memory storage — necesita DB real
    ├── ⚠️ proration_charge se convierte a float (pierde precision)
    └── → NEEDS SIGNIFICANT EDIT

Resumen de calibración del módulo:

Archivo               | Confianza | Decisión
----------------------|-----------|------------------
models.py             |    85%    | Acepta
pricing_service.py    |     5%    | Editar significativamente
subscription_service.py|    10%    | Editar significativamente
routes.py (no mostrado)|   45%    | Editar después de fixes

La calibración te dice exactamente dónde invertir tu tiempo: casi nada en models.py, casi todo en pricing y subscription.


La Diferencia entre Calibración Correcta e Incorrecta

Caso 1: Over-calibration (confías de más)

Tarea: Generar función de validación de contraseña
Tu calibración: 70% ("es una función simple")

Lo que pasó:
- La función solo validaba longitud mínima
- No verificaba caracteres especiales
- No prevenía contraseñas comunes (password123)
- No tenía protección contra timing attacks

Calibración correcta: 20-30%
- Es una función de seguridad
- Tiene implicaciones de compliance
- Requiere conocimiento específico de best practices

Error: Confundiste "simple de leer" con "bajo riesgo"

Caso 2: Under-calibration (desconfías de más)

Tarea: Generar modelos Pydantic para un blog
Tu calibración: 25% ("no confío en AI")
Tiempo invertido: 30 minutos revisando 40 líneas de modelos

Lo que encontraste:
- Todo estaba correcto
- Campos razonables
- Tipos correctos
- Validaciones presentes

Calibración correcta: 75-85%
- Modelos de datos simples
- Patrón estándar
- Bajo riesgo
- 3 minutos de revisión habrían sido suficientes

Error: Gastaste 27 minutos extra sin encontrar nada

Caso 3: Calibración correcta

Tarea: Generar endpoint de webhook para procesar pagos de Stripe
Tu calibración: 15%
Tiempo invertido: 25 minutos

Lo que encontraste:
- No verificaba la firma del webhook (crítico)
- No manejaba eventos duplicados (idempotency)
- Hardcodeaba el webhook secret
- No tenía retry logic para procesamiento fallido

Resultado: Encontraste 4 issues críticos en 25 minutos.
Sin tu revisión exhaustiva, cualquiera de estos issues
podría haber causado un incidente en producción.

Calibración correcta: Sí. 15% para payment webhooks.

Conexión con Proyecto

Cómo usarás Trust Calibration en el Módulo 8

En el proyecto integrador recibirás un codebase con múltiples módulos. Tu tabla de calibración te guía:

  1. Antes de empezar: Clasifica cada archivo del codebase por tipo de tarea y asigna confianza base.
  2. Durante la revisión: Ajusta confianza por factores contextuales. ¿Hay tests? ¿Conoces el dominio?
  3. Priorización: Empieza por los archivos con calibración más baja (mayor riesgo). Si tienes 60 minutos para la revisión, gasta 40 en los archivos de 10-20% de confianza y 20 en los demás.
  4. Documentación: Para cada módulo revisado, documenta tu calibración, lo que encontraste, y si tu calibración fue correcta.

Troubleshooting

Problema 1: "Mi tabla no cubre todos mis casos"

Causa: La tabla de 15 tipos es un punto de partida, no exhaustiva. Solución: Agrega filas a tu tabla según tu contexto. Si trabajas con WebSockets frecuentemente, agrega "WebSocket handlers" con la confianza que consideres apropiada. Si trabajas con ML pipelines, agrega esa categoría. La tabla es tuya — personalízala.

Problema 2: "No sé si un factor sube o baja mi confianza"

Causa: Falta de experiencia evaluando factores. Solución: Regla simple: si el factor reduce tu capacidad de detectar errores (no conoces el dominio, no hay tests, el código es complejo) → baja confianza. Si el factor aumenta tu capacidad (conoces el dominio, hay tests, patrón estándar) → sube confianza.

Problema 3: "Mi calibración inicial siempre está equivocada"

Causa: Tu tabla base puede no reflejar tu experiencia con Claude Code específicamente. Solución: Empieza conservador (confianza baja) y sube gradualmente con experiencia. Es mejor invertir tiempo extra al principio que descubrir bugs después. Después de 20-30 experiences, tu tabla será precisa para tu contexto.

Problema 4: "Mi equipo tiene diferentes calibraciones"

Causa: Cada persona tiene diferente experiencia y contexto. Solución: Eso es normal y esperado. Lo importante es que cada persona tenga una calibración explícita, no que todos tengan la misma. En el código compartido (auth, pagos), el equipo debería acordar una calibración mínima: "código de seguridad siempre tiene confianza < 20%, independientemente de quién lo revise."

Problema 5: "No tengo tiempo para llevar un registro de calibración"

Causa: El registro se siente como trabajo extra. Solución: No necesitas un registro formal. Basta con actualizar mentalmente tu tabla: "la última vez que generé SQL con Claude Code, encontré N+1. Mi confianza en queries baja a 35%." Si quieres ser riguroso, un archivo de texto con 5 columnas es suficiente. Toma 30 segundos por entry.


Ejercicios

Ejercicio 1: Calibrar tareas cotidianas (Fácil)

Para cada tarea, asigna confianza base, aplica factores de ajuste, y define profundidad de revisión:

  1. Generar un archivo docker-compose.yml para PostgreSQL + Redis + tu app
  2. Crear una función que parsea fechas en 5 formatos diferentes
  3. Implementar un endpoint que borra la cuenta de un usuario y todos sus datos
  4. Generar type hints para 20 funciones existentes
Ver solución

1. docker-compose.yml

  • Confianza base: 80% (Dockerfiles/CI config)
  • Ajuste: +5% si conoces Docker bien, -5% si hay secrets (passwords de DB)
  • Confianza final: ~80%
  • Revisión: Rápida (2-3 min). Verificar: ports correctos, passwords no hardcoded (usar env vars), versiones de imágenes.

2. Parseo de fechas (5 formatos)

  • Confianza base: 60% (función de utilidad)
  • Ajuste: -10% por complejidad (múltiples formatos = edge cases), -5% por regex implícito
  • Confianza final: ~45%
  • Revisión: Detallada (10-15 min). Verificar: que cubra los 5 formatos, que maneje formatos inválidos, que maneje timezones si aplica, probar con inputs edge case.

3. Delete de cuenta y datos

  • Confianza base: 25% (operación destructiva + compliance)
  • Ajuste: -10% si hay regulaciones (GDPR), -10% sin tests, -5% por side effects (borrar en múltiples tablas)
  • Confianza final: ~0-5%
  • Revisión: Línea por línea (25-35 min). Verificar: que borre TODO (no deje datos huérfanos), que sea transaccional, que requiera confirmación, que tenga auth, que haga logging, GDPR compliance si aplica.

4. Type hints para funciones existentes

  • Confianza base: 85% (documentación/boilerplate)
  • Ajuste: +5% si las funciones son simples, -5% si las funciones tienen lógica compleja que Claude Code podría malinterpretar
  • Confianza final: ~85%
  • Revisión: Visual rápida (3-5 min). Verificar: que los tipos sean correctos (especialmente return types y Optional), que no introduzca errores de mypy.

Ejercicio 2: Encontrar calibración incorrecta (Medio)

Un developer tiene esta tabla de calibración. Encuentra los errores:

Mi tabla de calibración:
1. Endpoints REST     → 80%  (son siempre iguales)
2. SQL queries        → 70%  (SQL es simple)
3. Auth middleware     → 60%  (ya lo he hecho antes)
4. README.md          → 30%  (no confío en la info)
5. Regex validation   → 75%  (expresiones cortas)
6. Payment processing → 50%  (es solo math)
Ver solución

Errores en la calibración:

  1. Endpoints REST (80%): Demasiado alto como generalización. Un endpoint de CRUD puede ser 70%, pero un endpoint que maneja permisos o datos sensibles debería ser 30-40%. La justificación "son siempre iguales" ignora que los endpoints varían enormemente en riesgo.

  2. SQL queries (70%): Peligrosamente alto. SQL tiene riesgo de injection, N+1, y lógica incorrecta. Debería ser 40-55%. La justificación "SQL es simple" es una trampa — SQL parece simple pero tiene trampas sutiles.

  3. Auth middleware (60%): Muy alto para seguridad. Auth debería estar en 10-20% siempre. "Ya lo he hecho antes" sube tu familiaridad (+5-10%) pero no lo suficiente para compensar que es código de seguridad.

  4. README.md (30%): Muy bajo. Documentación tiene riesgo bajo. 85-90% es apropiado. La preocupación de "info incorrecta" es válida pero se resuelve con una revisión de 2 minutos, no 15.

  5. Regex validation (75%): Muy alto. Regex es una de las áreas donde AI es más impredecible. 15-25% es más apropiado. "Expresiones cortas" no reduce el riesgo — una regex de 10 caracteres puede tener catastrophic backtracking.

  6. Payment processing (50%): Muy alto. Procesamiento financiero debería ser 10-20%. "Es solo math" ignora precision (float vs Decimal), compliance, edge cases de monedas, rounding, y el impacto de un error (pérdida financiera directa).

Patrón: Este developer calibra basándose en percepción de dificultad ("es simple", "son cortas") en vez de en impacto de error. Resultado: sobre-confía en código de alto riesgo y sub-confía en código de bajo riesgo.

Ejercicio 3: Calibrar un output real (Medio)

Claude Code generó esta función. Calibra: tipo de tarea, confianza base, factores de ajuste, confianza final, y profundidad de revisión. Después, revisa según tu calibración.

from datetime import datetime, timedelta
from typing import Optional
import jwt
import os

SECRET = os.getenv("JWT_SECRET")
ALGORITHM = "HS256"

def create_reset_token(user_email: str, expires_in: int = 3600) -> str:
    payload = {
        "sub": user_email,
        "type": "password_reset",
        "exp": datetime.utcnow() + timedelta(seconds=expires_in),
        "iat": datetime.utcnow(),
    }
    return jwt.encode(payload, SECRET, algorithm=ALGORITHM)

def verify_reset_token(token: str) -> Optional[str]:
    try:
        payload = jwt.decode(token, SECRET, algorithms=[ALGORITHM])
        if payload.get("type") != "password_reset":
            return None
        return payload.get("sub")
    except jwt.ExpiredSignatureError:
        return None
    except jwt.InvalidTokenError:
        return None

def reset_password(token: str, new_password: str) -> bool:
    email = verify_reset_token(token)
    if not email:
        return False

    # Update password in database
    from database import get_user_by_email, update_user_password
    user = get_user_by_email(email)
    if not user:
        return False

    update_user_password(user.id, new_password)
    return True
Ver solución

Calibración:

  • Tipo de tarea: Auth/Security (password reset) → Confianza base: 15%
  • Factores:
    • -10%: Token-based auth con implicaciones de seguridad
    • -5%: No hay tests
    • +5%: Código relativamente corto y legible
    • -5%: Import circular en reset_password (from database import...)
  • Confianza final: 0% (mínimo práctico: tratar como desconfianza total)
  • Profundidad: Línea por línea + verificar contra docs

Revisión línea por línea:

  1. ✅ SECRET = os.getenv("JWT_SECRET") — Sin fallback, bien. Pero si JWT_SECRET no está seteado, SECRET es None → jwt.encode fallará con error críptico. Debería validar que SECRET existe al startup.

  2. ⚠️ expires_in: int = 3600 — 1 hora para reset token. ¿Es apropiado? La mayoría de servicios usan 15-30 minutos. 1 hora es generoso para un atacante.

  3. ⚠️ verify_reset_token — Retorna None para cualquier error. No distingue entre token expirado (le dices al usuario "tu link expiró, pide uno nuevo") y token inválido (posible ataque). El UX y la seguridad se beneficiarían de distinguir estos casos.

  4. ⚠️ reset_password — No hashea new_password. Llama update_user_password(user.id, new_password) con la password en texto plano. Si update_user_password no hashea internamente, la password se guarda en texto plano en la base de datos. Issue CRÍTICO.

  5. ⚠️ reset_password — No invalida el token después de usarlo. Un token de reset puede usarse múltiples veces hasta que expire. Esto permite a un atacante que intercepte el token cambiar la password múltiples veces.

  6. ⚠️ Import circular — from database import... dentro de la función. Funciona pero es un code smell que puede causar problemas.

  7. ⚠️ No hay rate limiting — Un atacante puede intentar miles de tokens por fuerza bruta.

  8. ⚠️ No hay validación de complejidad de new_password — La nueva contraseña puede ser "1".

Decisión: RECHAZAR Y REGENERAR. Los issues 4 (no hashea password) y 5 (no invalida token) son deal-breakers de seguridad. La función tiene la forma correcta pero falla en los detalles que importan.

Ejercicio 4: Construir tu tabla personalizada (Difícil)

Crea tu propia tabla de Trust Calibration con al menos 10 tipos de tarea relevantes para tu trabajo. Para cada una:

  1. Tipo de tarea
  2. Confianza base (%)
  3. Top 3 cosas que verificar
  4. Un factor que sube tu confianza
  5. Un factor que baja tu confianza
Ver solución

No hay respuesta única. Tu tabla debería cumplir estos criterios:

  • ✅ Tiene al menos 3 niveles de confianza distintos (no todo en 50%)
  • ✅ Código de seguridad está en 10-25%
  • ✅ Boilerplate y docs están en 75-90%
  • ✅ Lógica de negocio está en 25-40%
  • ✅ Cada entrada tiene "qué verificar" específico (no solo "revisar")
  • ✅ Los factores de ajuste son concretos, no vagos

Ejemplo para un backend developer en SaaS:

Tipo de tareaConfianzaTop 3 verificacionesSube si...Baja si...
Modelos de datos80%Campos, tipos, validacionesDominio familiarRelaciones complejas
CRUD endpoints65%Validaciones, auth, status codesTests existenDatos sensibles
Auth/JWT15%Cada línea, contra docs, testsLibrería maduraCustom implementation
SQL queries45%Injection, N+1, lógicaORM usado bienRaw SQL
Background jobs40%Retry logic, idempotency, errorsPatrón estándarState complejo
WebSocket handlers35%Connection management, auth, memory leaksDominio familiarConcurrencia
Email templates80%Contenido correcto, variablesTexto simpleHTML complejo
API integrations35%Error handling, retry, API correctaAPI bien documentadaAPI cambió reciente
Config files85%Secrets no hardcoded, valoresSetup estándarMulti-environment
Migrations30%Reversibilidad, data loss, locksSchema simpleDatos existentes

Resumen

En esta cápsula aprendiste:

  • Trust Calibration convierte "creo que está bien" en un proceso estructurado con confianza cuantificada por tipo de tarea
  • La tabla de 15 tipos de tarea te da un punto de partida concreto para calibrar tu confianza
  • Factores de ajuste suben o bajan tu confianza base: tests, familiaridad, complejidad, seguridad, track record
  • Trust Debt se acumula cuando confías de más — los problemas no desaparecen, se acumulan silenciosamente
  • Tu tabla de calibración se actualiza con experiencia — empieza conservador y ajusta con datos reales
  • La calibración correcta invierte tiempo proporcional al riesgo: 30 minutos en auth, 2 minutos en modelos
  • Over-calibration (confiar de más) y under-calibration (desconfiar de más) son ambos costosos

Próxima cápsula: Ejercicio integrador — aplicar los 3 mental models juntos a escenarios reales con código.


Recursos Adicionales

  1. Thinking in Bets — Annie Duke - Calibración de confianza y toma de decisiones bajo incertidumbre
  2. Superforecasting — Philip Tetlock - Cómo los mejores pronosticadores calibran su confianza
  3. Google — Code Review Developer Guide - Cómo Google prioriza por riesgo en code review
  4. OWASP — Risk Rating Methodology - Framework de evaluación de riesgo para seguridad
  5. Anthropic — Claude Code Documentation - Documentación oficial de Claude Code
  6. Risk-Based Testing — ISTQB - Principios de testing basado en riesgo aplicables a calibración de confianza

Debugging & Code Review with Claude Code — Módulo 2, Cápsula 04 Claude Code Agentic Development Path — Guía #6 de 11