Todos os produtos
Search
Central de documentação

Realtime Compute for Apache Flink:Kafka connector

Última atualização: Sep 24, 2026

Use o Kafka SQL connector como tabela de origem ou tabela de destino no Realtime Compute for Apache Flink.

Visão geral

O Apache Kafka é uma plataforma de streaming de eventos distribuída e de código aberto, amplamente utilizada para processamento de dados de alto desempenho, análises de streaming e integração de dados. O Kafka connector para Realtime Compute for Apache Flink utiliza o cliente Apache Kafka de código aberto para oferecer alto throughput de dados, suporte à leitura e gravação em múltiplos formatos de dados, e semântica de exactly-once.

Categoria

Descrição

Tipos suportados

SQL source, sink

Flink CDC source, sink

DataStream source, sink

Modo de execução

Streaming

Formatos de dados

Formatos de dados suportados

  • CSV

  • JSON

  • Apache Avro

  • Confluent Avro

  • Debezium JSON

  • Canal JSON

  • Maxwell JSON

  • Raw

  • Protobuf

Nota
  • O formato de dados Protobuf integrado é suportado apenas no Ververica Runtime (VVR) 8.0.9 e versões posteriores.

  • Cada formato de dados suportado possui parâmetros correspondentes que podem ser especificados na cláusula WITH. Para mais informações, consulte Formats.

Métricas

Métricas

  • Source Table

    • numRecordsIn

    • numRecordsInPerSecond

    • numBytesIn

    • numBytesInPerSecond

    • currentEmitEventTimeLag

    • currentFetchEventTimeLag

    • sourceIdleTime

    • pendingRecords

  • Sink Table

    • numRecordsOut

    • numRecordsOutPerSecond

    • numBytesOut

    • numBytesOutPerSecond

    • currentSendTime

Nota

Para mais informações sobre as métricas, consulte Metrics.

Tipos de API

SQL, DataStream, Flink CDC

Atualização/exclusão no sink

O connector suporta apenas a adição de dados a uma tabela de destino. Atualizações e exclusões não são suportadas.

Nota

Para mais informações sobre como atualizar ou excluir dados em uma Sink Table, consulte Upsert Kafka.

Pré-requisitos

Antes de começar, verifique se os pré-requisitos para o tipo de cluster Kafka estão atendidos:

  • Conectar a um cluster ApsaraMQ for Kafka

    • O cluster Kafka deve ser da versão 0.11 ou posterior.

    • Crie um cluster ApsaraMQ for Kafka. Para mais informações, consulte Step 3: Create resources.

    • O workspace do Flink e o cluster Kafka devem estar na mesma Virtual Private Cloud (VPC), e o bloco CIDR do workspace do Flink deve ser adicionado à lista de permissões do ApsaraMQ for Kafka. Para mais informações, consulte Configure whitelists.

    Importante

    Limitações para gravação de dados no ApsaraMQ for Kafka:

    • O ApsaraMQ for Kafka não suporta o formato de compressão Zstandard (zstd) para gravações.

    • O ApsaraMQ for Kafka não suporta gravações idempotentes ou transacionais, o que impede o uso da semântica de exactly-once fornecida pelas Kafka sink tables. A partir do Ververica Runtime (VVR) 8.0.0, o Kafka connector utiliza o cliente Kafka 3.x, no qual a propriedade properties.enable.idempotence tem como padrão true. Portanto, para evitar falhas de gravação ao usar o Ververica Runtime (VVR) 8.0.0 ou posterior para gravar no ApsaraMQ for Kafka, adicione a configuração properties.enable.idempotence=false à definição da sua sink table. Para uma comparação dos mecanismos de armazenamento e das limitações de recursos do ApsaraMQ for Kafka, consulte Comparison between storage engines.

  • Conectar a um cluster Apache Kafka autogerenciado

    • O cluster Apache Kafka autogerenciado deve ser da versão 0.11 ou posterior.

    • O workspace do Flink deve ter conectividade de rede com o cluster Apache Kafka autogerenciado. Para detalhes sobre como conectar a um cluster pela internet pública, consulte FAQ about network connectivity.

    • Somente as opções de configuração de cliente para o Apache Kafka versão 2.8 são suportadas. Para mais informações, consulte a documentação do Apache Kafka sobre Consumer Configs e Producer Configs.

Observações

Gravações transacionais não são recomendadas devido a limitações de design conhecidas no Apache Flink e no Apache Kafka. Ao definir sink.delivery-guarantee = 'exactly-once', o Kafka connector ativa as gravações transacionais, com os seguintes problemas conhecidos:

  • Cada checkpoint gera um novo Transaction ID. Caso o intervalo entre checkpoints seja muito curto, o grande volume de Transaction IDs gerados pode esgotar a memória do coordenador do cluster Kafka, comprometendo sua estabilidade.

  • Cada transação cria uma nova instância de Producer. Se muitas transações forem confirmadas simultaneamente, o TaskManager pode ficar sem memória, desestabilizando o job do Apache Flink.

  • Se múltiplos jobs do Apache Flink utilizarem o mesmo sink.transactional-id-prefix, os Transaction IDs gerados poderão entrar em conflito. Quando uma operação de gravação falha em um job, isso pode impedir o avanço do Log Start Offset (LSO) de uma partição do Apache Kafka, afetando todos os consumidores daquela partição.

Caso necessite de semântica de exactly-once, use o Upsert Kafka connector para gravar em uma tabela de chave primária, garantindo idempotência. Se o uso de gravações transacionais for indispensável, consulte Exactly-once semantics usage notes.

Solucionar problemas de conectividade de rede

O erro Timed out waiting for a node assignment quando um job do Realtime Compute for Apache Flink falha ao iniciar geralmente indica um problema de conectividade de rede entre o Realtime Compute for Apache Flink e o cluster Kafka.

Um cliente Kafka se conecta aos brokers da seguinte forma:

  1. O cliente utiliza os endereços especificados em bootstrap.servers para estabelecer a conexão inicial com o cluster Kafka.

  2. O cluster Kafka retorna os metadados de cada broker, incluindo seus endpoints.

  3. O cliente então usa esses endpoints para se conectar aos brokers e ler ou gravar dados.

Mesmo que os endereços de bootstrap.servers estejam acessíveis, o cliente não conseguirá ler ou gravar dados se o Kafka retornar endpoints de broker incorretos. Esse problema ocorre com frequência em arquiteturas de rede que utilizam proxy, redirecionamento de porta ou linha dedicada.

Etapas de diagnóstico

ApsaraMQ for Kafka

  1. Confirme o tipo de Endpoint

    • Default Endpoint (rede interna)

    • SASL Endpoint (rede interna com autenticação)

    • Public Endpoint (requer solicitação separada)

    Use o recurso Network Probe no console de desenvolvimento do Realtime Compute for Apache Flink para descartar problemas de conectividade com o endereço bootstrap.servers.

  2. Verifique os grupos de segurança e as listas de permissões

    Adicione o bloco CIDR do workspace do Realtime Compute for Apache Flink à lista de permissões da sua instância Kafka. Para mais informações, consulte View VPC CIDR Block e Configure a whitelist.

  3. Verifique a configuração SASL (se habilitada)

    Ao usar um endpoint SASL_SSL, certifique-se de que os mecanismos JAAS, SSL e SASL estejam configurados corretamente no seu job do Realtime Compute for Apache Flink. Sem autenticação adequada, a conexão pode falhar durante a fase de handshake, o que também pode se manifestar como um timeout. Para mais informações, consulte Security and authentication.

Self-managed Kafka

  1. Use o recurso Network Probe****

    Esse recurso permite descartar problemas de conectividade com o endereço bootstrap.servers e verificar se o endpoint interno ou público correto está sendo utilizado.

  2. Verifique os grupos de segurança e as listas de permissões

    • O grupo de segurança da instância do Elastic Compute Service (ECS) deve permitir tráfego de entrada na porta do endpoint Kafka, normalmente 9092 ou 9093.

    • Certifique-se de que qualquer firewall na instância ECS permita tráfego originado da VPC do seu workspace do Realtime Compute for Apache Flink. Para mais informações, consulte View VPC CIDR Block.

  3. Verifique a configuração

    1. Use a ferramenta zkCli.sh ou zookeeper-shell.sh para fazer login no cluster ZooKeeper utilizado pelo Kafka.

    2. Execute um comando para obter os metadados do broker. Por exemplo, execute get /brokers/ids/0. No campo endpoints da resposta, localize o endereço que o Kafka divulga aos clientes.

      
      # bin/zookeeper-shell.sh localhost:2181
      Connecting to localhost:2181
      Welcome to ZooKeeper!
      JLine support is disabled
      
      WATCHER::
      
      WatchedEvent state:SyncConnected type:None path:null
      get /brokers/ids/0
      {"listener_security_protocol_map":{"PLAINTEXT":"PLAINTEXT"},"endpoints":["PLAINTEXT://116.62.xxx:9092"],"jmx_port":-1,"host":"116.62.xxx","timestamp":"1614840078030","port":9092,"version":4}
      
    3. Use o recurso Network Probe no console de desenvolvimento do Realtime Compute for Apache Flink para testar se esse endereço está acessível.

      Nota
      • Se o endereço não estiver acessível, entre em contato com os administradores do Kafka para verificar e corrigir as configurações listeners e advertised.listeners, garantindo que o endereço divulgado seja acessível a partir do Realtime Compute for Apache Flink.

      • Para mais informações sobre conexões de clientes Kafka, consulte Troubleshoot Connectivity.

  4. Verifique a configuração SASL (se habilitada)

    Ao usar um endpoint SASL_SSL, certifique-se de que os mecanismos JAAS, SSL e SASL estejam configurados corretamente no seu job do Realtime Compute for Apache Flink. Sem autenticação adequada, a conexão pode falhar durante a fase de handshake, o que também pode se manifestar como um timeout. Para mais informações, consulte Security and authentication.

SQL

Use o Kafka connector como tabela de origem ou tabela de destino em jobs SQL.

Sintaxe

CREATE TABLE KafkaTable (
  `user_id` BIGINT,
  `item_id` BIGINT,
  `behavior` STRING,
  `ts` TIMESTAMP_LTZ(3) METADATA FROM 'timestamp' VIRTUAL
) WITH (
  'connector' = 'kafka',
  'topic' = 'user_behavior',
  'properties.bootstrap.servers' = 'localhost:9092',
  'properties.group.id' = 'testGroup',
  'scan.startup.mode' = 'earliest-offset',
  'format' = 'csv'
)

Colunas de metadados

Defina colunas de metadados em uma tabela de origem ou de destino para acessar os metadados das mensagens Kafka. Por exemplo, ao assinar múltiplos tópicos, uma coluna de metadados pode identificar de qual tópico cada registro se origina.

CREATE TABLE kafka_source (
  -- Read the message topic as the `record_topic` column
  `record_topic` STRING NOT NULL METADATA FROM 'topic' VIRTUAL,
  -- Read the timestamp from the ConsumerRecord as the `ts` column
  `ts` TIMESTAMP_LTZ(3) METADATA FROM 'timestamp' VIRTUAL,
  -- Read the message offset as the `record_offset` column
  `record_offset` BIGINT NOT NULL METADATA FROM 'offset' VIRTUAL,
  ...
) WITH (
  'connector' = 'kafka',
  ...
);

CREATE TABLE kafka_sink (
  -- Write the timestamp from the `ts` column as the ProducerRecord's timestamp to Kafka
  `ts` TIMESTAMP_LTZ(3) METADATA FROM 'timestamp' VIRTUAL,
  ...
) WITH (
  'connector' = 'kafka',
  ...
);

A tabela a seguir lista as colunas de metadados suportadas pelas tabelas de origem e de destino do Kafka.

Chave

Tipo

Descrição

Escopo

topic

STRING NOT NULL METADATA VIRTUAL

Tópico da mensagem.

Tabela de origem

partition

INT NOT NULL METADATA VIRTUAL

ID da partição da mensagem.

Tabela de origem

headers

MAP<STRING, BYTES> NOT NULL METADATA VIRTUAL

Cabeçalhos da mensagem.

Tabela de origem e tabela de destino

leader-epoch

INT NOT NULL METADATA VIRTUAL

Leader-epoch da mensagem.

Tabela de origem

offset

BIGINT NOT NULL METADATA VIRTUAL

Offset da mensagem.

Tabela de origem

timestamp

TIMESTAMP(3) WITH LOCAL TIME ZONE NOT NULL METADATA VIRTUAL

Timestamp da mensagem.

Tabela de origem e tabela de destino

timestamp-type

STRING NOT NULL METADATA VIRTUAL

Tipo de timestamp da mensagem. Os valores válidos são:

  • NoTimestampType: Nenhum timestamp está definido na mensagem.

  • CreateTime: O momento em que a mensagem foi criada.

  • LogAppendTime: O momento em que a mensagem foi adicionada ao log do broker Kafka.

Tabela de origem

__raw_key__

STRING NOT NULL METADATA VIRTUAL

Chave bruta da mensagem.

Tabela de origem e tabela de destino

Nota

Este parâmetro é suportado apenas no Ververica Runtime (VVR) 11.4 e versões posteriores.

__raw_value__

STRING NOT NULL METADATA VIRTUAL

Valor bruto da mensagem.

Tabela de origem e tabela de destino

Nota

Este parâmetro é suportado apenas no Ververica Runtime (VVR) 11.4 e versões posteriores.

Opções do conector

  • General

    Option

    Description

    Type

    Required

    Default

    Remarks

    connector

    Tipo do conector.

    String

    Yes

    –

    O valor deve ser kafka.

    properties.bootstrap.servers

    Lista de endereços dos brokers Kafka.

    String

    Yes

    –

    Formato: host1:port1,host2:port2,.... Separe os endereços com vírgulas (,).

    properties.*

    Propriedades adicionais para o cliente Kafka.

    String

    No

    –

    As chaves de propriedade devem ser opções válidas definidas na documentação oficial do Apache Kafka para Producer Configs e Consumer Configs.

    O Realtime Compute for Apache Flink remove o prefixo properties. e repassa os pares chave-valor restantes ao cliente Kafka subjacente. Por exemplo, defina 'properties.allow.auto.create.topics' = 'false' para desativar a criação automática de tópicos.

    O conector Kafka sobrescreve as opções a seguir, portanto não é possível configurá-las por este meio:

    • key.deserializer

    • value.deserializer

    format

    Formato para serialização e desserialização do valor de uma mensagem Kafka.

    String

    No

    –

    Formatos suportados:

    • csv

    • json

    • avro

    • debezium-json

    • canal-json

    • maxwell-json

    • avro-confluent

    • raw

    Nota

    Para mais informações, consulte Opções de formato.

    key.format

    Formato para serialização e desserialização da chave de uma mensagem Kafka.

    String

    No

    –

    Formatos suportados:

    • csv

    • json

    • avro

    • debezium-json

    • canal-json

    • maxwell-json

    • avro-confluent

    • raw

    Nota

    Ao usar esta configuração, key.options é obrigatório.

    key.fields

    Campos do schema da tabela a serem usados como chave da mensagem Kafka.

    String

    No

    –

    Separe múltiplos nomes de campo com ponto e vírgula (;). Por exemplo, 'field1;field2'.

    key.fields-prefix

    Prefixo personalizado para todos os campos de chave, evitando conflitos de nomes com os campos de valor.

    String

    No

    –

    Este prefixo distingue os campos de chave dos campos de valor. Ele é removido antes da serialização da chave ou após a desserialização.

    Nota

    Ao usar esta opção, value.fields-include deve ser definido como EXCEPT_KEY.

    value.format

    Formato para serialização e desserialização do valor de uma mensagem Kafka.

    String

    No

    –

    Esta configuração equivale a format. Defina apenas uma das opções: format ou value.format. Se ambas forem configuradas, value.format tem precedência sobre format.

    value.fields-include

    Define se os campos de chave são incluídos no formato de valor.

    String

    No

    ALL

    Valores válidos:

    • ALL: O valor da mensagem Kafka inclui todas as colunas da tabela.

    • EXCEPT_KEY: O valor da mensagem Kafka inclui todas as colunas da tabela, exceto as definidas em key.fields.

  • Source table

    Option

    Description

    Type

    Required

    Default

    Remarks

    topic

    Tópico ou tópicos a serem lidos.

    String

    No

    –

    Para assinar múltiplos tópicos, separe os nomes com ponto e vírgula (;), por exemplo, 'topic-1;topic-2'.

    Nota

    Especifique esta opção ou topic-pattern, mas não ambas.

    topic-pattern

    Expressão regular que corresponde aos tópicos a serem assinados. O consumidor assina todos os tópicos cujos nomes correspondam a este padrão.

    String

    No

    –

    Exemplos:

    • user_event_.*: Corresponde a todos os tópicos com o prefixo user_event_.

    • prod\.logs\..*: Corresponde a tópicos com o prefixo prod.logs. (o caractere . deve ser escapado).

    Nota

    Especifique esta opção ou topic, mas não ambas.

    properties.group.id

    ID do grupo de consumidores da source Kafka.

    String

    No

    KafkaSource-{Source-Table-Name}

    Ao usar um ID de grupo de consumidores pela primeira vez, defina também properties.auto.offset.reset como earliest ou latest para estabelecer o offset inicial de leitura.

    scan.startup.mode

    Offset de inicialização do consumidor Kafka.

    String

    No

    group-offsets

    Valores válidos:

    • earliest-offset: Inicia a leitura a partir do offset mais antigo disponível.

    • latest-offset: Inicia a leitura a partir do offset mais recente.

    • group-offsets: Inicia a leitura a partir dos offsets confirmados do properties.group.id especificado.

    • timestamp: Inicia a leitura a partir do valor especificado em scan.startup.timestamp-millis.

    • specific-offsets: Inicia a leitura a partir dos offsets definidos em scan.startup.specific-offsets.

    Nota

    Esta opção aplica-se apenas quando um job é iniciado sem estado. Se um job retomar a partir de um checkpoint, a leitura começa pelos offsets armazenados no estado do checkpoint.

    scan.startup.specific-offsets

    Offset de início por partição quando scan.startup.mode é specific-offsets.

    String

    No

    –

    Por exemplo, partition:0,offset:42;partition:1,offset:300

    scan.startup.timestamp-millis

    Timestamp de início em milissegundos quando scan.startup.mode está definido como timestamp.

    Long

    No

    –

    A unidade é milissegundos.

    scan.topic-partition-discovery.interval

    Intervalo de descoberta de partições.

    Duration

    No

    5 minutes

    O conector descobre e lê periodicamente novas partições. Ao usar topic-pattern, o conector também detecta novos tópicos que correspondam ao padrão. Defina o intervalo como um valor não positivo para desativar este recurso.

    Nota

    No Ververica Runtime (VVR) 6.0.x, a descoberta dinâmica de partições está desativada por padrão. A partir do VVR 8.0, este recurso é ativado por padrão com um intervalo de descoberta de 5 minutos.

    scan.header-filter

    Filtra mensagens com base nos cabeçalhos da mensagem Kafka.

    String

    No

    –

    A chave e o valor do cabeçalho são separados por dois-pontos (:). Múltiplas condições de cabeçalho são conectadas por operadores lógicos (& e |). O operador lógico NOT (!) também é suportado. Por exemplo, depart:toy|depart:book&!env:test retém os dados Kafka se o cabeçalho contiver depart=toy ou depart=book e não contiver env=test.

    Nota
    • Esta opção é suportada apenas no Ververica Runtime (VVR) 8.0.6 e versões posteriores.

    • Parênteses em expressões não são suportados.

    • As operações lógicas são avaliadas da esquerda para a direita.

    • Os valores dos cabeçalhos são convertidos para strings UTF-8 para comparação.

    scan.check.duplicated.group.id

    Verifica se outro consumidor ativo já está usando o properties.group.id.

    Boolean

    No

    false

    Valores válidos:

    • true: Antes de iniciar o job, o sistema verifica a existência de um grupo de consumidores duplicado. Se encontrado, o job falha para evitar conflitos.

    • false: Inicia o job sem verificar conflitos.

    Nota

    Esta opção é suportada apenas no Ververica Runtime (VVR) 6.0.4 e versões posteriores.

  • Sink table

    Option

    Description

    Type

    Required

    Default

    Remarks

    topic

    Tópico de destino.

    String

    Yes

    –

    –

    sink.partitioner

    Mapeia registros de instâncias paralelas do sink para partições Kafka.

    String

    No

    default

    Valores válidos:

    • default: Usa o particionador padrão do Kafka.

    • ### **Confirmação de offsets do source** A tabela source do Kafka confirma o offset do consumidor no cluster Kafka somente após um checkpoint bem-sucedido. Por isso, intervalos longos de checkpoint fazem com que o offset confirmado fique defasado. O progresso real de leitura fica armazenado no estado do checkpoint, que o sistema utiliza para recuperação de falhas. Os offsets confirmados servem apenas como monitor de progresso e não são usados na recuperação — portanto, falhas de confirmação não afetam a precisão dos dados. ### **Partitioner customizado para sink** Se a estratégia de particionamento nativa do Kafka não atender às suas necessidades, implemente um partitioner customizado estendendo a classe [FlinkKafkaPartitioner](https://github.com/apache/flink-connector-kafka/blob/369e7be46a70fd50d68746498aed82105741e7d6/flink-connector-kafka/src/main/java/org/apache/flink/streaming/connectors/kafka/partitioner/FlinkKafkaPartitioner.java). Após o desenvolvimento, compile o código em um pacote JAR e faça o upload usando o recurso [Artifacts](t2740613.xdita#) no console do Realtime Compute. Com o pacote JAR carregado e referenciado, defina o parâmetro sink.partitioner na cláusula WITH com o nome completo e qualificado da sua classe de partitioner, por exemplo, `org.mycompany.MyPartitioner`. ### **Kafka, Upsert Kafka e Kafka JSON catalog** O Kafka é uma plataforma de streaming de eventos append-only que não suporta atualizações nem exclusões de dados. Em SQL de streaming, uma tabela sink Kafka padrão não consegue lidar com dados de Change Data Capture (CDC) provenientes de upstream nem com a lógica de retração de operadores como aggregate e join. Quando for necessário gravar dados que contenham alterações ou retrações, utilize uma tabela sink [Upsert Kafka](t2306784.dita#concept_2306784). Para simplificar a sincronização em lote de dados de Change Data Capture (CDC) de uma ou mais tabelas de banco de dados upstream para o Kafka, use um Kafka JSON catalog. Se os dados armazenados no Kafka estiverem em formato JSON, o Kafka JSON catalog permite pular a etapa de definição de schema e dos parâmetros WITH. Consulte [Manage Kafka JSON catalogs](t2212019.dita#task_2159375) para mais detalhes. ### **Exemplos** #### **Exemplo 1: Leitura e escrita no Kafka** Este exemplo lê dados de um tópico Kafka de source e os grava em um tópico de sink. Os dados estão no formato CSV. ```sql CREATE TEMPORARY TABLE kafka_source ( id INT, name STRING, age INT ) WITH ( 'connector' = 'kafka', 'topic' = 'source', 'properties.bootstrap.servers' = '', 'properties.group.id' = '', 'format' = 'csv' ); CREATE TEMPORARY TABLE kafka_sink ( id INT, name STRING, age INT ) WITH ( 'connector' = 'kafka', 'topic' = 'sink', 'properties.bootstrap.servers' = '', 'properties.group.id' = '', 'format' = 'csv' ); INSERT INTO kafka_sink SELECT id, name, age FROM kafka_source; ``` #### **Exemplo 2: Sincronização de schema e dados de tabela** Use o conector Kafka para sincronizar mensagens de um tópico Kafka para o Hologres em tempo real. Para evitar mensagens duplicadas no Hologres durante um failover, utilize o offset e o ID de partição das mensagens Kafka como chave primária composta. ```sql CREATE TEMPORARY TABLE kafkaTable ( `offset` INT NOT NULL METADATA, `part` BIGINT NOT NULL METADATA FROM 'partition', PRIMARY KEY (`part`, `offset`) NOT ENFORCED ) WITH ( 'connector' = 'kafka', 'properties.bootstrap.servers' = '', 'topic' = 'kafka_evolution_demo', 'scan.startup.mode' = 'earliest-offset', 'format' = 'json', 'json.infer-schema.flatten-nested-columns.enable' = 'true' -- Optional. Flattens all nested columns. ); CREATE TABLE IF NOT EXISTS hologres.kafka.`sync_kafka` WITH ( 'connector' = 'hologres' ) AS TABLE vvp.`default`.kafkaTable; ``` #### **Exemplo 3: Sincronização de chaves e valores do Kafka** Se a chave de uma mensagem Kafka contiver informações relevantes, sincronize tanto a chave quanto o valor. ```sql CREATE TEMPORARY TABLE kafkaTable ( `key_id` INT NOT NULL, `val_name` VARCHAR(200) ) WITH ( 'connector' = 'kafka', 'properties.bootstrap.servers' = '', 'topic' = 'kafka_evolution_demo', 'scan.startup.mode' = 'earliest-offset', 'key.format' = 'json', 'value.format' = 'json', 'key.fields' = 'key_id', 'key.fields-prefix' = 'key_', 'value.fields-prefix' = 'val_', 'value.fields-include' = 'EXCEPT_KEY' ); CREATE TABLE IF NOT EXISTS hologres.kafka.`sync_kafka`( WITH ( 'connector' = 'hologres' ) AS TABLE vvp.`default`.kafkaTable; ```
      Nota

      As chaves de mensagens do Kafka não suportam Schema Evolution nem análise automática de tipos. Declare o schema manualmente.

      #### **Exemplo 4: Sincronização de dados com transformações** Ao sincronizar dados do Kafka para o Hologres, pode ser necessário aplicar transformações leves. ```sql CREATE TEMPORARY TABLE kafkaTable ( `distinct_id` INT NOT NULL, `properties` STRING, `timestamp` TIMESTAMP_LTZ METADATA, `date` AS CAST(`timestamp` AS DATE) ) WITH ( 'connector' = 'kafka', 'properties.bootstrap.servers' = '', 'topic' = 'kafka_evolution_demo', 'scan.startup.mode' = 'earliest-offset', 'key.format' = 'json', 'value.format' = 'json', 'key.fields' = 'key_id', 'key.fields-prefix' = 'key_' ); CREATE TABLE IF NOT EXISTS hologres.kafka.`sync_kafka` WITH ( 'connector' = 'hologres' ) AS TABLE vvp.`default`.kafkaTable ADD COLUMN `order_id` AS COALESCE(JSON_VALUE(`properties`, '$.order_id'), 'default'); --Use COALESCE to handle null values. ``` #### **Exemplo 5: Análise de JSON aninhado** A seguir, um exemplo de mensagem JSON: ```json { "id": 101, "name": "VVP", "properties": { "owner": "Alibaba Cloud", "engine": "Flink" } } ``` Para evitar o uso de funções como `JSON_VALUE(payload, '$.properties.owner')` para analisar campos, defina a estrutura diretamente no DDL do Source: ```sql CREATE TEMPORARY TABLE kafka_source ( id VARCHAR, `name` VARCHAR, properties ROW<`owner` STRING, engine STRING> ) WITH ( 'connector' = 'kafka', 'topic' = 'xxx', 'properties.bootstrap.servers' = 'xxx', 'scan.startup.mode' = 'earliest-offset', 'format' = 'json' ); ``` Com essa abordagem, o Flink analisa o JSON em campos estruturados durante a fase de leitura. As consultas SQL subsequentes podem referenciar diretamente `properties.owner` sem chamadas adicionais de funções, o que melhora o desempenho geral. ## Semântica exactly-once
    • Configure o nível de isolamento do consumidor Todas as aplicações que consomem dados do Kafka devem definir a propriedade isolation.level: read_committed: Lê apenas dados confirmados.

    • read_uncommitted (Padrão): Permite a leitura de dados não confirmados.

    • O modo EXACTLY_ONCE depende de `read_committed`. Sem essa configuração, os consumidores podem enxergar dados não confirmados, comprometendo a consistência.
    • Timeout de transação e perda de dados Ao recuperar de um checkpoint, o Realtime Compute for Apache Flink considera apenas as transações confirmadas antes do início daquele checkpoint. Se o intervalo entre a falha do job e sua reinicialização exceder o timeout de transação do Kafka, o Kafka aborta automaticamente a transação aberta, podendo resultar em perda de dados. O valor padrão de transaction.max.timeout.ms para um broker Kafka é de 15 minutos.

    • Por padrão, o Flink Kafka Sink define o parâmetro transaction.timeout.ms como 1 hora.

    • Aumente o valor de transaction.max.timeout.ms no broker para que seja maior ou igual à configuração definida no Flink.

    • Pool de produtores e checkpoints concorrentes O modo EXACTLY_ONCE utiliza um pool de produtores Kafka de tamanho fixo. Cada checkpoint consome um produtor desse pool. Se o número de checkpoints concorrentes exceder o tamanho do pool, o job falhará. Dimensione o pool de produtores com base no número máximo de checkpoints concorrentes.

    • Restrições para redução de paralelismo Se um job falhar antes de o primeiro checkpoint ser concluído, as informações do pool de produtores original serão perdidas na reinicialização. Portanto, não reduza o paralelismo do job antes que o primeiro checkpoint seja concluído. Caso a redução seja inevitável, o novo paralelismo não deve ser inferior a FlinkKafkaProducer.SAFE_SCALE_DOWN_FACTOR.

    • Transações bloqueiam leituras No modo read_committed, qualquer transação que não tenha sido confirmada ou abortada bloqueia as operações de leitura em todo o tópico. Por exemplo: A Transação 1 grava dados.

    • A Transação 2 grava mais dados e é confirmada.

    • Enquanto a Transação 1 permanecer aberta, os dados da Transação 2 — já confirmada — ficam invisíveis para os consumidores.

    • Esse comportamento traz as seguintes implicações:
    • Em operação normal, a latência de visibilidade dos dados é aproximadamente igual ao intervalo de checkpoint.

    • Se um job falhar, qualquer tópico em que ele estivesse gravando ficará bloqueado para os consumidores até que o job seja reiniciado ou a transação expire. Em casos extremos, o próprio processo de expiração da transação também pode afetar as operações de leitura.

    • ## FAQ
    • How do I retrieve JSON data from Kafka using Realtime Compute for Apache Flink?

    • Why does an Event Time-based Window produce no output for a ApsaraMQ for Kafka Source Table?

    • How do I connect to a secured Kafka Cluster?

    • How do I resolve field name conflicts?

    • Workspaces and Namespaces