Realtime: Cas d'utilisation: synchronisation avec Elasticsearch / Solr

Créé le 26 août 2020  ·  6Commentaires  ·  Source: supabase/realtime

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

Pouvez-vous nous en dire un peu plus sur votre cas d'utilisation particulier? Cela nous aidera dans notre planification et nos améliorations. N'hésitez pas à créer un nouveau problème si je n'ai pas correctement répondu à votre question ici

Salut @kiwicopple. Je suis actuellement dans une phase exploratoire suite à l'exigence de synchroniser les données de PostgreSQL vers Solr ou Elasticsearch et de voir ce qui existe. Je savais que la réplication logique était la seule voie à suivre, mais je devais explorer les solutions existantes. J'ai entendu parler de la supabase en temps réel il y a un an, alors j'ai mis les pneus à l'épreuve pour voir ce qu'elle pouvait faire.

Ma pensée était de m'abonner à des tables d'intérêt et de mettre à jour ou d'insérer des enregistrements dans ES / Solr. Une livraison garantie est évidemment privilégiée pour cela. Je n'aime pas l'idée de devoir synchroniser occasionnellement des centaines de milliers d'e-mails qui _pourraient_ être désynchronisés.

Cependant, en explorant supabase/realtime , je vois comment cela pourrait être bénéfique pour d'autres aspects d'un produit sur lequel je travaille.

• S'abonner à des tables au lieu de créer beaucoup de déclencheurs NOTIFY (comme nous le faisons actuellement en production).

Une chose qui a sauté à ce sujet est que la taille de la charge utile, y compris l'objet types , bien qu'utile, s'additionne vraiment sur des milliers d'enregistrements (encore plus si vous recevez l'ancien enregistrement). Je pense que je préférerais que lors de mon inscription, je puisse demander des données spécifiques.

Cela semble être en partie discuté ici: https://github.com/supabase/realtime/issues/47 mais cela semble être simplement un filtrage conditionnel des données (ce qui est bien). Ce que je trouverais utile serait de demander un sous-ensemble de données, de sorte que seul le strict minimum doit être transmis entre le serveur en temps réel et le client. Un langage de requête et de transformation JSON comme https://github.com/schibsted/jslt ou https://github.com/jsonata-js/jsonata serait idéal car cela pourrait être passé comme argument lors de l'abonnement et transformer les données sur côté serveur. Je ne sais pas que des bibliothèques équivalentes sont disponibles dans Elixir.

Question:
Je suppose que l'approche préférée pour réduire la charge sur le serveur et la sortie en continu de PostrgreSQL est de créer uniquement une publication pour un sous-ensemble de tables plutôt que CREATE PUBLICATION supabase_realtime FOR ALL TABLES; ?

Une dernière chose: nous prévoyons le test de référence comme une exigence pour passer de l'alpha à la bêta.

BTW les cases à cocher dans le README pour ce dépôt suggèrent que vous êtes déjà en Bêta (https://github.com/supabase/realtime#status) mais le paragraphe ci-dessous suggère le contraire. Je n'ai pas lu le paragraphe ci-dessous à l'origine et juste les cases à cocher, je pensais donc que vous étiez en version bêta. :)

question

Commentaire le plus utile

Je suis réticent à l'appeler livraison garantie, car une fois qu'il l'envoie à ES, il n'attendra pas un accusé de réception.

Je pense qu'il serait logique pour moi de gérer les écritures sur Solr plutôt que de créer un webhook sur le serveur. J'aurais besoin de mettre à jour Solr FIFO mais j'ai lu dans https://github.com/supabase/realtime/issues/33#issuecomment -635010703 que vous avez suggéré des webhooks qui ne retournent pas 2XX qu'un journal est écrit quelque part. Cela briserait l'ordre des enregistrements qui mettent à jour les documents pertinents dans Solr, ce qui n'est pas idéal.

En remarque, si les enregistrements qui ne sont pas transmis avec succès à un webhook ne sont pas facilement interrogés (et éventuellement extraits), je pense que cela pourrait être un problème. Un journal est bien évidemment, mais j'aimerais voir des statistiques si certains webhooks échouent pour une raison quelconque. Interroger le serveur par programme pour les webhooks échoués serait utile, mais vous changez alors la simplicité du serveur. Il semble de plus en plus que vous allez devoir écrire une file d'attente de travaux pour les webhooks, ce qui n'est pas trivial. Ou à tout le moins garantir les écritures dans _quelque part_ afin que les événements ne soient pas perdus.

Les valeurs de charge utile sont toutes des chaînes, il peut donc être plus universellement utile d'ajouter un indicateur booléen tel que PARSE_PAYLOAD, et s'il est vrai, ce serveur pourrait analyser la charge utile dans les types corrects, en supprimant complètement la clé des colonnes.

L'analyse de la charge utile dans les types corrects peut être utile, mais je ne dirais pas que c'est nécessaire. Un transformateur JSON permettrait à quelqu'un de choisir les propriétés de sorte que dans une table de 30 colonnes, il ne renvoie que 3 et soit également capable de renommer les colonnes dans le processus.

le stockage est moins cher que le calcul

Par conséquent, ce n'est peut-être pas la meilleure idée si ce n'est que pour économiser de l'espace sur une base de données. Une raison pour laquelle vous ne pouvez pas nettoyer la colonne de la charge utile après son atterrissage dans ES?

Lorsque j'ai mentionné la taille de la charge utile, je ne parlais pas de la stocker, je parlais littéralement de la taille de la charge utile envoyée à travers les interfaces. Le trafic réseau entre les hôtes.

Si j'ai un serveur de base de données et que j'y mets supabase/realtime , alors avoir un serveur Websocket consommateur sur un hôte différent je vais recevoir beaucoup de données entre les hôtes. Il est fort possible que je jette beaucoup de ces données, il serait donc plus performant pour moi de revenir à l'envoi de NOTIFY partir de déclencheurs. Mais ensuite, je perds une partie de la flexibilité que supabase/realtime m'offrait à l'origine en n'ayant pas à continuer à me changer les migrations de bases de données pour ajouter / supprimer des colonnes de la charge utile NOTIFY . Comme discuté, les transformateurs JSON brilleraient vraiment ici.

Si vous ne l'avez pas vu, il y a une limite de 8000 octets pour les charges utiles NOTIFY

Hah, ouais. Je suis tombé sur cela en essayant d'envoyer des e-mails stockés dans la base de données sur les notifications. Je veux dire, il est logique de maintenir les performances, mais à l'époque, c'était un grattoir à la tête.

J'explorerai un transformateur JSON avec l'une de nos équipes et je vous le ferai savoir. Cela pourrait prendre un certain temps, mais je pense que cela vaut la peine d'être considéré dans le cadre de notre travail sur # 47

Super truc.

Addenda

Pour quiconque pourrait tomber sur ce problème à la recherche d'un moyen de synchroniser PostgreSQL avec ES / Solr, https://debezium.io/ semble être une bonne alternative. J'espérais ne pas ajouter trop de supplément à la pile car cela devient: ES / Solr, Debezium, Zookeeper, Kafka mais je suppose que c'est le prix que vous devez payer pour une livraison garantie dans ce cas.

Tous les 6 commentaires

Hey @kwakwaversal merci pour cet incroyable article.

les cases à cocher dans le README pour ce dépôt suggèrent que vous êtes déjà en version bêta

Oops. Merci pour l'information! Nous normalisons les statuts des versions dans l'ensemble de l'organisation. Je l'ai rétabli en alpha - je pense que c'est une représentation plus juste de l'état du serveur, mais aussi de Supabase dans son ensemble. Nous passerons à la version bêta une fois que nous aurons quelques points de repère et, plus important encore, nous embaucherons quelqu'un qui peut prendre en charge ce repo à plein temps (nous sommes une très petite équipe en ce moment)

mettre à jour ou insérer des enregistrements dans ES / Solr. Une livraison garantie est évidemment privilégiée pour cela.

Très cool. Celui-ci sera faisable avec les webhooks (https://github.com/supabase/realtime/issues/33). Une fois que j'aurai résolu le problème de la réutilisation des slots de réplication (https://github.com/supabase/realtime/issues/22), la lecture et l'envoi seront garantis

la taille de la charge utile, y compris l'objet types, bien qu'utile, s'additionne vraiment sur des milliers d'enregistrements (encore plus si vous recevez l'enregistrement ANCIEN)

Intéressant - aussi un auquel je n'avais pas pensé. Je vais creuser dans l'idée d'un transformateur JSON. Les valeurs de la charge utile sont toutes des chaînes, il peut donc être plus universellement utile d'ajouter un indicateur booléen comme PARSE_PAYLOAD , et si true, ce serveur pourrait analyser la charge utile dans les types corrects, en supprimant la clé columns tout à fait. Cela aura un impact sur les performances, c'est donc celui que nous devrons peser. Vous perdriez également beaucoup de détails (est-ce un smallint ou bigint ?), Mais dans de nombreux cas, cela n'a pas d'importance.

Mes premières réflexions à ce sujet:

  • le stockage est moins cher que le calcul
  • la performance est importante

Par conséquent, ce n'est peut-être pas la meilleure idée si ce n'est que pour économiser de l'espace sur une base de données. Une raison pour laquelle vous ne pouvez pas nettoyer le column de la charge utile après son atterrissage dans ES?

Je suppose que l'approche préférée pour réduire la charge sur le serveur et la sortie en continu de PostrgreSQL est de créer uniquement une publication pour un sous-ensemble de tables

Oui c'est correct. S'il y a des tables dont vous ne vous souciez pas de la diffusion en continu, n'activez simplement pas la réplication. Faites-moi savoir si c'est un problème pour votre cas d'utilisation!

S'abonner à des tables au lieu de créer de nombreux déclencheurs NOTIFY (comme nous le faisons actuellement en production).

Au cas où vous ne le verriez pas, il y a une limite de 8000 octets pour les charges utiles NOTIFY, alors faites attention à ce que votre système n'abandonne pas silencieusement les événements. Postgres lève en fait une erreur, mais c'est difficile à détecter. C'est la raison exacte pour laquelle nous avons créé Realtime l'année dernière - j'utilisais trigger / NOTIFY et je l'ai découvert à la dure.

Prochaines étapes

J'explorerai un transformateur JSON avec l'une de nos équipes et je vous le ferai savoir. Cela pourrait prendre un certain temps, mais je pense que cela vaut la peine d'être considéré dans le cadre de notre travail sur https://github.com/supabase/realtime/issues/47

Je suis réticent à l'appeler livraison garantie, car une fois qu'il l'envoie à ES, il n'attendra pas un accusé de réception.

Je pense qu'il serait logique pour moi de gérer les écritures sur Solr plutôt que de créer un webhook sur le serveur. J'aurais besoin de mettre à jour Solr FIFO mais j'ai lu dans https://github.com/supabase/realtime/issues/33#issuecomment -635010703 que vous avez suggéré des webhooks qui ne retournent pas 2XX qu'un journal est écrit quelque part. Cela briserait l'ordre des enregistrements qui mettent à jour les documents pertinents dans Solr, ce qui n'est pas idéal.

En remarque, si les enregistrements qui ne sont pas transmis avec succès à un webhook ne sont pas facilement interrogés (et éventuellement extraits), je pense que cela pourrait être un problème. Un journal est bien évidemment, mais j'aimerais voir des statistiques si certains webhooks échouent pour une raison quelconque. Interroger le serveur par programme pour les webhooks échoués serait utile, mais vous changez alors la simplicité du serveur. Il semble de plus en plus que vous allez devoir écrire une file d'attente de travaux pour les webhooks, ce qui n'est pas trivial. Ou à tout le moins garantir les écritures dans _quelque part_ afin que les événements ne soient pas perdus.

Les valeurs de charge utile sont toutes des chaînes, il peut donc être plus universellement utile d'ajouter un indicateur booléen tel que PARSE_PAYLOAD, et s'il est vrai, ce serveur pourrait analyser la charge utile dans les types corrects, en supprimant complètement la clé des colonnes.

L'analyse de la charge utile dans les types corrects peut être utile, mais je ne dirais pas que c'est nécessaire. Un transformateur JSON permettrait à quelqu'un de choisir les propriétés de sorte que dans une table de 30 colonnes, il ne renvoie que 3 et soit également capable de renommer les colonnes dans le processus.

le stockage est moins cher que le calcul

Par conséquent, ce n'est peut-être pas la meilleure idée si ce n'est que pour économiser de l'espace sur une base de données. Une raison pour laquelle vous ne pouvez pas nettoyer la colonne de la charge utile après son atterrissage dans ES?

Lorsque j'ai mentionné la taille de la charge utile, je ne parlais pas de la stocker, je parlais littéralement de la taille de la charge utile envoyée à travers les interfaces. Le trafic réseau entre les hôtes.

Si j'ai un serveur de base de données et que j'y mets supabase/realtime , alors avoir un serveur Websocket consommateur sur un hôte différent je vais recevoir beaucoup de données entre les hôtes. Il est fort possible que je jette beaucoup de ces données, il serait donc plus performant pour moi de revenir à l'envoi de NOTIFY partir de déclencheurs. Mais ensuite, je perds une partie de la flexibilité que supabase/realtime m'offrait à l'origine en n'ayant pas à continuer à me changer les migrations de bases de données pour ajouter / supprimer des colonnes de la charge utile NOTIFY . Comme discuté, les transformateurs JSON brilleraient vraiment ici.

Si vous ne l'avez pas vu, il y a une limite de 8000 octets pour les charges utiles NOTIFY

Hah, ouais. Je suis tombé sur cela en essayant d'envoyer des e-mails stockés dans la base de données sur les notifications. Je veux dire, il est logique de maintenir les performances, mais à l'époque, c'était un grattoir à la tête.

J'explorerai un transformateur JSON avec l'une de nos équipes et je vous le ferai savoir. Cela pourrait prendre un certain temps, mais je pense que cela vaut la peine d'être considéré dans le cadre de notre travail sur # 47

Super truc.

Addenda

Pour quiconque pourrait tomber sur ce problème à la recherche d'un moyen de synchroniser PostgreSQL avec ES / Solr, https://debezium.io/ semble être une bonne alternative. J'espérais ne pas ajouter trop de supplément à la pile car cela devient: ES / Solr, Debezium, Zookeeper, Kafka mais je suppose que c'est le prix que vous devez payer pour une livraison garantie dans ce cas.

Je parlais littéralement de la taille de la charge utile envoyée à travers les interfaces. Le trafic réseau entre les hôtes.

Compris, cela a du sens.

Debezium

Oui, super système! Certainement lourd si vous voulez des fonctionnalités complètes, je pense que c'est la seule chose sur le marché à l'heure actuelle.

Merci encore pour le contexte. J'aurai besoin de discuter avec Francesco de ce cas d'utilisation. Il n'est pas actif pour le moment, donc malheureusement, cela pourrait prendre un certain temps pour voir les progrès sur celui-ci. Néanmoins, voici les actions que j'ai:

  • Étudiez l'utilisation d'un système de mise en file d'attente ou d'une autre livraison garantie
  • explorer un transformateur JSON

@kwakwaversal

Addenda

Pour quiconque pourrait tomber sur ce problème à la recherche d'un moyen de synchroniser PostgreSQL avec ES / Solr, https://debezium.io/ semble être une bonne alternative. J'espérais ne pas ajouter trop de supplément à la pile car cela devient: ES / Solr, Debezium, Zookeeper, Kafka mais je suppose que c'est le prix que vous devez payer pour une livraison garantie dans ce cas.

Je cherchais une alternative à debezium (pour éviter la pile JVM) et je suis tombé sur ce problème. Pouvez-vous réussir la tentative d'utilisation de la supabase pour la synchronisation de la recherche Elastic? Dans mon cas, j'ai trouvé une alternative à la recherche élastique MeiliSearch (réticulation https://github.com/meilisearch/integration-guides/issues/20)

D'autre part, pour la transformation JSON, je pense que ces bibliothèques sont meilleures et populaires: https://github.com/jmespath/jmespath.js , https://github.com/jsonata-js/jsonata ou 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 -objet-mappeur)

Merci pour les analyseurs @rrjanbiah - nous aurons peut-être besoin de trouver quelque chose d'élixir natif, mais ce sont de bons antécédents sur lesquels travailler.

Notre discussion actuelle est de mettre à jour l'analyseur d'événements pour qu'il soit plus en ligne avec les flux de travail simples d'AWS. par exemple: https://states-language.net/#choice -state. Il s'agit d'une machine à états complète, ce qui devrait en faire un serveur très polyvalent. C'est une tâche importante, nous devrons donc passer du temps à déterminer si c'est possible et si nous pouvons l'expédier en plusieurs parties

@kiwicopple

Merci pour les analyseurs @rrjanbiah - nous aurons peut-être besoin de trouver quelque chose d'élixir natif, mais ce sont de bons antécédents sur lesquels travailler.

Cela n'a pas l'air maintenu, mais j'ai trouvé celui-ci https://github.com/stephan83/ex-jmes

Notre discussion actuelle est de mettre à jour l'analyseur d'événements pour qu'il soit plus en ligne avec les flux de travail simples d'AWS. par exemple: https://states-language.net/#choice -state. Il s'agit d'une machine à états complète, ce qui devrait en faire un serveur très polyvalent. C'est une tâche importante, nous devrons donc passer du temps à déterminer si c'est possible et si nous pouvons l'expédier en plusieurs parties

Je ne comprends pas tout à fait ici ... mais puisque vous faites référence aux machines à états, vous voudrez peut-être vérifier https://github.com/davidkpiano/xstate car c'est assez populaire

Cette page vous a été utile?
0 / 5 - 0 notes

Questions connexes

retendo picture retendo  ·  12Commentaires

awalias picture awalias  ·  5Commentaires

kiwicopple picture kiwicopple  ·  14Commentaires

awalias picture awalias  ·  9Commentaires

kiwicopple picture kiwicopple  ·  16Commentaires