Modelado de datos con Kafka? Temas y Particiones


Una de las primeras cosas en las que pienso cuando uso un nuevo servicio (como un almacén de datos que no sea RDBMS o una cola de mensajes) es: "¿Cómo debo estructurar mis datos?".

He leído y visto algunos materiales introductorios. En particular, tomemos, por ejemplo, Kafka: un Sistema de Mensajería Distribuida para el Procesamiento de Registros, que escribe:

  • "un tema es el contenedor con el que se asocian los mensajes"
  • "la unidad más pequeña de paralelismo es la partición de un tema. Esto implica que todos los mensajes que ... pertenecer a una partición particular de un tema será consumido por un consumidor en un grupo de consumidores."

Sabiendo esto, ¿cuál sería un buen ejemplo que ilustra cómo usar temas y particiones? ¿Cuándo debería ser un tema algo? Cuando debería ser algo una partición?

Como ejemplo, digamos que mis datos (Clojure) se ven como:

{:user-id 101 :viewed "/page1.html" :at #inst "2013-04-12T23:20:50.22Z"}
{:user-id 102 :viewed "/page2.html" :at #inst "2013-04-12T23:20:55.50Z"}

¿Debería el tema basarse en user-id? viewed? at? ¿Qué hay de la partición?

¿Cómo Decido?

 142
Author: David J., 2013-06-20

4 answers

Al estructurar sus datos para Kafka, realmente depende de cómo se debe consumir.

En mi mente, un tema es una agrupación de mensajes de un tipo similar que serán consumidos por el mismo tipo de consumidor, por lo que en el ejemplo anterior, solo tendría un solo tema y si decide enviar algún otro tipo de datos a través de Kafka, puede agregar un nuevo tema para eso más adelante.

Los temas están registrados en ZooKeeper, lo que significa que puede tener problemas si intenta agregar también muchos de ellos, por ejemplo, el caso en el que tienes un millón de usuarios y has decidido crear un tema por usuario.

Particiones por otro lado es una forma de paralelizar el consumo de los mensajes y el número total de particiones en un clúster de broker debe ser al menos el mismo que el número de consumidores en un grupo de consumidores para dar sentido a la función de partición. Los consumidores de un grupo de consumidores dividirán la carga del procesamiento del tema entre ellos de acuerdo con la partición para que un consumidor solo se preocupe por los mensajes en la partición en sí está "asignado a".

El particionamiento se puede establecer explícitamente usando una clave de partición en el lado productor o si no se proporciona, se seleccionará una partición aleatoria para cada mensaje.

 118
Author: Lundahl,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2013-06-20 13:57:03

Una vez que sepa cómo particionar su flujo de eventos, el nombre del tema será fácil, así que respondamos esa pregunta primero.

@Ludd es correcto - la estructura de partición que elija dependerá en gran medida de cómo desee procesar la secuencia de eventos. Idealmente, desea una clave de partición, lo que significa que su procesamiento de eventos es partition-local.

Por ejemplo:

  1. Si se preocupa por el tiempo promedio de los usuarios en el sitio, entonces debe particionar por :user-id. De esa manera, todos los eventos relacionados con la actividad del sitio de un solo usuario estarán disponibles dentro de la misma partición. Esto significa que un motor de procesamiento de secuencias como Apache Samza puede calcular el tiempo promedio en el sitio para un usuario determinado simplemente mirando los eventos en una sola partición. Esto evita tener que realizar cualquier tipo de costoso proceso de partición -global
  2. Si le importan las páginas más populares de su sitio web, debe particionar por la página :viewed. De nuevo, Samza será capaz de mantener un recuento de las vistas de una página dada con solo mirar los eventos en una sola partición

Generalmente, estamos tratando de evitar tener que confiar en el estado global (como mantener los recuentos en una base de datos remota como DynamoDB o Cassandra), y en su lugar ser capaces de trabajar utilizando el estado local de partición. Esto se debe a que el estado local es una primitiva fundamental en el procesamiento de flujos.

Si necesita los dos casos de uso anteriores, entonces un patrón común con Kafka es primero partición por decir :user-id y luego re-partición por :viewed listo para la siguiente fase de procesamiento.

En los nombres de los temas - uno obvio aquí sería events o user-events. Para ser más específico, podría ir con events-by-user-id y/o events-by-viewed.

 46
Author: Alex Dean,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2015-02-24 17:11:39

Creo que el nombre del tema es una conclusión de un tipo de mensajes, y el productor publica el mensaje al tema y el consumidor suscribe el mensaje a través de subscribe topic.

Un tema puede tener muchas particiones. la partición es buena para el paralelismo. la partición también es la unidad de replicación, por lo que en Kafka, líder y seguidor también se dice a nivel de partición. En realidad, una partición es una cola ordenada cuyo orden es el orden de llegada del mensaje. Y el tema está compuesto por una o más colas en una palabra simple. Esto es útil para modelar nuestra estructura.

Kafka es desarrollado por LinkedIn para la agregación y entrega de registros. esta escena es muy buena como ejemplo.

Los eventos del usuario en su web o aplicación pueden ser registrados por su servidor web y luego enviados a Kafka broker a través del productor. En producer, puede especificar el método de partición, por ejemplo: tipo de evento (se guarda un evento diferente en una partición diferente) o tiempo de evento (particionar un día en un período diferente según su lógica de aplicación) o tipo de usuario o simplemente sin lógica y equilibrar todos los registros en muchas particiones.

Sobre su caso en cuestión, puede crear un tema llamado "page-view-event" y crear N particiones a través de claves hash para distribuir los registros en todas las particiones de manera uniforme. O usted podría elegir una lógica de partición para hacer que el registro de distribución por su espíritu.

 3
Author: GuangshengZuo,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2017-07-21 03:34:45

Esto no está exactamente relacionado con la pregunta, pero en caso de que ya haya decidido la segregación lógica de registros basados en temas, y desee optimizar el conteo de temas/particiones en Kafka, este blog podría ser útil.

Conclusiones clave en pocas palabras:

  • En general, cuantas más particiones haya en un clúster de Kafka, mayor será el rendimiento que se pueda lograr. Deje que el máximo a lo largo alcanzable en una sola partición para la producción sea p y consumo c. Digamos que su rendimiento objetivo es t. A continuación, deberá tener, al menos, max(t/p, t/c) las particiones.

  • Actualmente, en Kafka, cada broker abre un manejador de archivo tanto del índice como del archivo de datos de cada segmento de registro. Por lo tanto, cuantas más particiones, mayor es la necesidad de configurar el archivo abierto handle limit en el sistema operativo subyacente. Por ejemplo, en nuestro sistema de producción, una vez vimos un error que decía too many files are open, mientras que teníamos alrededor de 3600 particiones temáticas.

  • Cuando un broker se cierra sin limpiar (por ejemplo, kill -9), la indisponibilidad observada podría ser proporcional al número de particiones.

  • La latencia de extremo a extremo en Kafka se define por el tiempo desde que el productor publica un mensaje hasta que el consumidor lee el mensaje. Como regla de thumb, si le importa la latencia, probablemente sea una buena idea limitar el número de particiones por corredor a 100 x b x r, donde b es el número de corredores en un clúster de Kafka y r es el factor de replicación.

 1
Author: Bitswazsky,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2018-03-05 08:07:20