Catálogo de audiencias
Tablas, columnas y registros repetidos disponibles para construir una audiencia.
Catálogo
El catálogo responde qué se puede filtrar. Son dos rutas: una lista las tablas disponibles y la otra, para una tabla, todo lo que ofrece —columnas escalares y columnas RECORD REPEATED.
Sin el catálogo la definición no es construible: no hay otra forma de saber cuál es la
columna de identidad de una tabla, qué columna TIMESTAMP sugiere como referencia
temporal, ni que attributes es un registro repetido y no una columna comparable.
Auth: Requerida — permiso audience-criteria:view en ambas rutas
GET /api/audience-criterias/tables
Lista las tablas del catálogo sobre las que se puede construir una audiencia. El catálogo es idéntico entre tenants: esta ruta no consulta el dataset del tenant.
Ejemplo
curl https://api.reten.ai/api/audience-criterias/tables \
-H "Authorization: Bearer <token>" \
-H "x-tenant-id: <tenant-id>" \
-H "x-project-id: <project-id>"import axios from 'axios';
const response = await axios.get(
'https://api.reten.ai/api/audience-criterias/tables',
{ headers: { Authorization: 'Bearer <token>', 'x-tenant-id': '<tenant-id>', 'x-project-id': '<project-id>' } },
);
const tables = response.data;Respuesta 200 OK
Un arreglo de IAudienceTable:
| Campo | Tipo | Descripción |
|---|---|---|
tableName | string | Nombre de la tabla; es el valor que va en from.table y en ColumnRefDto.table. |
identityColumn | string | Opcional. Columna de identidad de la tabla (por ejemplo user_id). Una tabla que solo sirve para cruzar puede no tenerla. |
defaultTimeReferenceColumn | string | Opcional. Columna TIMESTAMP sugerida como reference de la ventana temporal. Se puede elegir otra columna TIMESTAMP. |
requiresInnerJoin | boolean | true si la tabla solo admite participar como tabla principal del from o como destino de un INNER JOIN. |
[
{
"tableName": "user_properties",
"identityColumn": "user_id",
"defaultTimeReferenceColumn": "sign_up_date",
"requiresInnerJoin": false
},
{
"tableName": "event_transactions",
"identityColumn": "user_id",
"defaultTimeReferenceColumn": "event_date",
"requiresInnerJoin": false
},
{
"tableName": "user_segment_relation",
"identityColumn": "user_id",
"requiresInnerJoin": true
},
{
"tableName": "user_seller_relation",
"identityColumn": "user_id",
"requiresInnerJoin": true
}
]El identityColumn es la columna que al menos un bloque de consulta tiene que proyectar
en su select: una definición que no la expone se rechaza con 400. El detalle está en
Columna de identidad.
Una tabla con requiresInnerJoin: true restringe el bloque entero: si participa de
un bloque, todos los joins de ese bloque tienen que ser INNER. La señal está en el
catálogo para que el bloque se arme bien desde el principio, en vez de descubrirlo con un
400 al validar.
GET /api/audience-criterias/tables/:tableName/columns
Devuelve todo lo que el catálogo ofrece sobre una tabla. A diferencia de /tables, esta
ruta reconcilia el catálogo contra el schema real del dataset del tenant antes de
responder.
Parámetros de ruta
| Parámetro | Tipo | Descripción |
|---|---|---|
tableName | string | Nombre de la tabla, tal como lo devuelve GET /tables. |
Ejemplo
curl https://api.reten.ai/api/audience-criterias/tables/event_transactions/columns \
-H "Authorization: Bearer <token>" \
-H "x-tenant-id: <tenant-id>" \
-H "x-project-id: <project-id>"import axios from 'axios';
const response = await axios.get(
'https://api.reten.ai/api/audience-criterias/tables/event_transactions/columns',
{ headers: { Authorization: 'Bearer <token>', 'x-tenant-id': '<tenant-id>', 'x-project-id': '<project-id>' } },
);
const columns = response.data;Respuesta 200 OK
Un arreglo de IAudienceColumn: una unión discriminada por kind con dos variantes.
Estrecha por kind antes de leer type o fields. Solo la variante scalar trae
type; solo record trae fields. Leer column.type sin discriminar devuelve
undefined para un registro repetido.
-
kind: "scalar"— una columna filtrable directamente:Campo Tipo Descripción columnNamestring Nombre de la columna. Para hojas de un STRUCT no repetido es el path con punto ( pricing.final_amount).kind"scalar"Discriminador. typeCatalogFieldTypeEnumTipo del catálogo; determina qué operadores de comparación admite. isIdentityboolean truesi es la columna de identidad de la tabla. Como máximo una columna por tabla la tiene.isDefaultTimeReferenceboolean truesi es la referencia temporal sugerida de la tabla. Es una sugerencia: se puede anclar la ventana en otra columnaTIMESTAMP. -
kind: "record"— una columna RECORD REPEATED, filtrable solo con un filtro de registro:Campo Tipo Descripción columnNamestring Nombre de la columna repetida. kind"record"Discriminador. fieldsIAudienceColumn[]Sub-campos filtrables, relativos al registro. Puede contener otros record.isIdentityfalseSiempre false: un registro repetido no puede ser la identidad de la tabla.isDefaultTimeReferencefalseSiempre false: un registro repetido no puede anclar la ventana temporal.
Los fields de un record usan la misma unión scalar | record, así que la regla de
estrechar por kind aplica en cada nivel.
Un sub-campo de un registro nunca trae isIdentity ni isDefaultTimeReference en
true, ni siquiera si se llama igual que la columna de identidad de la tabla. Los dos
roles son de la tabla sobre sus columnas de primer nivel.
Ejemplo de respuesta
GET /api/audience-criterias/tables/event_transactions/columns:
[
{
"columnName": "user_id",
"kind": "scalar",
"type": "STRING",
"isIdentity": true,
"isDefaultTimeReference": false
},
{
"columnName": "event_date",
"kind": "scalar",
"type": "TIMESTAMP",
"isIdentity": false,
"isDefaultTimeReference": true
},
{
"columnName": "event_id",
"kind": "scalar",
"type": "STRING",
"isIdentity": false,
"isDefaultTimeReference": false
},
{
"columnName": "status",
"kind": "scalar",
"type": "STRING",
"isIdentity": false,
"isDefaultTimeReference": false
},
{
"columnName": "coupon_code",
"kind": "scalar",
"type": "STRING",
"isIdentity": false,
"isDefaultTimeReference": false
},
{
"columnName": "pricing.final_amount",
"kind": "scalar",
"type": "FLOAT64",
"isIdentity": false,
"isDefaultTimeReference": false
},
{
"columnName": "attributes",
"kind": "record",
"fields": [
{
"columnName": "key",
"kind": "scalar",
"type": "STRING",
"isIdentity": false,
"isDefaultTimeReference": false
},
{
"columnName": "value",
"kind": "scalar",
"type": "STRING",
"isIdentity": false,
"isDefaultTimeReference": false
}
],
"isIdentity": false,
"isDefaultTimeReference": false
}
]Cómo se usa cada variante en la definición
| Variante | Dónde va |
|---|---|
scalar | ColumnRefDto.column de una hoja predicate, del select, del groupBy, de un agregado, del on de un join o de la reference de la ventana temporal. |
record | column de una hoja recordPredicate; sus fields van en el field de las hojas del subWhere. |
Una columna record no se puede comparar ni proyectar: usarla en el select, en el
groupBy, en un agregado, en el on de un join o en una hoja predicate devuelve
400. Su único uso es el filtro de registro.
Respuestas de error
| Estado | Descripción |
|---|---|
401 | Falta o es inválido el Authorization: Bearer. |
403 | El usuario no tiene el permiso audience-criteria:view, o el x-tenant-id no está autorizado. |
404 | Solo en /tables/:tableName/columns: la tabla no está en el catálogo (La tabla no existe o no está en el catálogo de audiencias.), o el tenant no tiene dataset configurado (Dataset not configured for tenant <id>). |
500 | Solo en /tables/:tableName/columns: el schema real del dataset no satisface el catálogo (El schema de datos no satisface el catálogo de audiencias.). |
GET /api/audience-criterias/tables no consulta el dataset del tenant, así que solo devuelve
200, 401 o 403.