Text-to-SQL en local: consultar tu base de datos en lenguaje naturel
El text-to-SQL con un LLM local te permite hacer una pregunta en francés («¿cuál fue la facturación por región el mes pasado?») y obtener una consulta SQL ejecutable en tu PostgreSQL o MySQL, sin que el esquema ni los datos salgan de tu infraestructura. Esta guía cubre el funcionamiento real: introducir el esquema en el contexto, construir un pipeline Python con Ollama y, sobre todo, establecer las salvaguardas (solo lectura, validación, límites) sin las cuales ningún sistema text-to-SQL puede desplegarse en producción.
#¿Por qué hacer text-to-SQL con un LLM local?
Las soluciones de text to SQL en la nube (asistentes de BI, copilotos de data warehouse) envían tu esquema —nombres de tablas, de columnas y, a veces, muestras de filas— a un servidor de terceros. Para una base de datos de clientes, de recursos humanos o financiera, esto suele ser inaceptable: el esquema por sí solo ya revela la estructura de tu actividad, y las muestras contienen datos personales.
Un LLM local resuelve este problema de raíz: el modelo se ejecuta en tu máquina mediante Ollama, el esquema permanece en la memoria local y la consulta generada se ejecuta sobre tu base de datos sin que ningún byte pase por internet. Además, su uso es gratuito y no depende de ningún límite de tasa de solicitudes de una API.
- Confidencialidad
- El esquema y los datos nunca abandonan tu red, lo que facilita el cumplimiento del RGPD y la protección de los secretos empresariales.
- Coste
- Sin costo por consulta. Un analista de datos puede iterar cientos de veces sin factura.
- Accesibilidad
- Usuarios profesionales que no conocen SQL consultan la base en lenguaje natural.
- Control
- Tú eliges el modelo, el prompt y las medidas de protección: no hay una caja negra remota.
#¿Cómo funciona concretamente?
Esta guía te lleva al modelo. El kit te lleva al copiloto que programa en tu editor.
- Espacio en línea de por vida
- PDF + archivos
- Actualizaciones de por vida
El principio del texto a SQL con un LLM se reduce a tres pasos. Primero se describe el esquema de la base de datos al modelo (el DDL de las tablas relevantes). Luego se le envía la pregunta del usuario con una instrucción estricta: generar únicamente una consulta SQL para el dialecto objetivo. Por último, se recupera la consulta, se valida y se ejecuta en modo de solo lectura.
- 01Introspección del esquemaSe extrae la estructura de las tablas (columnas, tipos, claves) de la base de datos, automáticamente en lugar de a mano, para mantener la sincronización.
- 02Construcción del promptSe crea un prompt de sistema que incluye el dialecto SQL, el esquema pertinente y las reglas (solo SELECT, LIMIT obligatorio, sin comentarios).
- 03GeneraciónEl LLM local devuelve una consulta. La limpiamos (eliminación de los posibles delimitadores Markdown ```sql).
- 04Validación + ejecuciónSe verifica que sea realmente un SELECT, se ejecuta mediante un rol de base de datos de solo lectura y se devuelven las filas.
#Prerrequisitos
- Ollama instalado
- El demonio debe escuchar en http://localhost:11434. Verifica con «ollama ps».
- Un modelo capaz
- Un modelo de código reciente (Qwen3-Coder 30B-A3B, Devstral 24B) da resultados mucho mejores en SQL que un pequeño generalista (ver la sección modelos).
- Python 3.10+
- Con el cliente de base de datos adecuado: psycopg2-binary (PostgreSQL) o PyMySQL (MySQL).
- Acceso a la base de datos de solo lectura
- Idealmente, un rol SQL específico que solo permita ejecutar SELECT: la medida de protección más importante.
#Proporcionar al modelo el esquema de tu base de datos
Es el paso que determina un 80 % de la calidad del resultado. El modelo no puede generar una consulta correcta si no conoce los nombres exactos de las tablas y columnas, sus tipos y las relaciones entre ellas. Dos enfoques: pegar el DDL bruto o introspeccionar la base para construir una descripción compacta.
Para una base de datos pequeña (menos de unas veinte tablas), se puede introducir todo. Por encima de ese tamaño, el esquema supera el contexto útil y abruma al modelo: entonces hay que seleccionar las tablas pertinentes para la pregunta (mediante una primera fase de búsqueda o un mapeo del dominio de negocio). A continuación se muestra una introspección de PostgreSQL que genera un esquema legible para el LLM.
#Pipeline Python completo con Ollama
Aquí tienes un pipeline mínimo pero funcional: esquema → prompt → generación → limpieza → validación → ejecución. Utiliza el cliente oficial de Python de Ollama y un rol de base de datos de solo lectura.
La parte de ejecución separa deliberadamente la validación de la llamada a la base de datos. Se rechaza todo lo que no sea un único SELECT antes incluso de abrir el cursor.
#Mejorar la fiabilidad y la seguridad del SQL generado
Esta es la sección que distingue una demostración de un despliegue real. Un LLM puede generar una consulta destructiva si se le pide, o por accidente mediante una inyección en la pregunta. La defensa nunca debe basarse únicamente en el prompt: debe aplicarse en profundidad, en la base de datos.
- 01Rol de base de datos de solo lectura (defensa principal)Crea un rol SQL que tenga SOLO el privilegio SELECT. Aunque el modelo genere un DROP TABLE, la base lo rechaza. Este es el único mecanismo realmente confiable: 'GRANT SELECT ON ALL TABLES IN SCHEMA public TO readonly;' y nada más.
- 02Validación en la aplicaciónAntes, analiza el SQL con sqlparse y descarta todo lo que no sea una única sentencia SELECT. Doble barrera junto con el rol de la base de datos.
- 03Tiempo límite de la consultaSET statement_timeout impide que una consulta mal formada (producto cartesiano sobre millones de filas) sature la base de datos.
- 04LIMIT forzadoImpón un LIMIT tanto en el prompt como en el código para no cargar nunca tablas completas en memoria.
- 05Bucle de correcciónSi la ejecución devuelve un error SQL, envía el mensaje de error al modelo y pide una consulta corregida (1 o 2 intentos máximo).
El ciclo de corrección mejora significativamente el porcentaje de éxito. Muchos errores son triviales (nombre de columna ligeramente incorrecto, función de fecha propia del dialecto) y el modelo los corrige en el segundo intento si ve el mensaje de error del motor.
#¿Qué modelos locales destacan en SQL?
El SQL es una tarea de programación: los modelos especializados en código superan claramente a los generalistas del mismo tamaño. En 2026, un modelo de código reciente como Qwen3-Coder 30B-A3B lo cambia todo: los modelos pequeños de 2B a 8B improvisan consultas sencillas, pero fallan en cuanto hacen falta varias uniones o una agregación con funciones de ventana. (Codestral 22B, citado durante mucho tiempo para SQL, ahora tiene una licencia que no permite su uso en producción: hay que descartarlo en empresas.)
- Qwen3-Coder 30B-A3B
- La opción por defecto en 2026. Modelo MoE especializado en código con 3B de parámetros activos: rápido, 256k de contexto para esquemas grandes, ≈19 GB en Q4 en una RTX 4090 o un Mac reciente. Licencia Apache 2.0.
- Devstral 24B
- Especialista en código de Mistral AI (Apache 2.0), ≈14 GB en Q4: cabe en una tarjeta de 16 GB como la RTX 4080. El mejor equilibrio para SQL en una estación de trabajo modesta.
- Qwen 3.8 27B
- Modelo generalista reciente con razonamiento sólido en consultas con uniones complejas (≈18 GB, 262k de contexto, visión). Pon su ajuste de razonamiento en «low»: en una tarea tan estructurada como el SQL, tiende a razonar en exceso con el ajuste predeterminado.
- Modelos pequeños 2B–8B (Qwen 3.5 4B, Granite 4.2 8B)
- Para esquemas muy simples y preguntas directas únicamente. Evitar estos modelos en cuanto la base de datos tenga relaciones no triviales.
#Solución de problemas
- El modelo inventa columnas
- El esquema es incompleto o demasiado grande. Limítalo a las tablas pertinentes y añade comentarios sobre la lógica de negocio en las columnas ambiguas.
- Respuestas con texto alrededor del SQL
- Refuerza la instrucción «Solo SQL, sin explicaciones» y conserva la eliminación de los delimitadores de bloques de código Markdown en clean_sql.
- Errores en la función de fecha
- Especifica el dialecto en el prompt de sistema (PostgreSQL y MySQL difieren en DATE_TRUNC, YEAR(), etc.). El ciclo de corrección subsana los errores restantes.
- Consultas lentas o que agotan el tiempo de espera
- statement_timeout hace su trabajo. Añade «filtrar siempre en un rango de fechas razonable» al prompt para las grandes tablas.
- «Connection refused» en Ollama
- El daemon no está en ejecución. Comprueba «ollama ps» y que el servicio esté escuchando en http://localhost:11434.
#Para ir más allá
El text-to-SQL reutiliza varios componentes ya tratados en el sitio. Estas guías amplían esta guía:
- Integrar Ollama en una aplicación Python mediante la API REST
- Para exponer este pipeline detrás de una API FastAPI, gestionar el streaming y el modo JSON.
- Function calling y salidas JSON estructuradas con Ollama
- Una alternativa para estructurar la salida (consulta + explicación) de forma garantizada en lugar de mediante limpieza de texto.
- Elegir tu cuantización (Q4, Q5, Q8, FP16)
- Para encontrar el equilibrio entre el tamaño del modelo SQL y la VRAM disponible en tu tarjeta.
¿Un comentario, un error, una precisión? Avísanos, eso mejora la guía para todos.