Via Kondado: Referência KSQL

O KSQL é a linguagem de consulta da Kondado. Ele utiliza uma sintaxe em formato JSON que permite filtrar, agrupar, ordenar e transformar seus dados de forma simples e segura.

ℹ️ Beta: Consultas via KSQL estão disponíveis em modo beta.

Estrutura básica

Uma consulta KSQL é enviada como um objeto JSON dentro da chave ksql. Os campos disponíveis são:

CampoObrigatórioDescrição
table_nameSimNome da tabela a ser consultada
columnsSimLista de colunas a retornar
column_aggregationsNãoTipo de agregação para cada coluna (ex: "sum", "avg", "none")
distinctNãoQuando true, emite SELECT DISTINCT no escopo da consulta (booleano, padrão false)
where_conditionsNãoCondições de filtro
order_byNãoOrdenação dos resultados
limitNãoNúmero máximo de registros (máximo: 1.000)
customColumnsNãoColunas calculadas com expressões personalizadas
column_transformationsNãoTransformações aplicadas às colunas
column_aliasesNãoApelidos para renomear as colunas de saída (mesmo tamanho de columns)
aliasNãoApelido para a tabela principal (alias de FROM), usado para prefixar colunas
joinsNãoJunção com outras tabelas
unionNãoArray de consultas para combinar com UNION ALL (substitui os demais campos)
withNãoArray de CTEs (Common Table Expressions) — subconsultas nomeadas reutilizáveis (veja seção abaixo)

Exemplo mínimo

{
  "ksql": {
    "table_name": "vendas",
    "columns": ["produto", "valor", "data"]
  }
}

Filtros (where_conditions)

Os filtros são definidos como uma lista de condições. Todas as condições são combinadas com E (AND).

"where_conditions": [
  {"column": "status", "operator": "=", "value": "ativo"},
  {"column": "valor", "operator": ">", "value": 100}
]

Comparação coluna-com-coluna (value_column)

Em vez de comparar uma coluna com um valor fixo, você pode comparar uma coluna com outra coluna usando value_column no lugar de value:

"where_conditions": [
  {"column": "receita", "operator": ">", "value_column": "custo"},
  {"column": "data_envio", "operator": "<=", "value_column": "data_limite"}
]

value_column aceita apenas nomes de colunas válidos (letras, números, _ e .). As mesmas regras de segurança de column se aplicam.

Operadores de comparação

OperadorDescriçãoExemplo de valor
=Igual a"ativo"
!=Diferente de"cancelado"
>Maior que100
<Menor que50
>=Maior ou igual a100
<=Menor ou igual a200

Operadores de conjunto

OperadorDescriçãoExemplo de valor
INEstá na lista["SP", "RJ", "MG"]
NOT INNão está na lista["cancelado", "expirado"]

Operadores de texto

OperadorDescriçãoExemplo de valor
LIKECorresponde ao padrão (use % como coringa)"%kondado%"
NOT LIKENão corresponde ao padrão"%teste%"
STARTS_WITHComeça com"BR"
ENDS_WITHTermina com".com"
CONTAINSContém o texto"kondado"
NOT_CONTAINSNão contém o texto"teste"

Operadores de nulo

OperadorDescrição
IS NULLÉ nulo
IS NOT NULLNão é nulo

Operador de intervalo

OperadorDescriçãoExemplo de valor
BETWEENEstá entre dois valores[100, 500]

Operadores de data relativa

Estes operadores facilitam filtros de data sem precisar calcular datas manualmente:

OperadorDescrição
LAST_N_DAYSÚltimos N dias
NEXT_N_DAYSPróximos N dias
LAST_N_HOURSÚltimas N horas
LAST_N_MINUTESÚltimos N minutos
THIS_WEEKSemana atual
LAST_WEEKSemana passada
THIS_MONTHMês atual
LAST_MONTHMês passado
THIS_QUARTERTrimestre atual
LAST_QUARTERTrimestre passado
THIS_YEARAno atual
LAST_YEARAno passado

Exemplo:

{"column": "criado_em", "operator": "LAST_N_DAYS", "value": 7}

Agregações

Para calcular métricas sobre seus dados, use column_aggregations. Sempre que houver ao menos uma agregação diferente de none na consulta, as colunas marcadas como none viram automaticamente as colunas de agrupamento (GROUP BY implícito).

O campo column_aggregations é uma lista com o mesmo tamanho de columns. Cada posição define a agregação da coluna correspondente. Use "none" para colunas que não recebem agregação — elas viram colunas de agrupamento automaticamente quando há ao menos uma agregação real na consulta.

{
  "ksql": {
    "table_name": "pedidos",
    "columns": ["categoria", "receita", "quantidade"],
    "column_aggregations": ["none", "sum", "count"]
  }
}

Funções de agregação disponíveis

FunçãoDescrição
noneSem agregação (coluna de agrupamento)
sumSoma dos valores
avgMédia dos valores
countContagem de registros
count_distinctContagem de valores únicos
minValor mínimo
maxValor máximo
stddevDesvio padrão
varianceVariância

Deduplicar resultados (distinct)

A chave distinct é um booleano opcional (padrão false). Quando true, a consulta gerada usa SELECT DISTINCT no escopo correspondente, eliminando linhas duplicadas sem precisar de agregações.

{
  "ksql": {
    "table_name": "pedidos",
    "columns": ["pais", "cidade"],
    "column_aggregations": ["none", "none"],
    "distinct": true
  }
}

Onde usar distinct

  • No nível raiz de uma consulta simples (sem union).
  • Dentro de cada CTE definida em with[].ksql.
  • Dentro de cada item do array union[] — cada arm pode ter seu próprio distinct.

A chave distinct não é aceita no nível raiz de uma consulta com union: a deduplicação deve ser declarada arm por arm.

Apelidos de coluna (column_aliases)

Use column_aliases para renomear as colunas retornadas pela consulta. O array deve ter o mesmo tamanho de columns e column_aggregations. Cada posição define o nome da coluna de saída correspondente. Use null para manter o nome original.

{
  "ksql": {
    "table_name": "pedidos",
    "columns": ["categoria", "receita", "quantidade"],
    "column_aggregations": ["none", "sum", "count"],
    "column_aliases": [null, "total_receita", "total_pedidos"]
  }
}

Neste exemplo, a saída terá as colunas: categoria, total_receita e total_pedidos.

Alias de tabela (alias)

O campo alias no nível raiz define um apelido para a tabela principal da consulta, útil quando você precisa prefixar colunas para evitar ambiguidade (especialmente com JOINs e CTEs).

{
  "ksql": {
    "table_name": "pedidos",
    "alias": "p",
    "columns": ["p.id", "p.cliente_id", "p.total"],
    "joins": [
      {
        "tableName": "clientes",
        "joinType": "LEFT",
        "conditions": [
          {"leftColumn": "p.cliente_id", "rightColumn": "clientes.id"}
        ]
      }
    ]
  }
}

O alias da tabela principal é diferente do alias usado dentro de CTEs no parâmetro with.

Ordenação (order_by)

"order_by": [
  {"column": "receita", "direction": "desc"},
  {"column": "nome", "direction": "asc"}
]

Colunas calculadas (customColumns)

Crie colunas derivadas usando expressões:

"customColumns": [
  {"name": "lucro", "expression": "receita - custo"},
  {"name": "margem", "expression": "(receita - custo) / receita * 100"}
]

As colunas calculadas podem ser usadas em columns, where_conditions e order_by, como qualquer outra coluna.

Funções disponíveis em expressões

Matemáticas: ABS, CEIL, FLOOR, ROUND, TRUNCATE, MOD, SQRT, POWER, EXP, LOG, LN, SIGN

Texto: UPPER, LOWER, TRIM, LTRIM, RTRIM, SUBSTR, SUBSTRING, LENGTH, REPLACE, CONCAT, SPLIT_PART, LEFT, RIGHT, LPAD, RPAD, REVERSE, REPEAT, INSTR, LOCATE, REGEXP_EXTRACT, REGEXP_REPLACE, REGEXP_LIKE

Data: DATE, YEAR, MONTH, DAY, HOUR, MINUTE, SECOND, DATE_FORMAT, DATE_TRUNC, DATE_ADD, DATE_DIFF, CURRENT_DATE, CURRENT_TIMESTAMP, NOW, EXTRACT, TO_DATE, TO_TIMESTAMP, FROM_UNIXTIME

Conversão: CAST, COALESCE, NULLIF, NVL, IFNULL, GREATEST, LEAST

Condicional: IF, IIF, CASE WHEN ... THEN ... ELSE ... END

Transformações de colunas (column_transformations)

Aplique transformações sequenciais a colunas existentes. As transformações são processadas na ordem em que aparecem.

"column_transformations": {
  "nome": [
    {"type": "text", "operation": "uppercase"}
  ],
  "criado_em": [
    {"type": "date", "operation": "year_month"}
  ],
  "valor": [
    {"type": "number", "operation": "round", "params": {"decimals": 2}}
  ]
}

Transformações de texto: uppercase, lowercase, trim, ltrim, rtrim, extract_domain, extract_before, extract_after, replace (params: find, replace), regexp_extract (params: pattern), regexp_replace (params: pattern, replacement)

Transformações de data: date, year_month, year_week, year_quarter, year, hour, minute, extract_year, extract_month, extract_day, extract_hour, date_add_days (params: days), date_add_hours (params: hours), date_add_minutes (params: minutes)

Transformações numéricas: round (params: decimals), floor, ceil, abs, truncate (params: decimals), divide (params: divisor), multiply (params: multiplier)

Conversões de tipo: cast_to_text, cast_to_int, cast_to_number, cast_to_date, cast_to_timestamp

JOINs

Combine dados de múltiplas tabelas:

{
  "ksql": {
    "table_name": "pedidos",
    "columns": ["pedidos.id", "clientes.nome", "pedidos.total"],
    "column_aggregations": ["none", "none", "none"],
    "joins": [
    {
      "tableName": "clientes",
      "joinType": "LEFT",
      "conditions": [
        {
          "leftColumn": "pedidos.cliente_id",
          "rightColumn": "clientes.id"
        }
      ]
    }
    ]
  }
}

Tipos de JOIN: INNER (apenas registros com correspondência), LEFT (todos da tabela principal + correspondências), RIGHT (todos da tabela unida + correspondências), FULL (todos de ambas), CROSS (produto cartesiano).

Ao usar JOINs, prefixe os nomes das colunas com o nome da tabela (ex: pedidos.id, clientes.nome).

UNION ALL

Combine resultados de consultas em tabelas diferentes. Todas as consultas ficam dentro do array union (mínimo 2). Os campos order_by e limit ficam no nível raiz.

{
  "ksql": {
    "union": [
      {
        "table_name": "vendas_2025",
      "columns": ["mes", "receita"],
      "column_aggregations": ["none", "sum"]
      },
      {
        "table_name": "vendas_2024",
      "columns": ["mes", "receita"],
      "column_aggregations": ["none", "sum"]
      }
    ],
    "order_by": [{"column": "receita", "direction": "desc"}],
    "limit": 500
  }
}

CTEs — Common Table Expressions (with)

O parâmetro with permite criar subconsultas nomeadas (CTEs) que podem ser referenciadas na consulta principal como se fossem tabelas. Isso é útil para organizar consultas complexas em etapas.

O with é um array de objetos. Cada objeto define um CTE com:

CampoObrigatórioDescrição
aliasSimNome do CTE (usado como nome de tabela na consulta principal)
ksqlSim*Consulta KSQL que define os dados do CTE
saved_query_idSim*ID de uma consulta salva que será usada como CTE (alternativa ao ksql)

* Use ksql ou saved_query_id, nunca ambos.

CTE com consulta inline

{
  "ksql": {
    "with": [
      {
        "alias": "vendas_recentes",
        "ksql": {
          "table_name": "vendas",
          "columns": ["produto", "receita", "data_venda"],
          "where_conditions": [
            {"column": "data_venda", "operator": "LAST_N_DAYS", "value": 30}
          ]
        }
      }
    ],
    "table_name": "vendas_recentes",
    "columns": ["produto", "receita"],
    "column_aggregations": ["none", "sum"],
    "order_by": [{"column": "receita", "direction": "desc"}],
    "limit": 10
  }
}

CTE com consulta salva

Se você possui consultas salvas, pode referenciá-las pelo ID em vez de reescrever o KSQL:

{
  "ksql": {
    "with": [
      {
        "alias": "base_clientes",
        "saved_query_id": 31
      }
    ],
    "table_name": "base_clientes",
    "columns": ["nome", "email", "total_compras"],
    "order_by": [{"column": "total_compras", "direction": "desc"}],
    "limit": 50
  }
}

Múltiplos CTEs

Você pode definir vários CTEs e combiná-los na consulta principal com JOINs:

{
  "ksql": {
    "with": [
      {
        "alias": "receita_produto",
        "ksql": {
          "table_name": "vendas",
          "columns": ["produto_id", "receita"],
          "column_aggregations": ["none", "sum"]
        }
      },
      {
        "alias": "custo_produto",
        "ksql": {
          "table_name": "custos",
          "columns": ["produto_id", "custo_total"],
          "column_aggregations": ["none", "sum"]
        }
      }
    ],
    "table_name": "receita_produto",
    "columns": ["receita_produto.produto_id", "receita_produto.receita", "custo_produto.custo_total"],
    "joins": [
      {
        "tableName": "custo_produto",
        "joinType": "LEFT",
        "conditions": [
          {"leftColumn": "receita_produto.produto_id", "rightColumn": "custo_produto.produto_id"}
        ]
      }
    ]
  }
}

CTEs aninhados

Um CTE pode conter seus próprios CTEs internos, permitindo encadear subconsultas em camadas (um CTE pode referenciar outro CTE já declarado, mas não a si próprio — recursão não é suportada):

{
  "ksql": {
    "with": [
      {
        "alias": "resumo",
        "ksql": {
          "with": [
            {
              "alias": "vendas_mes",
              "ksql": {
                "table_name": "vendas",
                "columns": ["categoria", "receita"],
                "column_aggregations": ["none", "sum"],
                "where_conditions": [
                  {"column": "data_venda", "operator": "LAST_MONTH"}
                ]
              }
            }
          ],
          "table_name": "vendas_mes",
          "columns": ["categoria", "receita"],
          "where_conditions": [
            {"column": "receita", "operator": ">", "value": 1000}
          ]
        }
      }
    ],
    "table_name": "resumo",
    "columns": ["categoria", "receita"],
    "order_by": [{"column": "receita", "direction": "desc"}]
  }
}

⚠️ Todos os CTEs são executados no mesmo banco de dados da consulta principal. As mesmas regras de segurança e validação se aplicam a cada CTE individualmente.

Limites e restrições

RestriçãoValor
Máximo de registros por consulta1.000
Condições de filtroApenas AND
SubconsultasSuportadas via CTEs (parâmetro with)
UNION simplesNão suportado (apenas UNION ALL)

Exemplos completos

Vendas por região no último mês

{
  "ksql": {
    "table_name": "vendas",
    "columns": ["regiao", "receita", "pedidos"],
  "column_aggregations": ["none", "sum", "count"],
  "where_conditions": [
    {"column": "data_venda", "operator": "LAST_MONTH"}
  ],
  "order_by": [{"column": "receita", "direction": "desc"}]
  }
}

Top 10 clientes por valor de compra

{
  "ksql": {
    "table_name": "pedidos",
    "columns": ["pedidos.cliente_id", "clientes.nome", "pedidos.valor"],
  "column_aggregations": ["none", "none", "sum"],
  "joins": [
    {
      "tableName": "clientes",
      "joinType": "LEFT",
      "conditions": [
        {"leftColumn": "pedidos.cliente_id", "rightColumn": "clientes.id"}
      ]
    }
  ],
  "order_by": [{"column": "valor", "direction": "desc"}],
  "limit": 10
  }
}

Filtro com múltiplas condições

{
  "ksql": {
    "table_name": "leads",
    "columns": ["nome", "email", "origem", "score"],
  "where_conditions": [
    {"column": "score", "operator": ">=", "value": 80},
    {"column": "origem", "operator": "IN", "value": ["google", "facebook"]},
    {"column": "email", "operator": "IS NOT NULL"},
    {"column": "criado_em", "operator": "LAST_N_DAYS", "value": 90}
  ],
  "order_by": [{"column": "score", "direction": "desc"}],
  "limit": 1000
  }
}

Consultas KSQL estão em modo beta

Como consultar dados com KSQL no Via Kondado

Aprenda a estruturar consultas KSQL para filtrar, agrupar e transformar dados usando a linguagem de consulta JSON da Kondado.

1
Defina a tabela e colunas base

Inicie sua consulta KSQL informando o table_name e a lista de columns que deseja retornar. Este é o objeto JSON mínimo obrigatório para toda consulta no Via Kondado.

2
Aplique filtros com where_conditions

Use where_conditions para filtrar registros com operadores como =, IN, LIKE, BETWEEN e operadores de data relativa como LAST_N_DAYS. Todas as condições são combinadas com AND automaticamente.

3
Agrupe dados com dimensions e agregações

Para métricas, adicione column_aggregations (sum, avg, count, etc.) e dimensions (equivalente ao GROUP BY). Use "none" nas agregações para colunas de agrupamento.

4
Crie colunas calculadas e transformações

Utilize customColumns para expressões personalizadas (ex: receita - custo) e column_transformations para aplicar conversões de texto, data ou número sequencialmente às colunas existentes.

5
Combine tabelas com JOINs e CTEs

Use joins para unir tabelas com INNER, LEFT, RIGHT, FULL ou CROSS. Para consultas complexas, organize em with (CTEs) — subconsultas nomeadas reutilizáveis que podem ser referenciadas como tabelas, inclusive aninhadas.

6
Ordene, limite e envie para visualização

Finalize com order_by e limit (máximo 1.000 registros). Os resultados podem ser enviados para ferramentas de visualização ou dashboards prontos da Kondado.

Perguntas frequentes

O que é o KSQL e onde ele é usado?
O KSQL é a linguagem de consulta da Kondado, em formato JSON. Você envia uma consulta dentro da chave ksql para filtrar, agrupar, ordenar, unir e transformar os dados da sua Via Kondado, sem precisar escrever SQL diretamente.
Como filtrar por datas relativas no KSQL?
Use operadores de data relativa como LAST_N_DAYS, THIS_MONTH, LAST_QUARTER ou NEXT_N_DAYS dentro de where_conditions. Exemplo: {"column": "criado_em", "operator": "LAST_N_DAYS", "value": 7}.
Posso comparar duas colunas em um filtro?
Sim. Em vez de value, use value_column para comparar uma coluna com outra. Exemplo: {"column": "receita", "operator": ">", "value_column": "custo"}.
Como agregar valores no KSQL?
Preencha column_aggregations com a função desejada para cada coluna (sum, avg, count, count_distinct, min, max, stddev, variance) e use "none" nas colunas de agrupamento. Sempre que houver ao menos uma agregação real, as colunas marcadas como none viram automaticamente as colunas de GROUP BY.
Como funcionam os CTEs (with) no KSQL?
CTEs (Common Table Expressions) são definidos no array with com um alias e um ksql inline ou um saved_query_id. Você pode aninhar CTEs, encadeá-los e referenciá-los em JOINs. Recursão não é suportada.
Como deduplicar resultados sem usar agregações?
Use "distinct": true no nível raiz da consulta — ou dentro de cada with[].ksql e de cada item de union[] (per arm). O KSQL emite SELECT DISTINCT e devolve apenas linhas únicas. A chave distinct não é aceita no nível raiz de uma consulta com union: a deduplicação deve ser declarada arm por arm.
Quais são os principais limites do KSQL?
Máximo de 1.000 registros por consulta, condições de filtro só em AND (sem OR), UNION ALL suportado (sem UNION simples), e subconsultas via CTEs (with). Para deduplicação use a chave distinct; para contagem de únicos, count_distinct.

Escrito por·Publicado em 2026-04-01·Atualizado em 2026-05-27