RocksDB

В последние года наравне с традиционными реляционными хранилищами такими как MySQL, PostgreSQL, Oracle, MS SQL активно стали использоваться NoSQL решения - Mongo, Cassandra, и д.р. К отдельному классу NoSQL хранилищ стоит отнести встраиваемые хранилища. Характерными представителями это класса хранилищ являются LevelDB, RocksDB, SQLite, BerkeleyDB.  Об одном из низ и пойдет сегодня наша речь.

RocksDB – гибкое производительное встраиваемое NoSQL хранилище, разработанное в Facebook. Оно рассчитано на использование на быстрых носителях, таких как SSD диски. Кодовая база в качестве основы использует LevelDB, разработанную Google. Но в Rocks были проведены следующие доработки:

  • Оптимизирована работы с SSD дисками
  • Оптимизирована работы с большими объемами данных
  • Фильтр Блума для range сканирования
  • Многопоточное сбрасывание MemTable на диск
  • Многопоточное сжатие данных
  • Большая гибкость и расширяемость

Ниже проведен сравнительный тест RocksDB с LevelDB. Тестовая конфигурация: контейнер Digital Ocean, 4ГБ RAM, 2 Cores, 60GB SSD диск. В качестве ключа использовалось 3 unsigned int в Big Endian представлении.

тест

LevelDB

RocksDB

Запись 100 млн значений

36 мин 8 с

21 мин 18 с

Размер хранилища

2.7 ГБ

3.2 ГБ

Выборка 100 млн значений

2 мин 55 с

2 мин 45 с

Удаление 50 млн значений

3 мин 47 с

1 мин 54 с

 

На данный момент RocksDB активно используется в следующих компаниях: Facebook, LinkedIn, Yahoo, CoackroachDB, DNANexus и др.

Ключами и привязанными к ним значениями могут выступать произвольные байтовые массивы данных. Связки ключ/значение хранятся в отсортированном по ключу упорядоченном виде, метод сортировки задаётся через задаваемую пользователем функцию сравнения (comparator). Управление данными производится через базовые операторы Put, Write (запись в пакетном режиме) , Get, MultiGet, Delete и Scan, RangeScan (переход на удовлетворяющие определённым критериям соседние элементы отсортированного списка).

В рамках одной атомарной операции в базу может быть внесено сразу несколько изменений (Write). Поддерживается создание снапшотов со срезом состояния БД в текущий момент времени. Для контроля за возможным повреждением данных для каждого блока сохраняется контрольная сумма.

RocksDB – это встраиваемое решение. И для того что бы ее можно было использовать ее нужно либо встроить в свое приложение, либо обернуть в сервер. Официально поддерживается API на C++ и Java. Ниже приведен фрагмент кода на C++ для работы ним:

#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <assert.h>
#include "rocksdb/c.h"
#include <unistd.h> 

const char DBPath[] = "/tmp/rocksdb";
const char DBBackupPath[] = "/tmp/rocksdb_backup";

int main(int argc, char **argv) {
  rocksdb_t *db;
  rocksdb_backup_engine_t *be;
  rocksdb_options_t *options = rocksdb_options_create();

  // Optimize RocksDB. This is the easiest way to
  // get RocksDB to perform well
  // get # of online cores
  long cpus = sysconf(_SC_NPROCESSORS_ONLN);
  rocksdb_options_increase_parallelism(options, (int)(cpus));
  rocksdb_options_optimize_level_style_compaction(options, 0);

  // create the DB if it's not already present
  rocksdb_options_set_create_if_missing(options, 1);

  // open DB
  char *err = NULL;
  db = rocksdb_open(options, DBPath, &err);
  assert(!err);

  // open Backup Engine that we will use for backing up our database
  be = rocksdb_backup_engine_open(options, DBBackupPath, &err);
  assert(!err);

  // Put key-value
  rocksdb_writeoptions_t *writeoptions = rocksdb_writeoptions_create();
  const char key[] = "key";
  const char *value = "value";
  rocksdb_put(db, writeoptions, key, strlen(key), value, strlen(value) + 1,
              &err);
  assert(!err);
  // Get value
  rocksdb_readoptions_t *readoptions = rocksdb_readoptions_create();
  size_t len;
  char *returned_value =
      rocksdb_get(db, readoptions, key, strlen(key), &len, &err);
  assert(!err);
  assert(strcmp(returned_value, "value") == 0);
  free(returned_value);

  // create new backup in a directory
  //specified by DBBackupPath
  rocksdb_backup_engine_create_new_backup(be, db, &err);
  assert(!err);

  rocksdb_close(db);

  // If something is wrong, you might want to restore data from last backup
  rocksdb_restore_options_t *restore_options =
    rocksdb_restore_options_create();

  rocksdb_backup_engine_restore_db_from_latest_backup(
    be, DBPath, DBPath, restore_options, &err);

  assert(!err);
  rocksdb_restore_options_destroy(restore_options);

  db = rocksdb_open(options, DBPath, &err);
  assert(!err);

  // cleanup
  rocksdb_writeoptions_destroy(writeoptions);
  rocksdb_readoptions_destroy(readoptions);

  rocksdb_options_destroy(options);
  rocksdb_backup_engine_close(be);
  rocksdb_close(db);
  return 0;
}

 

Тэги: nosql rocksdb базы данных


 


 
архив

подписка