High-performance SDK to convert natural language prompts to MongoDB queries using AI (OpenAI GPT or Anthropic Claude)
Project description
Prompt to Query - Python SDK
SDK de alto rendimiento para convertir lenguaje natural en queries de MongoDB usando IA (OpenAI GPT o Anthropic Claude).
Características
- Alto Rendimiento: Core nativo en Go con bindings Python para máxima velocidad
- Multiplataforma: Soporta Linux, macOS y Windows (AMD64 y ARM64)
- Múltiples LLMs: Compatible con OpenAI (GPT-4, GPT-3.5) y Anthropic (Claude)
- Sin Dependencias Externas: Usa solo la librería estándar de Python (ctypes)
- Detección de Columnas: Genera automáticamente títulos legibles para las columnas de resultados
- Sugerencias Inteligentes: Análisis de queries con recomendaciones basadas exclusivamente en tu esquema de base de datos
- Optimización de Prompts: Mejora tus consultas en lenguaje natural con sugerencias contextuales
- Fácil de Usar: API simple y consistente
Instalación
pip install prompt-to-query
Requisitos
- Python >= 3.8 (recomendado >= 3.10)
- Una API key de OpenAI o Anthropic
- Las librerías nativas se incluyen para las siguientes plataformas:
- Linux (AMD64, ARM64) - glibc y musl (Alpine)
- macOS (AMD64/Intel, ARM64/Apple Silicon)
- Windows (AMD64)
Nota técnica: Este paquete usa ctypes de la librería estándar de Python para FFI (Foreign Function Interface), lo que significa cero dependencias externas.
Uso Rápido
Uso Básico
from prompt_to_query import PromptToQuery
# Inicializar el SDK
ptq = PromptToQuery(
llm_provider="openai", # o "anthropic"
api_key="your-api-key",
db_schema_path="schema.json"
)
# Generar query desde lenguaje natural
result = ptq.generate_query("Get all active users from last month")
print(result['query'])
# Output: {'operation': 'find', 'collection': 'users', 'filter': {...}}
print(result['columnTitles'])
# Output: ['User Name', 'Email', 'Status', 'Created At']
# Obtener versión del SDK
print(ptq.get_version())
Uso con Variables de Entorno
import os
from prompt_to_query import PromptToQuery
ptq = PromptToQuery(
llm_provider="openai",
api_key=os.getenv("OPENAI_API_KEY"),
db_schema_path="./schema.json"
)
try:
result = ptq.generate_query('Count orders from last week')
print('Query:', result['query'])
print('Columns:', result['columnTitles'])
except Exception as e:
print(f'Error: {e}')
Configuración
Opciones del Constructor
PromptToQuery(
llm_provider: str, # 'openai' o 'anthropic' (requerido)
api_key: str, # Tu API key (requerido)
db_schema: dict = None, # Esquema de DB como diccionario (opcional)
db_schema_path: str = None, # Path al archivo JSON del esquema (opcional)
model: str = None, # Modelo específico a usar (opcional)
lib_path: str = None # Path personalizado a la librería nativa (opcional)
)
Nota: Debes proporcionar o bien db_schema o bien db_schema_path.
Esquema de Base de Datos
Formato Recomendado: TOON
⚠️ Recomendación importante: Para reducir significativamente los costos de tokenización al usar LLMs, te recomendamos usar el formato TOON (Token-Oriented Object Notation) en lugar de JSON para tu esquema de base de datos.
Ventajas del formato TOON:
- 30-60% menos tokens que JSON, lo que reduce directamente los costos de API
- Mantiene la legibilidad humana
- Especialmente eficiente para estructuras uniformes como esquemas de base de datos
- Elimina redundancia en la repetición de claves y puntuación innecesaria
Ejemplo de esquema en formato TOON (schema.toon):
collections[2]{name,fields}:
users,{name:string;email:string;status:string;created_at:date;last_login:date}
products,{name:string;price:number;category:string;stock:number}
Comparación con JSON equivalente (schema.json):
{
"users": {
"fields": {
"name": "string",
"email": "string",
"status": "string",
"created_at": "date",
"last_login": "date"
}
},
"products": {
"fields": {
"name": "string",
"price": "number",
"category": "string",
"stock": "number"
}
}
}
Ahorro: El formato TOON usa aproximadamente 42% menos tokens en este ejemplo.
Uso con formato TOON
Para usar el formato TOON, simplemente pasa el archivo .toon como string:
with open('./schema.toon', 'r') as f:
schema = f.read()
ptq = PromptToQuery(
llm_provider="openai",
api_key=os.getenv("OPENAI_API_KEY"),
db_schema=schema # Pasa el contenido TOON como string
)
También puedes seguir usando JSON si lo prefieres con db_schema_path:
ptq = PromptToQuery(
llm_provider="openai",
api_key=os.getenv("OPENAI_API_KEY"),
db_schema_path="./schema.json"
)
API
PromptToQuery(config)
Crea una nueva instancia del SDK.
Parámetros:
llm_provider(str): Proveedor de LLM - 'openai' o 'anthropic'api_key(str): Tu API keydb_schema(dict, opcional): Esquema de base de datos como diccionariodb_schema_path(str, opcional): Path al archivo JSON del esquemamodel(str, opcional): Modelo específico a usarlib_path(str, opcional): Path personalizado a la librería nativa
Raises:
Exception: Si la inicialización falla o la configuración es inválida
generate_query(prompt: str) -> dict
Genera una query de MongoDB desde un prompt en lenguaje natural.
Parámetros:
prompt(str): Descripción en lenguaje natural de la query deseada
Returns:
dict: Diccionario con las siguientes claves:query: Diccionario de query de MongoDB con:operation: "find", "aggregate", o "count"collection: Nombre de la colecciónfilter: Filtro de query (para find/count)pipeline: Pipeline de agregación (para aggregate)projection,sort,limit,skip: Parámetros opcionales
columnTitles: Lista de strings con títulos legibles para las columnas
Raises:
Exception: Si la generación de query falla
Ejemplo:
result = ptq.generate_query('Top 10 products by price')
print(result['query'])
# {
# 'operation': 'find',
# 'collection': 'products',
# 'sort': {'price': -1},
# 'limit': 10
# }
print(result['columnTitles'])
# ['Product Name', 'Price', 'Category', 'Stock']
explain_query(query: dict) -> dict
Explica qué hace una query de MongoDB en lenguaje natural.
Parámetros:
query(dict): Diccionario de query de MongoDB (del resultado degenerate_query)
Returns:
dict: Diccionario con las siguientes claves:explanation(str): Explicación completa en lenguaje natural de lo que hace la queryoperation(str): Tipo de operación ("find", "aggregate", o "count")targetCollection(str): Colección siendo consultadadataReturned(list): Lista de campos/datos que serán retornadosfilters(list): Lista de descripciones de filtros en lenguaje naturalsorting(str): Descripción del ordenamiento (si aplica)limitations(str): Descripción de limit/skip (si aplica)complexity(str): Complejidad de la query ("low", "medium", o "high")estimatedDocuments(str): Número estimado de documentos ("1-10", "10-100", "100-1000", "1000+", o "all")
Raises:
Exception: Si la explicación falla
Ejemplo:
result = ptq.generate_query('Get top 10 products by price')
explanation = ptq.explain_query(result['query'])
print(explanation['explanation'])
# "Esta query recupera los 10 productos principales ordenados por precio en orden descendente"
print(explanation['operation']) # "find"
print(explanation['complexity']) # "low"
suggest_database_improvements(query: dict) -> dict
Obtiene sugerencias de optimización de base de datos para una query.
Parámetros:
query(dict): Diccionario de query de MongoDB (del resultado degenerate_query)
Returns:
dict: Diccionario con las siguientes claves:indexRecommendations(list): Lista de recomendaciones específicas de índices con comandos MongoDB. Cada objeto contiene:collection(str): Nombre de la colecciónfields(list): Lista de campos para el índicetype(str): Tipo de índice ("single", "compound", "text", etc.)reason(str): Razón para crear el índiceimpact(str): Impacto esperado ("high", "medium", "low")createQuery(str): Comando MongoDB para crear el índice
performanceHints(list): Lista de sugerencias de optimización de rendimientoschemaOptimizations(list): Lista de sugerencias de diseño de esquemaqueryOptimization(str): Descripción de enfoque alternativo de queryestimatedImprovement(str): Ganancia de rendimiento esperadapriority(str): Nivel de prioridad ("high", "medium", o "low")
Raises:
Exception: Si el análisis falla
Ejemplo:
result = ptq.generate_query('Get top 10 products by price')
improvements = ptq.suggest_database_improvements(result['query'])
print(improvements['indexRecommendations'])
# [{'collection': 'products', 'fields': ['price'], 'type': 'single', ...}]
print(improvements['estimatedImprovement'])
# "10-100x más rápido para operaciones de ordenamiento"
improve_prompt(query: dict, original_prompt: str) -> dict
Obtiene sugerencias para mejorar el prompt en lenguaje natural.
Parámetros:
query(dict): Diccionario de query de MongoDB (del resultado degenerate_query)original_prompt(str): El prompt original en lenguaje natural
Returns:
dict: Diccionario con las siguientes claves:originalPrompt(str): El prompt original del usuarioimprovedPrompt(str): Versión mejorada sugerida del promptambiguities(list): Lista de ambigüedades detectadasmissingDetails(list): Lista de detalles que podrían agregarsesuggestions(list): Lista de sugerencias específicas de mejoraclarityScore(str): Evaluación de claridad ("excellent", "good", "fair", o "poor")availableFields(list): Lista de campos relevantes del esquemaexamplePrompts(list): Lista de ejemplos de prompts bien escritos
Raises:
Exception: Si el análisis falla
Ejemplo:
result = ptq.generate_query('Get products')
improvement = ptq.improve_prompt(result['query'], 'Get products')
print(improvement['improvedPrompt'])
# "Obtener todos los productos activos ordenados por precio en orden descendente, limitado a 10 resultados"
print(improvement['clarityScore']) # "poor"
print(improvement['suggestions'])
# ["Agregar orden de clasificación", "Especificar filtros", "Agregar límite"]
get_version() -> str
Obtiene la versión del SDK.
Returns:
str: String de versión
Ejemplos
Ejemplo 1: Query Simple
result = ptq.generate_query('Get all active users')
print(result['query'])
# {'operation': 'find', 'collection': 'users', 'filter': {'status': 'active'}}
print(result['columnTitles'])
# ['Name', 'Email', 'Status', 'Created At']
Ejemplo 2: Query con Filtros Complejos
result = ptq.generate_query(
'Find products with price greater than 100 dollars'
)
print(result['query'])
# {
# 'operation': 'find',
# 'collection': 'products',
# 'filter': {'price': {'$gt': 100}}
# }
print(result['columnTitles'])
# ['Product Name', 'Price', 'Category']
Ejemplo 3: Query de Agregación
result = ptq.generate_query(
'Get top 10 products by sales with their categories'
)
print(result['query'])
# {
# 'operation': 'aggregate',
# 'collection': 'products',
# 'pipeline': [
# {'$sort': {'sales': -1}},
# {'$limit': 10},
# {'$project': {'name': 1, 'sales': 1, 'category': 1}}
# ]
# }
print(result['columnTitles'])
# ['Product Name', 'Sales', 'Category']
Ejemplo 4: Query de Conteo
result = ptq.generate_query('Count orders from last month')
print(result['query'])
# {
# 'operation': 'count',
# 'collection': 'orders',
# 'filter': {'created_at': {'$gte': '...'}}
# }
print(result['columnTitles'])
# ['Total Orders']
Ejemplo 5: Explicar Queries
result = ptq.generate_query('Get top 10 products by price')
# Obtener explicación de lo que hace la query
explanation = ptq.explain_query(result['query'])
print(explanation['explanation'])
# "Esta query recupera los 10 productos principales ordenados por precio en orden descendente"
print(f"Operación: {explanation['operation']}") # "find"
print(f"Colección: {explanation['targetCollection']}") # "products"
print(f"Datos retornados: {explanation['dataReturned']}")
# ['name', 'price', 'category', 'stock']
print(f"Filtros aplicados: {explanation['filters']}")
# [] (no hay filtros en esta query)
print(f"Ordenamiento: {explanation['sorting']}")
# "Ordenado por precio en orden descendente"
print(f"Limitaciones: {explanation['limitations']}")
# "Limitado a 10 documentos"
print(f"Complejidad: {explanation['complexity']}") # "low"
print(f"Documentos estimados: {explanation['estimatedDocuments']}") # "10"
Ejemplo 6: Sugerencias de Optimización de Base de Datos
result = ptq.generate_query('Get top 10 products by price')
# Obtener sugerencias de optimización de base de datos
improvements = ptq.suggest_database_improvements(result['query'])
print("Recomendaciones de índices:")
for idx in improvements['indexRecommendations']:
print(f" Colección: {idx['collection']}")
print(f" Campos: {idx['fields']}")
print(f" Tipo: {idx['type']}")
print(f" Razón: {idx['reason']}")
print(f" Impacto: {idx['impact']}")
print(f" Comando: {idx['createQuery']}")
# Ejemplo:
# Colección: products
# Campos: ['price']
# Tipo: single
# Razón: Mejorar rendimiento de ordenamiento
# Impacto: high
# Comando: db.products.createIndex({"price": -1})
print("\nSugerencias de rendimiento:")
for hint in improvements['performanceHints']:
print(f" - {hint}")
# ["Considerar cachear resultados si la data no cambia frecuentemente"]
print("\nOptimizaciones de esquema:")
for opt in improvements['schemaOptimizations']:
print(f" - {opt}")
# ["Considerar denormalizar datos de categoría si se accede frecuentemente"]
print(f"\nMejora estimada: {improvements['estimatedImprovement']}")
# "10-100x más rápido para operaciones de ordenamiento"
print(f"Prioridad: {improvements['priority']}") # "high"
Ejemplo 7: Mejorar Prompts en Lenguaje Natural
# Prompt poco claro
result = ptq.generate_query('Get products')
# Obtener sugerencias para mejorar el prompt
improvement = ptq.improve_prompt(result['query'], 'Get products')
print(f"Prompt original: {improvement['originalPrompt']}")
# "Get products"
print(f"\nPrompt mejorado sugerido: {improvement['improvedPrompt']}")
# "Obtener todos los productos activos ordenados por precio en orden descendente, limitado a 10 resultados"
print(f"\nPuntaje de claridad: {improvement['clarityScore']}") # "poor"
print("\nAmbigüedades detectadas:")
for amb in improvement['ambiguities']:
print(f" - {amb}")
# ["No se especifica orden de clasificación",
# "No se especifican criterios de filtrado",
# "No se especifica límite de resultados"]
print("\nDetalles faltantes:")
for detail in improvement['missingDetails']:
print(f" - {detail}")
# ["¿Ordenar por precio, nombre, o fecha?",
# "¿Incluir solo productos activos?",
# "¿Cuántos resultados retornar?"]
print("\nSugerencias específicas:")
for suggestion in improvement['suggestions']:
print(f" - {suggestion}")
# ["Agregar orden de clasificación (ej: 'ordenados por precio')",
# "Especificar filtros (ej: 'productos activos')",
# "Agregar límite (ej: 'los 10 primeros')"]
print("\nCampos disponibles en el esquema:")
print(improvement['availableFields'])
# ['name', 'price', 'category', 'stock', 'status', 'created_at']
print("\nEjemplos de buenos prompts:")
for example in improvement['examplePrompts']:
print(f" - {example}")
# ["Obtener los 10 productos más caros de la categoría electrónica",
# "Buscar productos con stock menor a 5 ordenados por nombre",
# "Contar productos activos creados en el último mes"]
Ejemplo 8: Manejo de Errores
try:
result = ptq.generate_query('invalid query')
print(result['query'])
print(result['columnTitles'])
except Exception as e:
print(f'Error del SDK: {e}')
Documentación Adicional
Para casos de uso más avanzados, consulta la documentación especializada:
Guía de Docker
Documentación completa para usar el SDK con Docker:
- Configuración con Alpine Linux y Ubuntu/Debian
- Multi-stage builds para optimizar tamaño de imagen
- Docker Compose con MongoDB
- Kubernetes deployments
- CI/CD con GitHub Actions
- Seguridad y best practices
- Ejemplos con FastAPI y Django
Características Avanzadas
Funcionalidades avanzadas y optimización:
- Detección automática de columnas
- Uso del esquema como diccionario
- Configuración de librería nativa personalizada
- Benchmarking y profiling con cProfile
- Manejo avanzado de errores (retry, circuit breaker, decoradores)
- Type hints y Mypy
- Patrones de diseño (Singleton, Factory, Context Manager)
- Debugging y logging con OpenTelemetry
Proveedores LLM
OpenAI
ptq = PromptToQuery(
llm_provider="openai",
api_key=os.getenv("OPENAI_API_KEY"),
model="gpt-4", # opcional, por defecto: gpt-3.5-turbo
db_schema_path="./schema.json"
)
Modelos soportados:
gpt-4gpt-4-turbo-previewgpt-3.5-turbo(por defecto)
Anthropic Claude
ptq = PromptToQuery(
llm_provider="anthropic",
api_key=os.getenv("ANTHROPIC_API_KEY"),
model="claude-3-opus-20240229", # opcional
db_schema_path="./schema.json"
)
Modelos soportados:
claude-3-opus-20240229claude-3-sonnet-20240229(por defecto)claude-3-haiku-20240307
Solución de Problemas
Error: "Library not found"
Si ves este error, significa que la librería nativa no se encuentra. Soluciones:
- Verifica que tu plataforma sea compatible
- Reinstala el paquete:
pip install --force-reinstall prompt-to-query - Especifica un path personalizado:
ptq = PromptToQuery(
llm_provider="openai",
api_key="your-key",
db_schema_path="./schema.json",
lib_path="/path/to/libprompttoquery.so"
)
Error: "Initialization failed"
Verifica:
- Que tu API key sea válida
- Que el archivo de esquema exista y sea JSON válido
- Que el provider sea 'openai' o 'anthropic'
Error en Alpine Linux (musl)
El SDK incluye librerías nativas para Alpine Linux. Si experimentas problemas:
- Verifica que estés usando una imagen Alpine oficial
- El SDK detecta automáticamente Alpine y selecciona la librería correcta
- Si falla, puedes especificar manualmente el path a la librería musl
Problemas con Permisos en Linux
Si ves errores de permisos al cargar la librería:
chmod +x /path/to/libprompttoquery.so
O en Docker, asegúrate de que el usuario tenga permisos de lectura:
RUN chmod 755 /usr/local/lib/python3.x/site-packages/prompt_to_query/lib/*
Seguridad
- Nunca incluyas API keys en el código o control de versiones
- Usa variables de entorno (
os.getenv()) para credenciales - El SDK valida todas las queries generadas antes de retornarlas
- No ejecuta queries automáticamente - siempre tienes control
- Las librerías nativas están firmadas y verificadas
Plataformas Soportadas
| OS | AMD64 | ARM64 | Alpine (musl) |
|---|---|---|---|
| Linux | ✅ | ✅ | ✅ |
| macOS | ✅ | ✅ | N/A |
| Windows | ✅ | ❌ | N/A |
Contribuir
Las contribuciones son bienvenidas! Por favor:
- Fork el repositorio
- Crea una rama para tu feature (
git checkout -b feature/amazing-feature) - Commit tus cambios (
git commit -m 'Add amazing feature') - Push a la rama (
git push origin feature/amazing-feature) - Abre un Pull Request
License
MIT License - see LICENSE file for details
Links
- GitHub: https://github.com/dimarb/prompt-to-query
- PyPI: https://pypi.org/project/prompt-to-query/
- Issues: https://github.com/dimarb/prompt-to-query/issues
- Documentación completa: GitHub
- Ejemplos: Ver directorio
examples/
Hecho con ❤️ usando Go + Python
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file prompt_to_query-1.0.9.tar.gz.
File metadata
- Download URL: prompt_to_query-1.0.9.tar.gz
- Upload date:
- Size: 24.9 MB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.9.6
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
0d40bdfc4cc90410ee6b61fb6cfafbea9d3f6b39dc0bdb36885f8f1e43d9f7f5
|
|
| MD5 |
90036802ee16f6cbf6ce68d47b287ae2
|
|
| BLAKE2b-256 |
b058c6bf4e00f5a99c87a09532ce95ed1f6f97ac9b73d5b5e6c7d6c5eb75b05f
|
File details
Details for the file prompt_to_query-1.0.9-py3-none-any.whl.
File metadata
- Download URL: prompt_to_query-1.0.9-py3-none-any.whl
- Upload date:
- Size: 25.0 MB
- Tags: Python 3
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.9.6
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
477ac2d003ec15ea0b45e9850b0d0130771ce0a415dd4d68c521fc542ca65071
|
|
| MD5 |
cfe5c64b81b84146a22b7d19a6c72f7e
|
|
| BLAKE2b-256 |
7954363811192ff8e5a0e1fd6a83fa75da3baf3874b23b93532661998d1f5561
|