marbuilds / recursosCuaderno de seguridad / edición web 1.0 / septiembre 2026

Antes de lanzar
tu app.

25 controles para pasar de «parece que funciona» a una revisión con evidencia.

Aprende qué revisar, dónde mirar y cómo decidir si un punto está resuelto.

Para quienes construyen apps web y móviles. qué mirar, cómo intentar romperlo y qué evidencia aceptaría antes de marcarlo.

25 controles

01Datos

RLS en las tablas expuestas

evita que una tabla expuesta ignore los límites entre usuarios
Pendiente

Cuándo aplicaSupabase/Postgres expuesto

Qué estás comprobandoLas tablas accesibles desde la Data API tienen RLS y políticas explícitas para las operaciones permitidas. Una tabla que nunca se expone puede usar otro límite de acceso.

Prueba rápida

Crea dos cuentas de prueba. Con una crea un registro. Intenta leerlo, modificarlo y borrarlo usando la otra.

Pasa si

La segunda cuenta no puede acceder ni alterar el registro, y las operaciones legítimas de la primera siguen funcionando.

Si usas Supabase o Expo

Activar RLS sin políticas no configura permisos: deja la tabla cerrada para la clave publishable. Revisa también vistas y funciones, que pueden saltarse lo que esperas.

Detalle técnico

Inventario de tablas expuestas y de sus políticas, una por operación:

select schemaname, tablename, rowsecurity
from pg_tables
where schemaname in ('public')
order by tablename;

select schemaname, tablename, policyname, cmd, roles, qual, with_check
from pg_policies
where schemaname in ('public')
order by tablename, cmd, policyname;

Adapta la lista de esquemas a los que expone tu API. Después repite las pruebas como anónimo y como usuario autenticado para las cuatro operaciones.

Evidencia que acepto: inventario completo, políticas por operación y tests que demuestren lo permitido y lo denegado.

02Datos

Regla de acceso explícita por registro

que te llegue un id no convierte ese objeto en tuyo
Pendiente

Cuándo aplicaWeb y móvil

Qué estás comprobandoCada registro tiene una regla de quién puede leerlo, cambiarlo o borrarlo. La regla puede ser un propietario, un equipo, un tenant, un rol o una relación compartida.

Prueba rápida

Con la cuenta B, repite todas las operaciones que acepten el id de un objeto de A: leer, editar, borrar, descargar, subir un archivo asociado y compartir.

Pasa si

B recibe una respuesta segura y el objeto de A no cambia.

Detalle técnico

Un UUID impredecible ayuda contra la enumeración, pero no es autorización: si el id se filtra en un listado, en un log o en una URL, el control tiene que seguir en pie.

Repite la prueba con ids obtenidos de listados, logs y URLs, no solo con los que te devuelve tu propia interfaz.

Evidencia que acepto: tests negativos por objeto y operación.

03Datos

El cliente solo escribe los campos permitidos

esconder un campo en la interfaz no impide enviarlo
Pendiente

Cuándo aplicaWeb y móvil

Qué estás comprobandoEl servidor construye la escritura desde una lista de campos permitidos. Campos como role, owner_id, is_pro, credits, precios o estados internos se calculan o autorizan en el servidor.

Prueba rápida

Intercepta una petición legítima y añade campos sensibles o desconocidos. Prueba también null, arrays, objetos anidados y nombres alternativos.

Pasa si

El servidor ignora o rechaza esos campos de forma deliberada, y el registro no cambia.

Detalle técnico

Es mass assignment, hoy dentro de API3:2023. El síntoma clásico es un PATCH que acepta cualquier propiedad que le llegue.

Evidencia que acepto: esquema de entrada explícito y un test que demuestre que una propiedad no autorizada no modifica el registro.

Consulta la fuente

OWASP API3:2023
04Datos

Cada respuesta devuelve solo lo necesario

lo que no sale en pantalla sigue estando en la respuesta
Pendiente

Cuándo aplicaWeb y móvil

Qué estás comprobandoLa autorización también existe al leer propiedades. La API devuelve los campos que hacen falta, no la fila entera para que el cliente esconda el resto.

Prueba rápida

Guarda la respuesta real de cada rol y compárala con el contrato de salida que esperas. Mira REST, GraphQL, exports, analytics, notificaciones y errores.

Pasa si

Ninguna respuesta incluye email, flags internos, tokens o metadatos que ese rol no debería ver.

Detalle técnico

Evidencia que acepto: esquema de respuesta por endpoint y tests que fallen si aparece una propiedad no permitida.

Consulta la fuente

OWASP API3:2023
05Secretos

La clave pública puede ir en el cliente; la secreta no

una clave diseñada para distribuirse no es un secreto
Pendiente

Cuándo aplicaWeb y móvil

Qué estás comprobandoUna clave publishable o pública vive en el cliente porque no concede privilegios por sí sola. Una clave secreta, o con capacidad de saltarse controles, vive solo en infraestructura que controlas.

Prueba rápida

Inventaria las claves por proveedor y clasifícalas con su documentación. Busca nombres de claves privilegiadas en código cliente, configuración nativa, builds, logs y source maps.

Pasa si

Ninguna credencial privilegiada aparece en un artefacto que recibe el usuario.

Si usas Supabase o Expo

En Supabase, lo que protege al cliente es Auth, RLS y la autorización por objeto, no esconder la clave publishable.

Detalle técnico

No pegues valores reales en comandos compartidos ni en capturas.

Evidencia que acepto: inventario con tipo, alcance, ubicación, propietario y fecha de rotación.

Consulta la fuente

Supabase · API keys
06Secretos

Todo lo compilado en el cliente se considera público

un .env no vuelve secreto lo que el bundler mete dentro de la app
Pendiente

Cuándo aplicaWeb y móvil

Qué estás comprobandoUn .env evita hardcodear configuración. No convierte en secreto un valor que acaba compilado en lo que descarga el usuario.

Prueba rápida

Busca las variables públicas en el código y revisa también el build, no solo los archivos versionados.

Pasa si

Ninguna operación privilegiada depende de una credencial que viaja al cliente.

Si usas Supabase o Expo

Expo lo documenta con todas las letras: las variables EXPO_PUBLIC_ quedan visibles en texto plano en la aplicación compilada.

Detalle técnico
rg -n "EXPO_PUBLIC_|NEXT_PUBLIC_|VITE_" . \
  -g '!node_modules' -g '!dist' -g '!build'

Clasifica cada resultado: una URL o una clave pensada para ser pública puede estar bien ahí. Si una operación necesita un secreto, lo que se mueve al servidor es la operación, no solo la clave.

Evidencia que acepto: revisión del build final.

07Secretos

Una credencial filtrada se revoca o rota primero

borrarla en un commit no la borra del historial
Pendiente

Cuándo aplicaWeb y móvil

Qué estás comprobandoReescribir el historial no invalida una credencial. Primero le quitas la capacidad de acceder desde el proveedor. Después decides si hace falta limpiar el historial.

Prueba rápida

Comprueba en el proveedor que la credencial antigua ya no autentica. Después busca el patrón en el historial, en las ramas y en los tags.

Pasa si

La credencial vieja no autentica, la nueva está desplegada, y la decisión sobre limpiar el historial está escrita.

Detalle técnico
git log --all --oneline --decorate
git log --all -S 'NOMBRE_O_FRAGMENTO_NO_SENSIBLE' --oneline

GitHub lo dice en ese orden: revocar o rotar es el primer paso, y una vez hecho, reescribir el historial puede no ser necesario. Si el secreto siguió expuesto en clones, forks o vistas cacheadas, eso ya no lo arregla un rebase.

No publiques el valor mientras lo buscas.

08Identidad

Cada endpoint no público autentica y autoriza

autenticar dice quién eres; autorizar dice si puedes hacer esto
Pendiente

Cuándo aplicaWeb y móvil

Qué estás comprobandoPara cualquier recurso que no sea público, el servidor identifica al que llama y comprueba si puede ejecutar esa acción sobre ese recurso.

Prueba rápida

Prueba cada ruta sin credencial, con una inválida, con una expirada, con la de otro usuario y con un rol insuficiente.

Pasa si

Sin credenciales válidas devuelve 401. Con credenciales válidas pero permisos insuficientes devuelve 403 o, si se ha decidido ocultar la existencia del recurso, 404. En ningún caso entrega datos ni ejecuta la acción.

Detalle técnico

No todos los endpoints llevan login: uno puede ser público a propósito, un webhook verifica una firma, un cron usa un secreto o una identidad de servicio, y un enlace compartido usa un token limitado. Lo que no puede haber es una ruta sin política intencional.

Evidencia que acepto: una matriz de endpoint por actor y acción, con tests negativos automatizados.

09Identidad

La sesión no vive donde la lee cualquier script

la respuesta correcta depende de la superficie, no hay una receta única
Pendiente

Cuándo aplicaWeb y móvil

Qué estás comprobandoDónde guardas el token decide quién puede leerlo si te entra un XSS. En web, localStorage es accesible desde el JavaScript del mismo origen.

Prueba rápida

En web, inspecciona almacenamiento y cookies, y prueba logout, expiración, refresh y revocación. En móvil, revisa la implementación real de almacenamiento y la política de backup.

Pasa si

En web, el token de sesión no queda disponible para JavaScript cuando la arquitectura usa una cookie HttpOnly. El logout revoca la sesión o impide su renovación, el access token expira según una política documentada y refresh, expiración y revocación se comportan como esperas.

Detalle técnico

En web: cookie con HttpOnly, Secure y el SameSite que corresponda. HttpOnly evita leerla desde JavaScript, pero el navegador la sigue enviando, así que aparece CSRF.

En móvil: Keychain en iOS o Keystore en Android, a través de una abstracción segura, y decidiendo si entra en el backup.

Evidencia que acepto: la ubicación documentada y los tests de ciclo de vida, sin tokens impresos en logs.

10Identidad

Las contraseñas están delegadas o bien almacenadas

si las guardas tú, el algoritmo importa
Pendiente

Cuándo aplicaWeb y móvil

Qué estás comprobandoO delegas las credenciales en un proveedor de identidad, y entonces no guardas copia, o las almacenas con un algoritmo de password hashing.

Prueba rápida

Identifica quién recibe y guarda la contraseña. Si es tu servidor, revisa algoritmo, parámetros, salt, migración de hashes antiguos y que no aparezca en logs.

Pasa si

Ninguna contraseña se guarda en claro ni cifrada de forma reversible, y los flujos de cambio y recuperación funcionan.

Detalle técnico

OWASP pone Argon2id primero, con parámetros mínimos que conviene revisar cada cierto tiempo, después scrypt, y bcrypt solo para lo heredado, con su límite de 72 bytes.

Si usas un proveedor, lo correcto es precisamente no hashear tú nada.

Consulta la fuente

OWASP · Password Storage
11Identidad

Hay segundo factor donde el riesgo lo pide

no para todo el mundo en todo momento: para lo que duele
Pendiente

Cuándo aplicaSegún riesgo

Qué estás comprobandoEl segundo factor está disponible y se exige en cuentas privilegiadas y operaciones de alto impacto según el riesgo. La recuperación de cuenta tiene controles propios y no permite saltarse el segundo factor sin una verificación equivalente.

Prueba rápida

Enumera las operaciones de alto impacto y define cuándo pides reautenticación o step-up. Prueba el alta, la pérdida y sustitución del factor, los códigos de recuperación y los intentos de convertir la recuperación en un bypass.

Pasa si

Una sesión antigua o débil no ejecuta una acción que exige step-up.

Detalle técnico

Un proveedor social puede aplicar sus propios factores, y aun así tu app sigue teniendo que proteger los cambios de identidad y de sesión.

Evidencia que acepto: la política escrita por riesgo y la prueba de que el step-up se aplica de verdad.

12Entradas y salidas

La validación que protege vive en el servidor

la del cliente es experiencia de uso, no un control
Pendiente

Cuándo aplicaWeb y móvil

Qué estás comprobandoEl servidor valida estructura, tipo, longitud, rango, formato y reglas de negocio. Una lista de lo permitido suele ser más segura que intentar enumerar lo malo.

Prueba rápida

Manda directamente valores fuera de rango, tipos incorrectos, campos extra, Unicode raro, payloads grandes y estados imposibles. Hazlo contra staging.

Pasa si

Devuelve un error controlado y no deja el registro a medias.

Detalle técnico

Validar no previene XSS por sí solo: eso es el punto 14, y son cosas distintas que se usan juntas.

Evidencia que acepto: el esquema ejecutándose en el límite de confianza y tests negativos.

Consulta la fuente

OWASP · Input Validation
13Entradas y salidas

Consultas parametrizadas, y allowlist para lo que no se parametriza

los nombres de tabla y columna no aceptan parámetros
Pendiente

Cuándo aplicaWeb y móvil

Qué estás comprobandoLos valores viajan como parámetros preparados. El nombre de tabla, el de columna y el orden no se parametrizan, así que salen del input o se mapean desde una lista fija.

Prueba rápida

Busca SQL dinámico, template strings y EXECUTE, y revisa cada concatenación a mano. Prueba comillas y operadores en staging.

Pasa si

Ninguna consulta construye SQL con texto que venga del usuario.

Detalle técnico
rg -n "EXECUTE|query\(|raw\(|SELECT .*\$\{|ORDER BY.*\$\{" . \
  -g '!node_modules'

La búsqueda da candidatos, no un veredicto: cada resultado se mira.

Evidencia que acepto: consultas parametrizadas o mapeo explícito de identificadores, más tests de inyección.

14Entradas y salidas

La protección va en el lugar exacto donde usas el dato

validación, encoding, sanitización y safe sinks no son lo mismo
Pendiente

Cuándo aplicaWeb y móvil

Qué estás comprobandoCada destino tiene su defensa. Texto en HTML, un atributo, una URL o HTML permitido no se protegen igual, y usar la protección del destino equivocado abre el agujero.

Prueba rápida

Haz inventario de dónde se pinta contenido del usuario y prueba cada sitio con un payload inocuo que te diga si se interpreta como código o como texto.

Pasa si

El payload aparece como texto, no se ejecuta, y el HTML que sí permites pasa por sanitización.

Detalle técnico

Como mapa rápido: texto en HTML va con textContent; un atributo inocuo y fijo, con binding seguro o setAttribute; un parámetro de URL, validando el destino y codificando el parámetro; y el HTML que aceptas a propósito, sanitizado.

En React o React Native el framework ya codifica en la mayoría de sitios. El riesgo real está en dangerouslySetInnerHTML, en innerHTML y en el WebView.

Hay contextos que es mejor no usar aunque sepas codificarlos, como meter datos del usuario dentro de JavaScript en línea.

Consulta la fuente

OWASP · XSS Prevention
15Entradas y salidas

La URL que pega el usuario se valida antes de cada acceso

y otra vez en cada redirección, no solo la primera
Pendiente

Cuándo aplicaSi aceptas URLs

Qué estás comprobandoSi tu servidor abre una URL que elige el usuario, hay riesgo de SSRF. Se comprueba el esquema, el destino y la IP a la que resuelve.

Prueba rápida

Prueba `localhost`, IPs privadas, formatos raros de IP, credenciales dentro de la URL, un dominio público que resuelve a una IP interna, y cadenas de redirecciones.

Pasa si

Los destinos no permitidos se bloquean después de resolver DNS, la conexión no termina en una IP distinta que no se haya validado y el control completo se repite en cada redirección.

Detalle técnico

Bloquea loopback, rangos privados, link-local y los endpoints de metadatos de tu proveedor de nube salvo que tengas una razón explícita.

Normaliza y comprueba todas las direcciones A y AAAA, incluidos IPv4 e IPv6. Evita que la conexión vuelva a resolver el dominio hacia una IP que no hayas validado: usa una implementación preparada para SSRF o conecta contra la dirección validada preservando correctamente Host y SNI. Desactiva las redirecciones automáticas o repite el control completo en cada salto.

Si el caso de uso lo permite, una allowlist de dominios es más fácil de defender que una lista de bloqueos.

Consulta la fuente

OWASP · SSRF Prevention
16Entradas y salidas

Las subidas tienen varias barreras, no una

el Content-Type lo pone el cliente, así que no prueba nada
Pendiente

Cuándo aplicaSi aceptas archivos

Qué estás comprobandoExtensiones permitidas, tamaño y cantidad limitados, nombre generado por el servidor, almacenamiento separado de la entrega, y autorización tanto al subir como al leer.

Prueba rápida

Prueba doble extensión, un MIME falso, un archivo enorme, un nombre con ../, una colisión de nombre, contenido activo y subir a la carpeta de otra cuenta.

Pasa si

Cada prueba se rechaza o se neutraliza de acuerdo con una política explícita, no permite ejecutar contenido activo, no sobrescribe archivos y nunca concede acceso a la carpeta o los archivos de otra cuenta.

Detalle técnico

OWASP lo dice claro: ninguna técnica basta sola. Valida firma o contenido cuando aplique y escanea archivos de riesgo si tu caso lo pide.

Evidencia que acepto: tests por capa y la comprobación de autorización en la lectura, no solo en la escritura.

Consulta la fuente

OWASP · File Upload
17Coste y acciones

Hay límites en todo lo que cuesta dinero o recursos

por usuario o cliente y por operación, además de por IP
Pendiente

Cuándo aplicaWeb y móvil

Qué estás comprobandoCada operación que consume dinero o recursos tiene un techo en el servidor: IA, emails, OTP, archivos, procesamiento, búsquedas caras y exports.

Prueba rápida

Haz una ráfaga de llamadas a la misma operación con el mismo usuario. Repite con varias cuentas y con concurrencia.

Pasa si

Al pasar el límite responde 429 o degrada de forma segura, y el coste máximo de la ventana está acotado.

Detalle técnico

Rate limiting no es solo peticiones por IP: una IP puede ser un colegio entero y un atacante puede tener mil. El límite útil combina identidad, sesión, dispositivo, tenant y operación.

Evidencia que acepto: un presupuesto por operación y un test que demuestre el techo.

18Coste y acciones

Los flujos automatizables tienen defensa antiabuso

un CAPTCHA es una capa, no la solución
Pendiente

Cuándo aplicaWeb y móvil

Qué estás comprobandoRegistro, OTP, recuperación e invitaciones combinan límites y señales de abuso. Según el riesgo, una petición sospechosa recibe un challenge o una verificación adicional que se valida en el servidor.

Prueba rápida

Intenta automatizar y repetir el flujo. Cuando la política exija un challenge, prueba también a omitirlo y a enviar un token reutilizado, manipulado o caducado.

Pasa si

El abuso repetido se limita y queda registrado. Cuando el riesgo exige un challenge, el servidor rechaza los tokens ausentes, inválidos, reutilizados o caducados sin bloquear innecesariamente a todos los usuarios.

Detalle técnico

Cuando el proveedor lo permita, valida también el hostname, la acción y la vigencia del token.

19Coste y acciones

Un fallo de verificación no concede acceso nuevo

fallar cerrado es no dar nada nuevo, no quitar lo ya concedido
Pendiente

Cuándo aplicaSi tienes pagos

Qué estás comprobandoEl precio, el producto y el estado se validan en el servidor con datos del proveedor. Si no puedes verificar una compra nueva, no la concedes.

Prueba rápida

Simula una respuesta manipulada, un evento duplicado, uno fuera de orden, una firma inválida, un timeout y un replay.

Pasa si

Ningún evento sin verificar crea acceso nuevo, los duplicados no duplican efectos, y un usuario ya verificado conserva lo suyo durante una caída.

Detalle técnico

Para quien ya está verificado, respeta el último estado confirmado y el ciclo del proveedor, incluidos los periodos de gracia. Quitar el acceso porque el verificador no contesta es el error contrario.

Evidencia que acepto: idempotencia y una reconciliación posterior.

20Coste y acciones

La IA no ejecuta acciones de impacto solo porque se lo pidan

un system prompt no es una barrera
Pendiente

Cuándo aplicaSi la IA ejecuta acciones

Qué estás comprobandoEl modelo propone y una capa que controlas valida identidad, permiso, recurso, parámetros y estado antes de ejecutar.

Prueba rápida

Intenta inyección por el prompt, cambiar el id objetivo, repetir una aprobación, ampliar el alcance y ejecutar con un usuario insuficiente.

Pasa si

La capa de ejecución niega la acción aunque el modelo la pida.

Detalle técnico

Las operaciones destructivas, financieras, administrativas o hacia fuera necesitan alcance limitado y, según el riesgo, una confirmación vinculada a la acción exacta. No todo delete necesita un modal.

Evidencia que acepto: autorización en el servidor por acción y recurso, tokens de aprobación de vida corta, idempotencia y traza.

Consulta la fuente

OWASP · AI Agent Security
21Web

CORS restringido, y nada público por accidente

CORS es cosa del navegador: curl no lo obedece
Pendiente

Cuándo aplicaWeb

Qué estás comprobandoCORS decide qué orígenes pueden leer una respuesta desde un navegador. No autentica, y no detiene curl, una app móvil ni una llamada de servidor a servidor.

Prueba rápida

Prueba un origen permitido y uno que no lo esté desde el navegador. Repite la misma llamada con curl. Después prueba el control real sin credenciales y con las de otro usuario.

Pasa si

Los recursos privados niegan el acceso venga la petición de donde venga. Sin credenciales válidas responden 401; con permisos insuficientes, 403 o un 404 deliberado para ocultar la existencia del recurso. CORS permite únicamente los orígenes previstos para cada recurso.

Detalle técnico

Lo que sí es un fallo de esta capa es exponer sin querer un endpoint, un bucket, un panel, una ruta de depuración o un archivo. Un recurso puede ser público a propósito; el problema es el que lo es por descuido.

Revisa buckets y rutas públicas por inventario, no de memoria.

22Web

Cabeceras actuales, no recetas heredadas

hay tres que se quitan, no se ponen
Pendiente

Cuándo aplicaWeb

Qué estás comprobandoConfiguras y pruebas las cabeceras que le sirven a tu superficie: CSP, HSTS, X-Content-Type-Options, Referrer-Policy y las cookies seguras.

Prueba rápida

Mira las cabeceras de la respuesta desplegada, ruta por ruta.

Pasa si

Las cabeceras que esperas están, la CSP no rompe el producto, y las obsoletas no aparecen.

Detalle técnico
curl -sS -D - -o /dev/null https://TU-DOMINIO-DE-STAGING.example

OWASP recomienda no poner X-XSS-Protection o ponerla a 0, y marca Expect-CT y Public-Key-Pins como obsoletas.

Una API que solo devuelve JSON no saca el mismo partido a todas las cabeceras que una página interactiva. Y HSTS solo se valida sobre HTTPS: piensa antes de meter includeSubDomains.

23Operación

Los errores públicos no cuentan nada de dentro

el detalle va al log, no a la respuesta
Pendiente

Cuándo aplicaWeb y móvil

Qué estás comprobandoEl cliente recibe un mensaje y un código estables. El detalle para investigar queda en logs protegidos, correlacionado con un identificador.

Prueba rápida

Provoca errores de validación, de auth, de base de datos, un timeout y un fallo de un proveedor externo. Mira el cuerpo, las cabeceras, la interfaz y los logs.

Pasa si

Ninguna respuesta pública devuelve stack traces, SQL, rutas, secretos ni nombres internos. Los flujos de autenticación y recuperación tampoco revelan si una cuenta existe mediante el mensaje, el código HTTP, el tamaño de la respuesta o diferencias de tiempo evitables.

Detalle técnico

Mira también las diferencias sutiles: un mensaje distinto para "ese email no existe" y para "contraseña incorrecta" es un enumerador de cuentas.

Consulta la fuente

OWASP · Error Handling
24Operación

Los eventos importantes generan logs y alertas probadas

registrar no es alertar
Pendiente

Cuándo aplicaWeb y móvil

Qué estás comprobandoDefines qué eventos registras, con qué severidad y campos, cuánto tiempo, quién los ve, y qué umbral dispara un aviso a alguien que pueda actuar.

Prueba rápida

Genera en staging un evento conocido: varios fallos de autorización seguidos, un pico de uso, una firma inválida o una acción destructiva denegada.

Pasa si

El evento aparece, la alerta llega, y sabes cuánto tardó y a dónde llegó.

Detalle técnico

No registres contraseñas, tokens, claves ni datos personales que no necesites.

Un informe semanal no cuenta como alerta. Y una alerta sin un runbook al lado llega a alguien que no sabe qué hacer con ella.

Consulta la fuente

OWASP · Logging
25Operación

Restauración ensayada y borrado comprobado

son dos comprobaciones distintas y se marcan por separado
Pendiente

Cuándo aplicaWeb y móvil

Qué estás comprobandoTener backups describe una configuración. La evidencia es haber restaurado. Y el borrado se comprueba en todas las superficies donde hay datos.

Prueba rápida

25A: restaura una copia en un entorno aislado siguiendo la documentación de tu proveedor. 25B: crea una cuenta de prueba con datos en todas las superficies, ejecútale el borrado y búscala después por identificadores conocidos.

Pasa si

25A: la copia restaura, los datos cuadran y los flujos críticos funcionan. 25B: los datos que debían suprimirse han desaparecido o han quedado irreversiblemente anonimizados en los sistemas activos. Cualquier dato que se conserve por una obligación o excepción documentada tiene finalidad, acceso y retención limitados. Lo que permanece temporalmente en backups tiene una retención escrita y un procedimiento que evita reintroducirlo al restaurar.

Detalle técnico

25A · Mide RPO y RTO, comprueba integridad y anota qué sistemas no entran en el backup principal: objetos, secretos, proveedores externos. No sobrescribas producción para probarlo.

25B · Documenta cuándo desaparecen los datos de los backups y cómo evitas reintroducir lo borrado si algún día restauras. El derecho de supresión tiene excepciones: no significa borrar cualquier dato en cualquier circunstancia.

Evidencia que acepto: fecha, backup usado, entorno, duración, checks ejecutados y limpieza posterior.

25A · Restauración

25B · Borrado

El estado conjunto se calcula a partir de ambas comprobaciones. Si una falla, queda por corregir; si falta una, queda pendiente.

Si solo tienes 15 minutos

empieza por lo que puede exponer datos, conceder permisos, generar gasto o ejecutar acciones irreversibles:

no es una priorización universal. es una ruta rápida por impacto para una aplicación típica.

Cómo usar esta guía

Para cada punto guarda cuatro cosas: el alcance, la prueba que hiciste, el resultado que esperabas y la evidencia.

Estados: cumple, no cumple, no aplica con el motivo escrito, y sin verificar. "Parece correcto" no es un estado.

No ejecutes pruebas destructivas, de carga o de abuso contra producción ni uses datos de otras personas. Hazlas en staging con fixtures y cuentas que controles. En producción, limita la comprobación a pruebas autorizadas, controladas y no destructivas.

En las fichas, «Comprobado» corresponde a cumple, «Por corregir» a no cumple y «Pendiente» a sin verificar.

esto no certifica que una app sea segura y no sustituye una auditoría o un modelo de amenazas.

no tienes que leerlo entero. empieza por las fichas, marca qué te aplica y abre únicamente los puntos que necesites comprobar.

Lo que esta lista no cubre

Que algo no esté entre los 25 no significa que no importe. Esta lista prioriza lo que cabía en el formato del vídeo. Una revisión completa también puede necesitar:

Fuentes generales

OWASP Top 10:2025

OWASP Cheat Sheet Series

OWASP API Security Top 10:2023

Última revisión: 12 de septiembre de 2026. Adaptación interactiva: 14 de septiembre de 2026. Se conserva el contenido técnico de esa revisión.

un check no se marca porque el archivo exista o porque una herramienta diga "done".

se marca cuando sabes qué intentaste, qué ocurrió y qué evidencia guardaste.