Théorie et pratique de l'utilisation de HBase

Bon après-midi Je m'appelle Danil Lipova, notre équipe de Sbertech a commencé à utiliser HBase comme référentiel de données opérationnelles. Au cours de son étude, une expérience a été acquise que je souhaitais systématiser et décrire (nous espérons qu'elle sera utile à beaucoup). Toutes les expériences ci-dessous ont été menées avec des versions de HBase 1.2.0-cdh5.14.2 et 2.0.0-cdh6.0.0-beta1.

  1. Architecture générale
  2. Écriture de données dans HBASE
  3. Lecture des données de HBASE
  4. Mise en cache des données
  5. Traitement par lots MultiGet / MultiPut
  6. Stratégie de répartition des tableaux en régions (déversement)
  7. Tolérance aux pannes, compactification et localisation des données
  8. Paramètres et performances
  9. Test de charge
  10. Conclusions

1. Architecture générale



Le maître de secours écoute le rythme cardiaque actif sur le nœud ZooKeeper et, en cas de disparition, reprend les fonctions du maître.

2. Écriture de données dans HBASE


Tout d'abord, considérons le cas le plus simple - écrire un objet valeur-clé dans une certaine table en utilisant put (rowkey). Le client doit d'abord savoir où se trouve le serveur de région racine (RRS) qui stocke la métabase hbase :. Il reçoit ces informations de ZooKeeper. Il se tourne ensuite vers RRS et lit la table méta hbase: à partir de laquelle il récupère les informations dont RegionServer (RS) est responsable du stockage des données pour la clé de ligne donnée dans la table qui l'intéresse. Pour une utilisation future, la méta-table est mise en cache par le client et donc les appels suivants vont plus vite, directement vers RS.

RS, après avoir reçu la demande, l'écrit tout d'abord dans WriteAheadLog (WAL), ce qui est nécessaire pour la récupération en cas de panne. Ensuite, il enregistre les données dans MemStore. Il s'agit d'un tampon en mémoire qui contient un ensemble trié de clés pour une région donnée. Le tableau peut être divisé en régions (partitions), chacune contenant un jeu de clés disjoint. Cela permet de placer des régions sur différents serveurs pour obtenir de meilleures performances. Cependant, malgré l'évidence de cette déclaration, nous verrons plus loin que cela ne fonctionne pas dans tous les cas.

Après avoir placé l'enregistrement dans MemStore, le client reçoit une réponse indiquant que l'enregistrement a été enregistré avec succès. En même temps, il n'est réellement stocké que dans le tampon et n'atteint le disque qu'après un certain laps de temps ou lorsqu'il est rempli de nouvelles données.


Lors de l'exécution de l'opération «Supprimer», aucune suppression physique des données ne se produit. Ils sont simplement marqués comme supprimés et la destruction elle-même se produit lorsque la fonction compacte principale est appelée, ce qui est décrit plus en détail dans la section 7.

Les fichiers au format HFile sont accumulés dans HDFS et de temps en temps le processus compact mineur démarre, qui colle simplement de petits fichiers en plus gros sans rien supprimer. Au fil du temps, cela devient un problème qui ne se manifeste que lors de la lecture des données (nous y reviendrons plus tard).

En plus du processus de démarrage décrit ci-dessus, il existe une procédure beaucoup plus efficace, qui est probablement le côté le plus puissant de cette base de données - BulkLoad. Il consiste dans le fait que nous créons indépendamment des HFiles et les mettons sur le disque, ce qui nous permet de parfaitement évoluer et d'atteindre des vitesses très décentes. En fait, la limitation ici n'est pas HBase, mais les possibilités du fer. Vous trouverez ci-dessous les résultats du chargement sur un cluster composé de 16 RegionServers et 16 NodeManager YARN (CPU Xeon E5-2680 v4 @ 2.40GHz * 64 threads), version HBase 1.2.0-cdh5.14.2.



On peut voir qu'en augmentant le nombre de partitions (régions) dans la table, ainsi que les exécutables Spark, on obtient une augmentation de la vitesse de téléchargement. De plus, la vitesse dépend de la quantité d'enregistrement. Les gros blocs augmentent la mesure de Mo / sec, les petits le nombre d'enregistrements insérés par unité de temps, toutes choses étant égales par ailleurs.

Vous pouvez également commencer à charger dans deux tables en même temps et obtenir un doublement de la vitesse. On peut voir ci-dessous que des blocs de 10 Ko sont écrits sur deux tables à la fois avec une vitesse d'environ 600 Mb / s chacune (total 1275 Mb / s), ce qui coïncide avec la vitesse d'écriture de 623 Mo / s sur une table (voir n ° 11 ci-dessus)


Mais le deuxième lancement avec des enregistrements de 50 Ko montre que la vitesse de téléchargement augmente déjà légèrement, ce qui indique une approximation des valeurs limites. Il convient de garder à l'esprit qu'il n'y a pratiquement pas de charge sur HBASE lui-même, tout ce qui est requis est de donner d'abord les données de hbase: meta, et après avoir doublé les HFiles, videz les données BlockCache et enregistrez le tampon MemStore sur le disque s'il ne l'est pas. vide.

3. Lecture des données de HBASE


Si nous supposons que toutes les informations de hbase: meta ont déjà un client (voir la section 2), la demande va immédiatement au RS où la clé souhaitée est stockée. La recherche s'effectue d'abord dans MemCache. Qu'il y ait ou non des données, la recherche est également effectuée dans le tampon BlockCache et, si nécessaire, dans HFiles. Si les données ont été trouvées dans un fichier, elles sont placées dans BlockCache et seront renvoyées plus rapidement à la prochaine demande. Les recherches de fichiers H sont relativement rapides en raison de l'utilisation du filtre Bloom, c'est-à-dire Après avoir lu une petite quantité de données, il détermine immédiatement si ce fichier contient la clé souhaitée et, sinon, passe à la suivante.


Ayant reçu des données de ces trois sources, RS forme une réponse. En particulier, il peut transférer plusieurs versions de l'objet trouvé à la fois si le client a demandé un contrôle de version.

4. Mise en cache des données


Les tampons MemStore et BlockCache occupent jusqu'à 80% de la mémoire RS allouée RS (le reste est réservé aux tâches de service RS). Si le mode d'utilisation typique est tel que les processus écrivent et lisent immédiatement les mêmes données, alors il est logique de réduire BlockCache et d'augmenter MemStore, car lorsque l'écriture de données dans le cache de lecture ne tombe pas, l'utilisation de BlockCache se produit moins fréquemment. Le tampon BlockCache se compose de deux parties: LruBlockCache (toujours sur le tas) et BucketCache (généralement hors tas ou sur SSD). BucketCache doit être utilisé lorsqu'il y a beaucoup de demandes de lecture et qu'elles ne rentrent pas dans LruBlockCache, ce qui conduit au travail actif de Garbage Collector. Dans le même temps, vous ne devez pas vous attendre à une augmentation radicale des performances de l'utilisation du cache de lecture, mais nous y reviendrons dans la section 8


BlockCache est un pour l'ensemble du RS, et MemStore a le sien pour chaque table (un pour chaque famille de colonnes).

Comme décrit en théorie, lorsque l'écriture de données ne tombe pas dans le cache, et en effet, ces paramètres CACHE_DATA_ON_WRITE pour la table et "Cache DATA on Write" pour RS sont définis sur false. Cependant, dans la pratique, si vous écrivez des données dans MemStore, puis les videz sur le disque (en les nettoyant de cette façon), puis supprimez le fichier résultant, puis en exécutant une requête get, nous recevrons avec succès les données. Et même si vous désactivez complètement BlockCache et remplissez le tableau avec de nouvelles données, puis récupérez le MemStore sur le disque, supprimez-les et demandez à une autre session, ils seront toujours récupérés quelque part. HBase stocke donc non seulement des données, mais aussi des énigmes mystérieuses.

hbase(main):001:0> create 'ns:magic', 'cf' Created table ns:magic Took 1.1533 seconds hbase(main):002:0> put 'ns:magic', 'key1', 'cf:c', 'try_to_delete_me' Took 0.2610 seconds hbase(main):003:0> flush 'ns:magic' Took 0.6161 seconds hdfs dfs -mv /data/hbase/data/ns/magic/* /tmp/trash hbase(main):002:0> get 'ns:magic', 'key1' cf:c timestamp=1534440690218, value=try_to_delete_me 

Cache DATA on Read est défini sur false. Si vous avez des idées, n'hésitez pas à en discuter dans les commentaires.

5. Traitement par lots des données MultiGet / MultiPut


Le traitement de requêtes uniques (Get / Put / Delete) est une opération assez coûteuse, vous devez donc les combiner autant que possible dans une liste ou une liste, ce qui vous permet d'obtenir une amélioration significative des performances. Cela est particulièrement vrai de l'opération d'écriture, mais lors de la lecture, il y a le piège suivant. Le graphique ci-dessous montre le temps de lecture de 50 000 enregistrements de MemStore. La lecture a été effectuée en un seul flux et l'axe horizontal indique le nombre de clés dans la demande. On peut voir que lorsque vous augmentez à un millier de clés en une seule demande, le temps d'exécution diminue, c.-à-d. la vitesse augmente. Toutefois, lorsque le mode MSLAB est activé par défaut, après ce seuil, une baisse spectaculaire des performances commence et plus la quantité de données dans l'enregistrement est grande, plus la durée est longue.



Les tests ont été effectués sur une machine virtuelle, 8 cœurs, HBase version 2.0.0-cdh6.0.0-beta1.

Le mode MSLAB est conçu pour réduire la fragmentation du segment de mémoire, qui se produit en raison du mélange des données de nouvelle et ancienne génération. Pour résoudre le problème lorsque MSLAB est activé, les données sont placées dans des cellules relativement petites (blocs) et traitées par lots. Par conséquent, lorsque le volume dans le paquet de données demandé dépasse la taille allouée, les performances diminuent fortement. En revanche, la désactivation de ce mode est également déconseillée, car elle entraînera des arrêts dus au GC pendant les moments de travail intensif avec les données. Une bonne solution consiste à augmenter le volume de la cellule, dans le cas d'une écriture active via put simultanément avec la lecture. Il convient de noter que le problème ne se produit pas si, après l'enregistrement, exécutez la commande flush qui vide MemStore sur le disque ou si le chargement est effectué à l'aide de BulkLoad. Le tableau ci-dessous montre que les requêtes à partir de données MemStore d'un volume plus important (et de la même quantité) entraînent un ralentissement. Cependant, l'augmentation de la taille des blocs ramène le temps de traitement à la normale.


En plus d'augmenter la taille des blocs, la fragmentation des données par région aide, c'est-à-dire fractionnement de table. Cela conduit au fait que moins de demandes arrivent dans chaque région et si elles sont placées dans une cellule, la réponse reste bonne.

6. La stratégie de division des tableaux en régions (découpage)


Étant donné que HBase est un stockage de valeurs-clés et que le partitionnement est effectué par clé, il est extrêmement important de partager les données de manière uniforme dans toutes les régions. Par exemple, le partitionnement d'une telle table en trois parties entraînera la division des données en trois régions:


Il arrive que cela entraîne un net ralentissement si les données chargées à l'avenir ressembleront, par exemple, à des valeurs longues, dont la plupart commencent par le même chiffre, par exemple:

1000001
1000002
...
1100003

Étant donné que les clés sont stockées sous la forme d'un tableau d'octets, elles démarreront toutes de la même manière et appartiendront à la même région # 1 qui stocke cette plage de clés. Il existe plusieurs stratégies divisées:

HexStringSplit - Transforme la clé en une chaîne avec un codage hexadécimal dans la plage "00000000" => "FFFFFFFF" et en la remplissant de zéros à gauche.

UniformSplit - Transforme une clé en un tableau d'octets avec un codage hexadécimal dans la plage "00" => "FF" et en la remplissant de zéros à droite.

De plus, vous pouvez spécifier n'importe quelle plage ou ensemble de clés à diviser et configurer la division automatique. Cependant, l'une des approches les plus simples et les plus efficaces est UniformSplit et l'utilisation de la concaténation de hachage, par exemple, une paire élevée d'octets provenant de l'exécution d'une clé via la fonction CRC32 (rowkey) et rowkey elle-même:

hash + rowkey

Ensuite, toutes les données seront réparties uniformément entre les régions. Lors de la lecture, les deux premiers octets sont simplement supprimés et la clé d'origine reste. RS contrôle également la quantité de données et de clés dans la région et lorsque les limites sont dépassées, il les décompose automatiquement en morceaux.

7. Tolérance aux pannes et localisation des données


Étant donné qu'une seule région est responsable de chaque jeu de clés, la solution aux problèmes associés aux plantages RS ou au déclassement consiste à stocker toutes les données nécessaires dans HDFS. Lorsque RS se bloque, le maître le détecte par l'absence de pulsation sur le nœud ZooKeeper. Ensuite, il attribue la région desservie à une autre RS et puisque les HFiles sont stockés dans un système de fichiers distribué, le nouvel hôte les lit et continue de servir les données. Cependant, comme certaines des données peuvent se trouver dans MemStore et n'ont pas eu le temps d'entrer dans les HFiles, les WAL, qui sont également stockés dans HDFS, sont utilisés pour restaurer l'historique des opérations. Après le transfert des modifications, RS est en mesure de répondre aux demandes, cependant, le déplacement conduit au fait qu'une partie des données et leurs processus se trouvent sur différents nœuds, c'est-à-dire localité réduite.

La solution au problème est un compactage majeur - cette procédure déplace les fichiers vers les nœuds qui en sont responsables (où se trouvent leurs régions), à la suite de quoi la charge sur le réseau et les disques augmente fortement pendant cette procédure. Cependant, à l'avenir, l'accès aux données est sensiblement accéléré. De plus, major_compaction combine tous les HFiles en un seul fichier dans la région et nettoie également les données en fonction des paramètres de la table. Par exemple, vous pouvez spécifier le nombre de versions d'un objet que vous souhaitez enregistrer ou sa durée de vie, après quoi l'objet est physiquement supprimé.

Cette procédure peut avoir un effet très positif sur HBase. L'image ci-dessous montre comment les performances se sont dégradées suite à l'enregistrement actif des données. Ici, vous pouvez voir comment 40 flux ont été écrits dans une table et 40 flux lire des données en même temps. L'écriture de flux forme de plus en plus de HFiles, qui sont lus par d'autres flux. En conséquence, de plus en plus de données doivent être supprimées de la mémoire et à la fin, le GC commence à fonctionner, ce qui paralyse pratiquement tout le travail. Le lancement d'un compactage majeur a conduit au nettoyage des blocages qui en résultent et à la restauration des performances.


Le test a été effectué sur 3 DataNode et 4 RS (CPU Xeon E5-2680 v4 @ 2.40GHz * 64 threads). HBase version 1.2.0-cdh5.14.2

Il convient de noter que le lancement du compactage majeur a été effectué sur une table «en direct», dans laquelle les données ont été activement écrites et lues. Il y avait une déclaration sur le réseau que cela pourrait conduire à une réponse incorrecte lors de la lecture des données. Pour vérifier, un processus a été lancé qui a généré de nouvelles données et les a écrites dans la table. Après quoi j'ai immédiatement lu et vérifié si la valeur obtenue coïncidait avec ce qui a été enregistré. Au cours de ce processus, un compactage majeur a été lancé environ 200 fois et aucune défaillance n'a été enregistrée. Peut-être que le problème apparaît rarement et uniquement pendant une charge élevée, il est donc plus sûr d'arrêter de manière planifiée les processus d'écriture et de lecture et d'effectuer le nettoyage sans autoriser ces rabattements GC.

De plus, le compactage majeur n'affecte pas l'état de MemStore, pour le vider sur le disque et le compacter, vous devez utiliser flush (connection.getAdmin (). Flush (TableName.valueOf (tblName))).

8. Paramètres et performances


Comme déjà mentionné, HBase montre le plus grand succès où il n'a rien à faire lors de l'exécution de BulkLoad. Cependant, cela s'applique à la plupart des systèmes et des personnes. Cependant, cet outil est plus adapté à l'empilement en bloc de données en gros blocs, alors que si le processus nécessite beaucoup de demandes de lecture et d'écriture concurrentes, les commandes Get et Put décrites ci-dessus sont utilisées. Pour déterminer les paramètres optimaux, des lancements ont été effectués avec différentes combinaisons de paramètres et de réglages de table:

  • 10 threads ont été lancés en même temps 3 fois de suite (appelons cela un bloc de threads).
  • La durée de fonctionnement de tous les flux dans le bloc a été moyennée et était le résultat final du fonctionnement du bloc.
  • Tous les fils fonctionnaient avec la même table.
  • Avant chaque démarrage du bloc de threads, un compactage majeur a été exécuté.
  • Chaque bloc n'a effectué qu'une seule des opérations suivantes:

- Mettez
- obtenir
- Get + Put

  • Chaque bloc a effectué 50 000 répétitions de son opération.
  • La taille d'enregistrement dans le bloc est de 100 octets, 1000 octets ou 10000 octets (aléatoire).
  • Les blocs ont été lancés avec un nombre différent de clés demandées (soit une clé, soit 10).
  • Des blocs ont été lancés à différents paramètres de table. Paramètres modifiés:

- BlockCache = activé ou désactivé
- BlockSize = 65 Ko ou 16 Ko
- Cloisons = 1, 5 ou 30
- MSLAB = activé ou désactivé

Ainsi, le bloc ressemble à ceci:

a. Le mode MSLAB est activé / désactivé.
b. Une table a été créée pour laquelle les paramètres suivants ont été définis: BlockCache = true / none, BlockSize = 65/16 Kb, Partitions = 1/5/30.
c. Réglez la compression GZ.
d. 10 threads ont été lancés simultanément effectuant 1/10 des opérations put / get / get + put dans ce tableau avec des enregistrements de 100/1000/10000 octets, exécutant 50 000 requêtes consécutives (clés aléatoires).
e. Le point d a été répété trois fois.
f. La durée de fonctionnement de tous les threads a été moyennée.

Toutes les combinaisons possibles ont été vérifiées. Il est prévisible qu'à mesure que la taille d'enregistrement augmente, la vitesse diminue ou que la désactivation de la mise en cache ralentit. Cependant, l'objectif était de comprendre le degré et l'importance de l'influence de chaque paramètre, par conséquent, les données collectées ont été introduites dans l'entrée de la fonction de régression linéaire, ce qui permet d'évaluer la fiabilité à l'aide de statistiques t. Voici les résultats des blocs effectuant des opérations de vente. Un ensemble complet de combinaisons 2 * 2 * 3 * 2 * 3 = 144 options + 72 depuis certains ont été exécutés deux fois. Par conséquent, 216 lancements au total:


Les tests ont été effectués sur un mini-cluster composé de 3 DataNode et 4 RS (CPU Xeon E5-2680 v4 @ 2.40GHz * 64 flux). HBase version 1.2.0-cdh5.14.2.

La vitesse d'insertion la plus élevée de 3,7 secondes a été obtenue lorsque le mode MSLAB a été désactivé, sur une table avec une partition, avec BlockCache activé, BlockSize = 16, enregistrements de 100 octets de 10 pièces par paquet.
La vitesse d'insertion la plus faible de 82,8 secondes a été obtenue lorsque le mode MSLAB était activé, sur une table avec une partition, avec BlockCache activé, BlockSize = 16, enregistrements de 10 000 octets chacun.

Voyons maintenant le modèle. Nous voyons un modèle de bonne qualité pour R2, mais il est clair que l'extrapolation est ici contre-indiquée. Le comportement réel du système lors de la modification des paramètres ne sera pas linéaire, ce modèle n'est pas nécessaire pour les prévisions, mais pour comprendre ce qui s'est passé dans les paramètres donnés. Par exemple, ici nous voyons par le critère de Student que pour l'opération Put, les paramètres BlockSize et BlockCache n'ont pas d'importance (ce qui est généralement prévisible):


Mais le fait qu'une augmentation du nombre de partitions entraîne une baisse des performances est quelque peu inattendu (nous avons déjà vu l'effet positif d'une augmentation du nombre de partitions avec BulkLoad), bien que cela soit compréhensible. Tout d'abord, pour le traitement, il est nécessaire de former des requêtes sur 30 régions au lieu d'une, et la quantité de données n'est pas telle qu'elle donne un gain. Deuxièmement, le temps de fonctionnement total est déterminé par le RS le plus lent, et puisque le nombre de DataNode est inférieur au nombre de RS, certaines régions ont une localité nulle. Eh bien, regardons les cinq premiers:


Maintenant, évaluons les résultats de l'exécution des blocs Get:


Le nombre de partitions a perdu de son importance, ce qui est probablement dû au fait que les données sont bien mises en cache et que le cache de lecture est le paramètre le plus significatif (statistiquement). Naturellement, l'augmentation du nombre de messages dans une demande est également très utile pour les performances. Les meilleurs résultats:


Eh bien, enfin, regardez le modèle du bloc qui a exécuté get first, puis mettez:


Ici, tous les paramètres sont significatifs. Et les résultats des dirigeants:


9. Test de charge


Enfin, nous allons lancer une charge plus ou moins décente, mais c'est toujours plus intéressant quand il y a quelque chose à comparer. Le site de DataStax, un développeur clé de Cassandra, présente les résultats de NT d'un certain nombre de référentiels NoSQL, dont HBase version 0.98.6-1. Le chargement a été effectué par 40 flux, taille des données 100 octets, disques SSD. Le résultat des tests des opérations de lecture-modification-écriture a montré ces résultats.


Si je comprends bien, la lecture a été effectuée par blocs de 100 enregistrements et pour 16 nœuds HBase, le test DataStax a montré une performance de 10 000 opérations par seconde.

Heureusement que notre cluster possède également 16 nœuds, mais pas très «chanceux» que chacun a 64 cœurs (threads), tandis que le test DataStax n'en a que 4. D'autre part, ils ont des disques SSD, et nous avons des disques durs et plus encore la nouvelle version de HBase et l'utilisation du CPU pendant la charge n'ont pratiquement pas augmenté de manière significative (visuellement de 5 à 10%). Néanmoins, nous allons essayer de démarrer sur cette configuration. Paramètres de table par défaut, la lecture est effectuée dans une plage de clés de 0 à 50 millions au hasard (c'est-à-dire, en fait, à chaque fois une nouvelle). Dans le tableau, 50 millions d'entrées sont réparties en 64 partitions. Les clés sont hachées par crc32. Les paramètres de table sont définis par défaut, MSLAB est activé. À partir de 40 threads, chaque thread lit un ensemble de 100 clés aléatoires et réécrit immédiatement les 100 octets générés sur ces clés.


Support: 16 DataNode et 16 RS (CPU Xeon E5-2680 v4 @ 2.40GHz * 64 flux). HBase version 1.2.0-cdh5.14.2.

Le résultat moyen est plus proche de 40 000 opérations par seconde, ce qui est nettement meilleur que dans le test DataStax. Cependant, aux fins de l'expérience, les conditions peuvent être légèrement modifiées. Il est peu probable que tous les travaux soient effectués exclusivement avec une seule table, ainsi qu'avec des clés uniques. Supposons qu'il existe un certain jeu de clés «à chaud» qui génère la charge principale. Par conséquent, nous allons essayer de créer une charge avec des enregistrements plus volumineux (10 Ko), également en paquets de 100 chacun, dans 4 tableaux différents et en limitant la plage de clés demandées à 50 000. Le graphique ci-dessous montre le début de 40 threads, chaque flux lit un ensemble de 100 clés et écrit immédiatement 10 aléatoires KB sur ces clés de retour.


Support: 16 DataNode et 16 RS (CPU Xeon E5-2680 v4 @ 2.40GHz * 64 flux). HBase version 1.2.0-cdh5.14.2.

Pendant le chargement, un compactage majeur a été lancé plusieurs fois, comme illustré ci-dessus sans cette procédure, les performances se dégraderont progressivement, cependant, une charge supplémentaire se produit également lors de l'exécution. Les prélèvements sont causés par diverses raisons. Parfois, les threads se terminaient et pendant leur redémarrage, il y avait une pause, parfois des applications tierces créaient une charge sur le cluster.

Lire et écrire tout de suite est l'un des scénarios de travail les plus difficiles pour HBase. Si vous ne mettez que des requêtes put d'une petite taille, par exemple 100 octets chacune, en les combinant en lots de 10 à 50 000 pièces, vous pouvez obtenir des centaines de milliers d'opérations par seconde et la situation est similaire avec des requêtes en lecture seule. Il est à noter que les résultats sont radicalement meilleurs que ceux qui ont été obtenus chez DataStax surtout en raison de demandes en blocs de 50 000.


Support: 16 DataNode et 16 RS (CPU Xeon E5-2680 v4 @ 2.40GHz * 64 flux). HBase version 1.2.0-cdh5.14.2.

10. Conclusions


Ce système est suffisamment flexible pour être configuré, mais l'effet d'un grand nombre de paramètres est encore inconnu. Certains d'entre eux ont été testés, mais n'ont pas été inclus dans la suite de tests résultante. Par exemple, des expériences préliminaires ont montré l'insignifiance d'un paramètre tel que DATA_BLOCK_ENCODING, qui code les informations en utilisant les valeurs des cellules voisines, ce qui est tout à fait compréhensible pour les données générées de manière aléatoire. Dans le cas de l'utilisation d'un grand nombre d'objets répétitifs, le gain peut être important. En général, nous pouvons dire que HBase donne l'impression d'une base de données assez sérieuse et bien pensée, qui peut être assez productive lorsqu'il s'agit de gros blocs de données. Surtout s'il est possible d'étaler les processus de lecture et d'écriture dans le temps.

Si, à votre avis, quelque chose n'est pas suffisamment divulgué, je suis prêt à le dire plus en détail. Nous vous suggérons de partager votre expérience ou de débattre si vous n'êtes pas d'accord avec quelque chose.

Source: https://habr.com/ru/post/fr420425/


All Articles