Cómo funciona
El modelo propone.
SQAI decide.
Un agente nunca escribe SQL ni emite código para ejecutar. Escribe una solicitud tipada — y cada solicitud recorre el mismo camino: validada contra un contrato fijado, verificada contra tu política, ejecutada en un motor determinista, devuelta con los hashes que permiten reproducirla.
Cada solicitud — ask(), compute() o una llamada a herramienta del AI SDK — recorre el mismo camino. Nada toca el motor hasta que todas las verificaciones han pasado.
01Intención tipada
Una solicitud que el motor puede analizar. No una cadena que deba confiar.
El modelo emite un objeto tipado — nunca SQL, nunca código. Una intención de consulta es un QuerySpec: una métrica a agregar sobre una fuente nombrada. Una intención de cómputo es un ComputationSpec: una función nombrada del contrato, con argumentos y enlaces. Una unión discriminada, dos formas — y en ninguna de ellas hay lugar donde una cadena ejecutable pueda ocultarse.
Esa es la superficie de autoría completa. Lo que la forma no puede expresar, el modelo no puede solicitar.
QuerySpecanatomía{"kind": "query",la etiqueta de unión — consulta o cómputo"version": "1",la versión del spec, fijada"source_name": "sales",una fuente conectada, por nombre exacto"metric": "revenue",la columna a agregar"aggregation": "sum",una de sum · avg · count · min · max"group_by": "region"opcional — divide el resultado por un campo}también opcionalfilter · limit · order
la forma de cómputomodule · function · args · kwargs · bindings · seed?
02Verificación de contrato
Un contrato, fijado por hash. Lo desconocido se rechaza con indicaciones.
El spec se valida contra el contrato de capacidades — un archivo generado y fijado por hash que lista cada operación, su firma exacta y sus indicadores de determinismo. Una capacidad es accesible solo si es de solo lectura y determinista, o determinista con semilla. Las operaciones con escritura y no deterministas no se bloquean en tiempo de ejecución; nunca se generaron en la superficie.
Una función desconocida falla como unsupported_operation y responde con nearest_matches del mismo índice — el modelo se corrige en lugar de entrar en bucle.
contract_hashsha256:79f1c5a6c7164e7e9e1750e70a5c03292fa87eb52d8148a740c06695924be9a1
- 4,778
- operaciones listadas en el contrato
- 4,574
- expuestas a los SDK, solo lectura
- 4,564
- completamente deterministas
- 10
- simulaciones que requieren semilla
- 204
- excluidas de la superficie
elegibilidadread_only && (deterministic || deterministic_when_seeded)
ante un nombre desconocidounsupported_operation + nearest_matches
03Control de política
Tu lista de permisos decide si — y cómo — se ejecuta.
La política se fija cuando createSQAI() construye la instancia y se aplica en proceso antes de que nada se ejecute — sobre la fuente, cada métrica, agrupación, filtro y columna enlazada, y sobre el nombre de la función. Solo puede restringir el contrato: nombrar una capacidad fuera de la superficie elegible sigue lanzando unsupported_operation.
La entrada de herramienta del modelo no lleva ningún campo allowed*. Nada en la solicitud puede ampliar el acceso — así que no hay nada que una inyección de prompt pueda ampliar.
allowedSourcesfuentes que el modelo puede nombrar
- "sales"
allowedFieldscolumnas que puede leer, por fuente
- sales.region
- sales.revenue
- sales.order_date
allowedFunctionsel valor por defecto — toda capacidad de solo lectura, nada más
- "all-readonly"
una denegación es precisa, atribuida, definitiva
- policy_denied_source
- policy_denied_field
- policy_denied_function
source: "sqai" · no reintentable
04Motor determinista
Fijado antes de ejecutar: float64, un hilo, un runtime.
Primero, los enlaces se resuelven. El modelo nombró una fuente y un campo; SQAI extrae los valores reales a través del primitivo extractColumns del motor, alineado por filas, con nulos tratados por pares. SQAI nunca combina arrays por su cuenta — así que la entrada que se hashea es exactamente la entrada que se ejecutó.
Solo entonces toca la solicitud al motor. El runtime está firmado, versionado y fijado: precisión float64, un único hilo. El primer compute() lo aprovisiona una vez, en unos 110 segundos; después permanece residente — finance.npv mide 0,83–0,93 ms en caliente.
0.1.04d64142e4c1ff63d299cfc8b172fdf97cb59169b545e1e02978e678a632ce6e1darwinarm64float641—2ea5ede72acd2912fe9e1230cef34afad4c9436bfa8a709bac2da02b478e3212Registrada con cada resultado — la envolvente declara el alcance de la garantía en lugar de exagerarlo.
05Respuesta + procedencia
Dos hashes. Uno antes, uno después.
invocation_hash se sella antes de la ejecución — sobre el módulo, la función, los argumentos, los enlaces resueltos, la semilla, el contrato y el alcance. computation_hash se sella después: el hash de invocación combinado con el resultado canónico. Reproducir significa ejecutarlo de nuevo y comparar bytes.
Ambos SDK comparten un serializador canónico único, de modo que el mismo cómputo produce hashes byte a byte idénticos en TypeScript y Python. Las respuestas de consulta siguen la misma disciplina: un plan_hash sobre el plan resuelto canónico, más la ruta de decisión y el alcance exacto en que se ejecutó.
3188.1687606249325finance.npv · enlazado a una columna activa · 0,83 ms en caliente
sellado antes de la ejecución
invocation_hash
8223a694250fc751fcf8a7777b8e1f524c44ff1f0e7e83451467f554a6123950
módulo · función · args · bindings resueltos · seed · contrato · ámbito
sellado tras la ejecución
computation_hash
ff5280ea128113f528dd1e9a28b9bc4a81469075ed7c981c7176fb172d98085d
el hash de invocación, combinado con el resultado canónico
Idéntico byte a byte en TypeScript y Python — un resultado calculado en un lenguaje se reproduce y verifica en el otro.
ambos calculados contracontract_hash sha256:79f1c5a6…
en el plano de consultaplan_hash f87610d8afeb…decision_path "exact_spec"deterministic_scope "local_registered_source"
06El bucle de descubrimiento
Sin suposiciones. Descubre, simula, luego ejecuta.
Los nombres de campo y las firmas de función se descubren, no se alucinan. El AI SDK expone exactamente tres herramientas — y solo una de ellas ejecuta.
- 01
listSources()¿Qué puedo consultar?
Fuentes conectadas, con nombres de campo exactos, tipos y las operaciones permitidas por campo. Nunca ejecuta.
- 02
listSources({ capabilitySearch: "npv" })¿Qué puedo calcular?
La misma herramienta, buscando en el catálogo determinista — módulos coincidentes, firmas exactas y si se requiere un seed.
- 03
explainQuery({ … })¿Funcionará?
Una simulación en seco. Devuelve el plan resuelto, la confianza y un invocation_hash de vista previa — una vista previa, nunca un hash ejecutado.
- 04
queryData({ … })Ejecutar.
La única herramienta que ejecuta. Devuelve el resultado junto con su procedencia completa; los resultados de gran tamaño permanecen recuperables por result_id.
Las herramientas nunca lanzan errores — cada resultado tiene tipook · needs_clarification · rejected · error
La mecánica, campo por campo.
Leer la documentación →- IA deterministael sobre y los tres hashes, campo por campo
- Gobernanza de datos con IAlistas de permisos y la regla de solo restricción, en profundidad
- Conectar datoscada fuente adopta la misma forma tipada