YAWNDB - time series база даних

  1. трохи теорії
  2. RRDTool
  3. YAWNDB: загальна інформація
  4. Внутрішній пристрій
  5. установка
  6. конфігурація
  7. приклади використання
  8. висновок

В рамках багатьох наших послуг нам потрібно регулярно надавати клієнтам різну статистичну інформацію

В рамках багатьох наших послуг нам потрібно регулярно надавати клієнтам різну статистичну інформацію. Клієнтам, що орендують виділені сервери, потрібна інформація про споживання трафіку. Користувачам хмарних серверів потрібна статистика використання апаратних і мережевих ресурсів, а користувачам хмарного сховища - статистика скачування файлів.

Найбільш простим і наочним способом подання статистичних даних є побудова графіків. Існує багато спеціалізованих програмних рішень, призначених для аналізу статистичних даних з подальшою візуалізаціей.Ми стали шукати підходящий інструмент; основною вимогою при цьому була висока продуктивність. В результаті цих пошуків ... Втім, про все по порядку. Почнемо з невеликого теоретичного вступу.

трохи теорії

На будь-якому графіку мережевої активності ви можете бачити різницю деяких параметрів протягом певного періоду часу (за місяць, за тиждень, за добу і т.п.) Щоб побудувати графік, необхідно обробити статистичний матеріал, що представляє собою сукупність пар «час - значення» за вказаний часовий проміжок. Такий матеріал називається тимчасовим поруч (англ. Time series).

Для аналізу часових рядів існує досить багато програмних інструментів. Їх спільною рисою є використання кільцевих баз даних (англ. Round Robin database). Кільцевій називається база даних, в якій обсяг збережених даних не змінюється з часом, оскільки кількість даних постійно: осередки бази даних задіюються циклічно.

У кільцевій базі даних зберігається один або кілька наборів даних, що об'єднуються в архіви (англ. Round Robin Archives, RRA). За своєю структурою кільцеві таблиці аналогічні масивам, у яких адреса останнього елемента збігається з адресою першого елемента. Положення останнього оновленого елемента зберігається у вигляді покажчика. Архіви пов'язані між собою так, що кожний наступний архів зберігає інформацію з попереднього: один архів зберігає дані з невеликим інтервалом між записами, інший через задану кількість інтервалів зберігає консолідовані дані з попереднього, третій робить це ще рідше і так далі.

Для цього використовуються функції консолідації, вбудовані в базу даних і застосовуються автоматично при оновленні інформації. Під функціями консолідації розуміється отримання мінімального, максимального, середнього і загального значень за вказаний період часу. Консолідація даних в кільцевих базах здійснюється за записи, а не під час зчитування (завдяки цьому забезпечується висока швидкість роботи).

RRDTool

Найвідомішим і найпоширенішим інструментом для аналізу часових рядів та подальшої візуалізації є, звичайно ж,.

Ми пробували використовувати RRDTool в своїй практиці, однак він з цілого ряду причин нас не влаштував - в першу чергу тому, що дуже погано справлявся з навантаженнями.

Коли кількість файлів, в які ми записували дані, перевищила 1000, почали виникати проблеми: наприклад, запис цих самих даних стала займати занадто багато часу. Іноді дані просто не записувалися, хоча ніяких помилок або перебоїв в роботі не виникало.

Наведених фактів цілком достатньо, щоб зробити висновок про те, що RRDTool абсолютно нам не підходить: з наявним у нас кількістю віртуальних машин в хмарі потрібно здійснювати десятки тисяч операцій записи в секунду.

Зменшити кількість операцій запису на диск при роботі з великими обсягами даних в RRD Tool можна за допомогою демона RRDcacheD, який кешируєт дані і після накопичення певного обсягу записує в базу. Однак практика показала, що для вирішення наших завдань RRDcacheD підходить погано.

Акумулюючи дані, він в той же час не дає прочитати їх з кешу, а тільки записує на диск. Якщо потрібно якимось чином обробити дані, то буде потрібно все записати на диск і потім зчитувати з диска. Чим більше обсяг даних, тим гірше працює кеш: сильно завантажується жорсткий диск, створюється додаткове навантаження на процесор ...

Ще одна особливість RRDcacheD полягає в тому, що він пише дані на диск в найнесподіваніший і невідповідний момент.

Аргументом проти RRDTool стала і неможливість змінити налаштування кільцевої бази даних. Звичайно, це можна зробити шляхом експорту даних, створення файлу з новими параметрами та подальшого імпорту в нього старих даних, але такий спосіб занадто незручний і трудомісткий.

Зіткнувшись з усіма описаними труднощами, ми вирішили від використання RRDTool відмовитися. Пробували ми і інші засоби обробки і візуалізації даних - наприклад,, що не підійшов нас через низьку продуктивність.

В ході знайомства з існуючими інструментами ми все виразніше розуміли, що жоден з них під нашу специфіку не підходить. У нас виникло бажання розробити власне рішення, яке повністю відповідає всім нашим вимогам. Основними вимогами до продукту були, по-перше, гнучкість, налаштування і можливість адаптації під специфіку наших сервісів, а по-друге - висока продуктивність. Так з'явилася кільцева in-memory база даних YAWNDB.

YAWNDB: загальна інформація

YAWNDB (ця назва з англійським дієсловом to yawn - «позіхати» - нічого спільного не має; акронім YAWN означає Yet Another iNvented Wheel) являє собою in-memory базу даних; всі дані зберігаються в пам'яті і періодично записуються на диск. Вона написана на Erlang. Модель легковагих процесів, що лежить в основі цієї мови, дозволяє забезпечити швидку обробку великих наборів даних при невеликому споживанні системних ресурсів.

Вступники в YAWNDB дані розподіляються по архівах (в термінології YAWNDB званим також кошиками - buckets) відповідно до деякими правилами.

Під правилом розуміється набір властивостей для тієї чи іншої статистики (розмір даних, період збору і т.п.).

Всі ці дані представляють собою триплети, що складаються з часу, значення і ключа (ключ в термінології YAWNDB називається також шляхом). Шлях являє собою послідовність малих літер і цифр, що визначає, де саме повинен бути збережений триплет. У цій послідовності найбільш важливий перший компонент - префікс. Правило включає в тому числі і поле Prefix і таким чином визначає, як зберігаються дані для конкретного префікса. Для одного і того ж префікса можна створювати кілька правил. В такому випадку триплет буде записаний в базу відповідно до кожного з цих правил.

Це означає, що конкретна пара «час - значення» надійде в N кошиків, де N - кількість правил, відповідних префіксу шляху для даної пари.

Використовуваний нами підхід дозволяє отримати наступні переваги:

  • видалення втратили актуальність даних без зайвих витрат ресурсів;
  • фіксоване споживання пам'яті для певної кількості ключів;
  • фіксований час доступу до довільного запису.

Внутрішній пристрій

В основі YAWNDB лежить round-robin алгоритм, реалізований в бібліотеці на мові С.

Інші модулі, написані на Erlang взаємодіють з нею за допомогою NIF (Native Implemented Functions) .Для збереження даних на диску використовується Erlang-додаток.

REST API побудований на базі веб-сервера Cowboy.
Запис даних здійснюється через сокет, а зчитування - з допомогою REST API-інтерфейсу.

установка

Для роботи з YAWNDB потрібно обов'язково встановити парсер LibYAML . Потім потрібно клонувати репозиторій:

$ Git clone [email protected]: selectel / yawndb.git

І виконати наступні команди:

$ Cd yawndb $ make all

Запуск YAWNDB здійснюється за допомогою команди:

$ ./start.sh

Перед запуском необхідно скопіювати приклад конфігураційного файлу на місце справжнього:

$ Cp priv / yawndb.yml.example priv / yawndb.yml

Або ж створити відповідний симлінк.

конфігурація

Всі настройки YAWNDB зберігаються в конфігураційному файлі yawndb.yml.

Як приклад розглянемо конфігураційний файл, який використовується для обробки статистики в нашому хмарному сховище:

rules: # User statistics # деталізована статистика по хвилинах (за 24 години) - name: per_min prefix: clientstats type: sum timeframe: 60 limit 1440 split, backward value_size, large additional_values: [] # статистика по годинах (за останній місяць) - name: per_hour prefix: clientstats type: sum timeframe 3600 limit: 720 split: backward value_size: large additional_values: [] # статистика по днях (зберігати за останні два роки) - name: per_day prefix: clientstats type: sum timeframe: 86400 limit: 730 split: backward value_size: large additional_values: []

приклади використання

Формування пакету для запису даних (Python)

def encode_yawndb_packet (is_special, path, time, value): "" "Сформувати пакет даних для відправки в yawndb.: param bool is_special: спеціальне значення? використовується для additional_values: param str path: ідентифікатор метрики: param int value: значення метрики" " "is_special_int = 1 if is_special else 0 pck_tail = struct.pack ("> BBQQ ", YAWNDB_PROTOCOL_VERSION, is_special_int, time, value) + path pck_head = struct.pack ("> H ", len (pck_tail)) return pck_head + pck_tail Формування пакету для запису даних на С // задаємо версію протоколу #define YAWNDB_PROTOCOL_VERSION 3 // описуємо структуру пакета struct yawndb_packet_struct {uint16_t length; uint8_t version; int8_t isSpecial; uint64_t timestamp; uint64_t value; char path []; }; // формуємо пакет yawndb_packet_struct * encode_yawndb_packet (int8_t isSpecial, uint64_t timestamp, uint64_t value, const char * path) {yawndb_packet_struct * packet; uint16_t length; lenght = sizeof (uint8_t) + sizeof (int8_t) + sizeof (uint64_t) + sizeof (uint64_t) + strlen (path); packet = malloc (length + sizeof (uint16_t)); packet-> length = htobe16 (length); packet-> version = YAWNDB_PROTOCOL_VERSION; packet-> isSpecial = isSpecial; packet-> timestamp = htobe64 (timestamp); packet-> value = htobe64 (value); strncpy (packet-> path, path, strlen (path)); return packet; }

висновок

Сьогодні YAWNDB використовується нами як в публічних сервісах, так і на внутрішніх проектах. Вихідний код проекту. Ми будемо раді, якщо хтось із наших читачів скористається нашим продуктом. Будемо також дуже вдячні за зауваження і пропозиції щодо його поліпшення.

28 березня ми опублікували сайт присвячений нашим Open Source розробок: selectel.io . На ньому можна знайти детальну документацію до YAWNDB російською мовою , А також інформацію про інших наших проектах.

Param bool is_special: спеціальне значення?

Дополнительная информация

rss
Карта