Realtime: Caso de uso: sincronización con Elasticsearch / Solr

Creado en 26 ago. 2020  ·  6Comentarios  ·  Fuente: supabase/realtime

https://github.com/supabase/realtime/issues/40#issuecomment -680699263

¿Puede desarrollar un poco su caso de uso particular? Ayudará con nuestra planificación y mejoras. No dude en comenzar un nuevo problema si no he abordado correctamente su pregunta aquí.

Hola @kiwicopple. Actualmente estoy en una etapa exploratoria siguiendo un requisito para sincronizar datos de PostgreSQL a Solr o Elasticsearch y ver qué hay disponible. Sabía que la replicación lógica era el único camino a seguir, pero necesitaba explorar las soluciones existentes. Escuché sobre supabase en tiempo real hace un año, así que estuve pateando los neumáticos para ver qué podía hacer.

Mi idea era suscribirme a tablas de interés y actualizar o insertar registros en ES / Solr. Obviamente, se prefiere la entrega garantizada para esto. No me gusta la idea de tener que sincronizar ocasionalmente cientos de miles de correos electrónicos que _podría_ estar desincronizados.

Sin embargo, al explorar supabase/realtime , veo cómo podría ser beneficioso para otros aspectos de un producto en el que estoy trabajando.

• Suscribirse a tablas en lugar de crear muchos activadores de NOTIFY (como lo hacemos actualmente en producción).

Una cosa que resaltó sobre esto es que el tamaño de la carga útil que incluye el objeto types , aunque es útil, realmente suma miles de registros (incluso más si está recibiendo el registro VIEJO). Creo que preferiría que al suscribirme pudiera solicitar datos específicos.

Esto parece discutirse en parte aquí: https://github.com/supabase/realtime/issues/47 pero eso parece estar filtrando datos condicionalmente (lo cual es bueno). Lo que me parecería útil sería solicitar un subconjunto de los datos, por lo que, opcionalmente, solo se debe transmitir lo mínimo entre el servidor y el cliente en tiempo real. Un lenguaje de consulta y transformación JSON como https://github.com/schibsted/jslt o https://github.com/jsonata-js/jsonata sería ideal, ya que esto podría pasarse como un argumento en la suscripción y transformar los datos en el lado del servidor. No sé que hay bibliotecas equivalentes disponibles en Elixir.

Pregunta:
Supongo que el enfoque preferido para reducir la carga en el servidor y la salida de transmisión de PostrgreSQL es crear solo una publicación para un subconjunto de tablas en lugar de CREATE PUBLICATION supabase_realtime FOR ALL TABLES; ?

Una cosa más: estamos planeando la prueba de referencia como un requisito para pasar de alfa a beta.

Por cierto, las casillas de verificación en el archivo README para este repositorio sugieren que ya está en Beta (https://github.com/supabase/realtime#status) pero el párrafo siguiente sugiere lo contrario. No leí el párrafo a continuación originalmente y solo las casillas de verificación, así que pensé que estabas en Beta. :)

question

Comentario más útil

Soy reacio a llamarlo entrega garantizada, porque una vez que lo envía a ES, no esperará un acuse de recibo.

Creo que tendría sentido para mí manejar las escrituras en Solr en lugar de usar crear un webhook en el servidor. Necesitaría actualizar Solr FIFO pero leí en https://github.com/supabase/realtime/issues/33#issuecomment -635010703 que sugirió webhooks que no devuelven 2XX que se escribe un registro en algún lugar. Eso rompería el orden de los registros que actualizan los documentos relevantes en Solr, lo cual no es ideal.

Como nota al margen, si los registros que no se reenvían correctamente a un webhook no se consultan fácilmente (y opcionalmente se extraen), creo que esto podría ser un problema. Obviamente, un registro es genial, pero me gustaría ver algunas estadísticas si algunos webhooks fallan por cualquier motivo. Sería útil sondear programáticamente el servidor en busca de webhooks fallidos, pero luego está cambiando la simplicidad del servidor. Suena cada vez más como si acabara teniendo que escribir una cola de trabajos para los webhooks, lo cual no es trivial. O al menos garantizar las escrituras en _en algún lugar_ para que los eventos no se pierdan.

Los valores de la carga útil son todas cadenas, por lo que podría ser más útil universalmente agregar una bandera booleana como PARSE_PAYLOAD, y si es verdadero, este servidor podría analizar la carga útil en los tipos correctos, eliminando la clave de las columnas por completo.

Analizar la carga útil en los tipos correctos puede ser útil, pero no diría que es necesario. Un transformador JSON permitiría a alguien seleccionar propiedades de manera que en una tabla de 30 columnas, solo devuelva 3 y también pueda cambiar el nombre de las columnas en el proceso.

el almacenamiento es más barato que la computación

Por lo tanto, puede que no sea la mejor idea si solo se trata de ahorrar espacio en una base de datos. ¿Alguna razón por la que no pudo limpiar la columna de la carga útil después de que aterrizó en ES?

Cuando mencioné el tamaño de la carga útil, no estaba hablando de almacenarlo, estaba literalmente hablando del tamaño de la carga útil que se envía a través de las interfaces. El tráfico de red entre hosts.

Si tengo un servidor de base de datos y pongo supabase/realtime allí, luego de tener un servidor websocket consumidor en un host diferente, obtendré muchos datos enviados entre los hosts. Es muy posible que esté tirando muchos de esos datos, por lo que sería más eficaz para mí volver a enviar NOTIFY desde los activadores. Pero luego pierdo algo de la flexibilidad que supabase/realtime me estaba dando originalmente al no tener que seguir cambiando las migraciones de la base de datos para agregar / eliminar columnas de la carga útil NOTIFY . Como se discutió, los transformadores JSON realmente brillarían aquí.

En caso de que no vea esto, hay un límite de 8000 bytes para las cargas útiles NOTIFICAR

Ja, sí. Me encontré con esto cuando intentaba enviar correos electrónicos almacenados en la base de datos a través de las notificaciones. Quiero decir, tiene sentido mantener el rendimiento, pero en ese momento era un rasguño de cabeza.

Exploraré un transformador JSON con uno de nuestro equipo y te lo haré saber. Podría llevar algo de tiempo, pero creo que vale la pena considerarlo como parte de nuestro trabajo en el n. ° 47.

Buena cosa.

Apéndice

Para cualquier otra persona que pueda tropezar con este problema en busca de una forma de sincronizar PostgreSQL con ES / Solr, https://debezium.io/ parece una buena alternativa. Esperaba no agregar demasiado a la pila porque esto se convierte en: ES / Solr, Debezium, Zookeeper, Kafka, pero supongo que ese es el precio que debe pagar por la entrega garantizada en este caso.

Todos 6 comentarios

Hola @kwakwaversal, gracias por la increíble

las casillas de verificación en el archivo README de este repositorio sugieren que ya está en Beta

UPS. ¡Gracias por el aviso! Estamos estandarizando los estados de publicación en toda la organización. Lo cambié de nuevo a alfa; creo que es una representación más justa del estado del servidor, pero también de Supabase en su conjunto. Pasaremos a Beta una vez que tengamos algunos puntos de referencia y, lo que es más importante, contrataremos a alguien que pueda respaldar este repositorio a tiempo completo (somos un equipo muy pequeño en este momento)

actualizar o insertar registros en ES / Solr. Obviamente, se prefiere la entrega garantizada para esto.

Muy genial. Este será factible con los webhooks (https://github.com/supabase/realtime/issues/33). Una vez que resuelva el problema con la reutilización de las ranuras de replicación (https://github.com/supabase/realtime/issues/22), habrá garantizado la lectura de Postgres y el envío . Soy reacio a llamarlo entrega garantizada, porque una vez que lo envía a ES, no esperará un acuse de recibo. Si la carga útil no llega a ES (por cualquier motivo), el evento de cambio también se pierde. Esto podría ser algo en lo que trabajemos en el futuro, pero será un avance importante (ya que requiere persistencia).

el tamaño de la carga útil, incluido el objeto de tipos, si bien es útil, realmente suma más de miles de registros (incluso más si está recibiendo el registro ANTIGUO)

Interesante, también uno en el que no había pensado. Profundizaré en la idea de un transformador JSON. Los valores de la carga útil son todas cadenas, por lo que podría ser más universalmente útil agregar una bandera booleana como PARSE_PAYLOAD , y si es verdadero, este servidor podría analizar la carga útil en los tipos correctos, soltando la clave columns en total. Esto tendrá un impacto en el rendimiento, por lo que tendremos que sopesarlo. También perdería muchos detalles (¿es smallint o bigint ?), Pero en muchos casos eso no importará.

Mis pensamientos iniciales sobre esto:

  • el almacenamiento es más barato que la computación
  • el rendimiento es importante

Por lo tanto, puede que no sea la mejor idea si solo se trata de ahorrar espacio en una base de datos. ¿Alguna razón por la que no pudo limpiar el column de la carga útil después de que aterrizó en ES?

Supongo que el enfoque preferido para reducir la carga en el servidor y la salida de transmisión de PostrgreSQL es crear solo una publicación para un subconjunto de tablas

Si eso es correcto. Si hay tablas que no le interesan en la transmisión, simplemente no habilite la replicación. ¡Avíseme si eso es un problema para su caso de uso!

Suscribirse a tablas en lugar de crear muchos desencadenantes NOTIFY (como lo hacemos actualmente en producción).

En caso de que no vea esto, hay un límite de 8000 bytes para las cargas útiles NOTIFICAR, así que tenga cuidado de que su sistema no descarte los eventos de manera silenciosa. Postgres en realidad genera un error, pero es difícil de detectar. Esta es la razón exacta por la que creamos Realtime el año pasado: estaba usando trigger / NOTIFY y descubrí esto de la manera más difícil.

Próximos pasos

Exploraré un transformador JSON con uno de nuestro equipo y te lo haré saber. Podría llevar algo de tiempo, pero creo que vale la pena considerarlo como parte de nuestro trabajo en https://github.com/supabase/realtime/issues/47

Soy reacio a llamarlo entrega garantizada, porque una vez que lo envía a ES, no esperará un acuse de recibo.

Creo que tendría sentido para mí manejar las escrituras en Solr en lugar de usar crear un webhook en el servidor. Necesitaría actualizar Solr FIFO pero leí en https://github.com/supabase/realtime/issues/33#issuecomment -635010703 que sugirió webhooks que no devuelven 2XX que se escribe un registro en algún lugar. Eso rompería el orden de los registros que actualizan los documentos relevantes en Solr, lo cual no es ideal.

Como nota al margen, si los registros que no se reenvían correctamente a un webhook no se consultan fácilmente (y opcionalmente se extraen), creo que esto podría ser un problema. Obviamente, un registro es genial, pero me gustaría ver algunas estadísticas si algunos webhooks fallan por cualquier motivo. Sería útil sondear programáticamente el servidor en busca de webhooks fallidos, pero luego está cambiando la simplicidad del servidor. Suena cada vez más como si acabara teniendo que escribir una cola de trabajos para los webhooks, lo cual no es trivial. O al menos garantizar las escrituras en _en algún lugar_ para que los eventos no se pierdan.

Los valores de la carga útil son todas cadenas, por lo que podría ser más útil universalmente agregar una bandera booleana como PARSE_PAYLOAD, y si es verdadero, este servidor podría analizar la carga útil en los tipos correctos, eliminando la clave de las columnas por completo.

Analizar la carga útil en los tipos correctos puede ser útil, pero no diría que es necesario. Un transformador JSON permitiría a alguien seleccionar propiedades de manera que en una tabla de 30 columnas, solo devuelva 3 y también pueda cambiar el nombre de las columnas en el proceso.

el almacenamiento es más barato que la computación

Por lo tanto, puede que no sea la mejor idea si solo se trata de ahorrar espacio en una base de datos. ¿Alguna razón por la que no pudo limpiar la columna de la carga útil después de que aterrizó en ES?

Cuando mencioné el tamaño de la carga útil, no estaba hablando de almacenarlo, estaba literalmente hablando del tamaño de la carga útil que se envía a través de las interfaces. El tráfico de red entre hosts.

Si tengo un servidor de base de datos y pongo supabase/realtime allí, luego de tener un servidor websocket consumidor en un host diferente, obtendré muchos datos enviados entre los hosts. Es muy posible que esté tirando muchos de esos datos, por lo que sería más eficaz para mí volver a enviar NOTIFY desde los activadores. Pero luego pierdo algo de la flexibilidad que supabase/realtime me estaba dando originalmente al no tener que seguir cambiando las migraciones de la base de datos para agregar / eliminar columnas de la carga útil NOTIFY . Como se discutió, los transformadores JSON realmente brillarían aquí.

En caso de que no vea esto, hay un límite de 8000 bytes para las cargas útiles NOTIFICAR

Ja, sí. Me encontré con esto cuando intentaba enviar correos electrónicos almacenados en la base de datos a través de las notificaciones. Quiero decir, tiene sentido mantener el rendimiento, pero en ese momento era un rasguño de cabeza.

Exploraré un transformador JSON con uno de nuestro equipo y te lo haré saber. Podría llevar algo de tiempo, pero creo que vale la pena considerarlo como parte de nuestro trabajo en el n. ° 47.

Buena cosa.

Apéndice

Para cualquier otra persona que pueda tropezar con este problema en busca de una forma de sincronizar PostgreSQL con ES / Solr, https://debezium.io/ parece una buena alternativa. Esperaba no agregar demasiado a la pila porque esto se convierte en: ES / Solr, Debezium, Zookeeper, Kafka, pero supongo que ese es el precio que debe pagar por la entrega garantizada en este caso.

Literalmente estaba hablando del tamaño de la carga útil que se envía a través de las interfaces. El tráfico de red entre hosts.

Entendido, eso tiene sentido.

Debezium

¡Sí, gran sistema! Definitivamente pesado si quieres una funcionalidad completa, creo que es lo único que hay en el mercado en este momento.

Gracias de nuevo por el contexto. Necesitaré conversar con Francesco sobre este caso de uso. No está activo en este momento, por lo que, desafortunadamente, podría llevar un tiempo ver el progreso en este. No obstante, estas son las acciones que tengo:

  • Investigar el uso de un sistema de colas o alguna otra entrega garantizada.
  • explorar un transformador JSON

@kwakwaversal

Apéndice

Para cualquier otra persona que pueda tropezar con este problema en busca de una forma de sincronizar PostgreSQL con ES / Solr, https://debezium.io/ parece una buena alternativa. Esperaba no agregar demasiado a la pila porque esto se convierte en: ES / Solr, Debezium, Zookeeper, Kafka, pero supongo que ese es el precio que debe pagar por la entrega garantizada en este caso.

Estaba buscando una alternativa de debezium (para evitar la pila de JVM) y me encontré con este problema. ¿Puede tener éxito con el intento de usar supabase para la sincronización de búsqueda elástica? En mi caso, he encontrado la alternativa de búsqueda de Elastic MeiliSearch (entrecruzamiento https://github.com/meilisearch/integration-guides/issues/20)

En otra nota, para la transformación JSON, creo que estas bibliotecas son mejores y populares: https://github.com/jmespath/jmespath.js , https://github.com/jsonata-js/jsonata o https: // github .com / wankdanker / node-object-mapper (FWIW, https://www.npmtrends.com/json-query-vs-jsonata-vs-JSONPath-vs-jsonpath-vs-jsonpath-plus-vs-jmespath-vs -mapeador de objetos)

Gracias por los analizadores @rrjanbiah ; es posible que necesitemos encontrar algo nativo de elixir, pero estos son buenos antecedentes para trabajar.

Nuestra discusión actual es actualizar el analizador de eventos para que esté más en línea con los flujos de trabajo simples de AWS. por ejemplo: https://states-language.net/#choice -state. Esta es una máquina de estado completo, lo que debería convertirlo en un servidor muy versátil. Sin embargo, es una gran tarea, por lo que tendremos que dedicar tiempo a averiguar si es posible y si podemos enviarlo en partes.

@kiwicopple

Gracias por los analizadores @rrjanbiah ; es posible que necesitemos encontrar algo nativo de elixir, pero estos son buenos antecedentes para trabajar.

Parece no mantenido, pero encontré este https://github.com/stephan83/ex-jmes

Nuestra discusión actual es actualizar el analizador de eventos para que esté más en línea con los flujos de trabajo simples de AWS. por ejemplo: https://states-language.net/#choice -state. Esta es una máquina de estado completo, lo que debería convertirlo en un servidor muy versátil. Sin embargo, es una gran tarea, por lo que tendremos que dedicar tiempo a averiguar si es posible y si podemos enviarlo en partes.

No lo entiendo del todo aquí ... pero dado que te refieres a las máquinas de estado, es posible que desees consultar https://github.com/davidkpiano/xstate ya que es bastante popular

¿Fue útil esta página
0 / 5 - 0 calificaciones