DEV Community

Cover image for Seguridad en APIs REST: Supabase vs API propia
Fernando Gallardo
Fernando Gallardo

Posted on

Seguridad en APIs REST: Supabase vs API propia

Cuando hablamos de seguridad en APIs REST, la mayoría de las conversaciones asumen que hay un servidor en medio validando cada request. Con Supabase eso no siempre es cierto: por debajo corre PostgREST, que introspecciona tu esquema de Postgres y genera automáticamente un endpoint por cada tabla. El cliente, tu frontend/app móvil, habla casi directo con la base de datos. Es un modelo distinto al de una API REST tradicional, y el modelo de amenazas también cambia por completo. Esto es lo que hemos visto al auditar ambos.

Dos formas de exponer datos

En una API tradicional, tú escribes y el servidor recibe el request, aplica lógica de negocio, valida, y solo entonces toca la base de datos con queries que tú controlas. El cliente nunca ve la estructura de tus tablas.

Con Supabase, la tabla es el endpoint. No hay una capa intermedia que te obligue a pensar “¿quién puede ver esto y por qué?” para cada operación, esa responsabilidad se mueve completa a las políticas de Row Level Security (RLS) de Postgres.

Row Level Security: dónde vive (y dónde se rompe) la seguridad

RLS funciona escribiendo políticas SQL por tabla que determinan qué filas puede leer o escribir cada usuario, normalmente basadas en el JWT que Supabase valida (auth.uid(), claims, roles).

El problema no es el mecanismo, es que centraliza todo el modelo de permisos en un solo lugar que es fácil de olvidar. Una tabla sin política, o una política mal escrita (USING (true) por accidente, o una condición que no cubre todos los casos), expone la tabla completa sin que haya un “endpoint” visible que alguien tuvo que decidir crear. El bug no está en un archivo de rutas que puedas grepear, está en el catálogo de Postgres.

Lo que la API tradicional resuelve mejor

Ciertas reglas de negocio son difíciles de expresar de forma segura solo en SQL declarativo: “solo se puede cancelar un pedido si pasaron menos de 24 horas, el usuario es el dueño, y el estado sigue siendo pendiente” es trivial en código imperativo y más frágil en RLS, donde termina viviendo en funciones SECURITY DEFINER, que si están mal escritas, escalan privilegios en vez de limitarlos.

Con una API propia, también controlas completamente qué modelo de datos expone el cliente. Con PostgREST, tu esquema de tablas, columnas y relaciones es en buena medida inferible desde afuera.

Supabase/PostgREST API REST propia
Dónde vive la autorización Políticas RLS en SQL Código del servidor
Superficie de ataque típica Esquema de base de datos completo Endpoints definidos explícitamente
Velocidad de desarrollo Alta — CRUD casi gratis Depende del scaffolding propio
Lógica de negocio compleja Difícil de expresar de forma segura Natural en código imperativo
Error más común Política RLS ausente o mal escrita Falta de validación en algún endpoint

El patrón que más se repite en auditorías

En nuestra experiencia analizando proyectos con Supabase, el hallazgo más frecuente no es sofisticado: una tabla nueva se crea durante desarrollo, RLS se deja deshabilitado “temporalmente” para probar algo rápido, y nadie vuelve a habilitarlo antes de producción. Es el equivalente moderno de un IDOR clásico, pero a nivel de tabla completa en vez de un solo endpoint y por eso una plataforma de seguridad de código que analice el esquema completo del proyecto, no solo el diff de un PR, atrapa este tipo de casos antes de que lleguen a producción.

Cuál elegir según el contexto

Ninguno de los dos modelos es “más seguro” en abstracto, son superficies de ataque distintas que exigen disciplina distinta. Supabase tiene sentido para MVPs, productos con modelos de permisos relativamente simples (multi-tenant por user_id, por ejemplo), o equipos que priorizan velocidad. Una API propia tiene sentido cuando la lógica de autorización es compleja, cuando necesitas ocultar tu modelo de datos interno, o cuando integras sistemas externos que no encajan bien en el modelo CRUD.

Lo que no cambia es la pregunta que hay que hacerse en cualquiera de los dos casos: ¿quién puede tocar qué, y quién revisó esa regla la última vez? Si tu equipo trabaja con Supabase, vale la pena auditar tus políticas RLS con la misma rigurosidad con la que revisarías el código de un endpoint escrito a mano, herramientas como Ixtli pueden ayudarte a detectar ese tipo de huecos de autorización como parte del análisis de vulnerabilidades en cada pull request, antes de que una tabla sin política llegue a main.

Top comments (0)