Graphite був написаний Крісом Дейвісом (Chris Davis), співробітником компанії Orbitz в 2006 році. Мова програмування оригінального проекту - Python, але наразі майже всі компоненти Graphite можна замінити на сторонні, написані на мові Go. Більш того, навіть бібліотеку Whisper для роботи з базою Graphite можна замінити на альтернативні рішення зі збереженням даних в базі Cassandra, ClickHouse і т.п. Якраз про останній і піде мова цього разу.
Детальніше про оригінальний стек Graphite можна почитати в моїй попередній статті. До його недоліків можна віднести досить слабку продуктивність, неефективну роботу з дисковим простором, відсутність можливості масштабування бази даних і ін. Але це зовсім не значить, що він не підійде у випадках не надто високих навантажень.
Спершу пройдемось по кожному із компонентів та опишемо їх призначення.
- Carbon-clickhouse - демон, що працює у якості заміни оригінального Carbon та може писати отримані метрики від третіх систем в базу даних ClickHouse.
- ClickHouse - OLAP база даних, що була розроблена в компанії Yandex, проте із 2021 року вона розвивається в межах окремої одноіменної компанії. Пізніше розповім про неї детальніше.
- Graphite-clickhouse - проміжне програмне забезпечення для роботи між API сервісом та базою ClickHouse.
- Carbonapi - API-сервер Graphite, написаний на мові Go. Теоретично замість нього може бути використано Graphite-web (оригінальна імплементація API та веб-панель) чи Graphite-api (лише API на Flask фреймворку)
- Grafana - веб-панель на Go/NodeJS для побудови та відображення метрик. Вміє опитувати Graphite "із коробки", підтримує всі його API-функції. Для Grafana-и увесь описаний вгорі стек буде виглядати як звичайна інсталяція Graphite-у.
елементи наведені пунктиром - опціональні
1. CLICKHOUSE
1.1. ClickHouse intro
ClickHouse - база даних, що взяла свій початок в компанії Yandex, програмне рішення перевірене в бою, адже компанія використовує її для свого сервісу Yandex.Metrika. Код ClickHouse був відкритий в 2016 році, до цього часу база існувала як закритий продукт всередині компанії. Наразі це американська компанія, що базується в Bay Area.
ClickHouse - це стовпцева (колонкова) аналітична реляційна база. Це значить, що тут дані інакше зберігаються на диску ніж в більш традиційних "строкових" рішеннях на кшталт MySQL чи PostgreSQL. Кожне значення колонки (те що по-вертикалі) таблиці фізично буде зберігатись поряд, тобто послідовно записано в файл на диску. Інакше кажучи, значення з різних стовпців зберігаються окремо, а дані одного стовпця - разом. Ця особливість чудово підійде на запитах типу:
> SELECT time, region, smartphone FROM analitic_db WHERE region = 'Kyiv';
Усі інші стовпці таблиці, окрім наведених у прикладі, навіть не будуть прочитані з диску, що в свою чергу зменшить к-ть io-операцій і, як наслідок, позитивним чином вплине на швидкість роботи запиту.
А як же аналогічний запит буде виконуватись в реляційних (в т.ч. більш універсальних) базах?
ClickHouse має SQL-подібний синтаксис, хоч і не підтримує всі його можливості. Наприклад ця база даних не має транзакцій, відсутні точкові UPDATE/DELETE (пакетний UPDATE/DELETE був введений лише в червні 2018 роки) і т.п. Поряд з даними ClickHouse не зберігає метадані, що дозволяє в деякому сенсі прогнозувати розмір даних наперед. Всі ці особливості впливають на високі показники її продуктивності.
Зрозуміло, що ClickHouse не "срібна куля" і підійде далеко не для всіх сценаріїв роботи. Тенденції наразі вказують на те, що для кожної відносно популярної задачі пишуть мало не окрему базу, в чому дійсно є сенс на досить високих навантаженнях. Якщо система підходить під широку множину сценаріїв роботи, то, у разі інтенсивного її використання, система буде справлятися з усіма сценаріями роботи погано, або ж справлятися добре тільки з одним із них.
Не буду переказувати офіційну документацію ClickHouse, адже з нею можна ознайомитись за посиланням https://clickhouse.com/docs/ru/.
У чому ж плюси використання ClickHouse як бази для Graphite? Вони наступні:
- Має вбудований engine GraphiteMergeTree, що базується на MergeTree, але з функціоналом проріджування і агрегування/усереднення (storage aggregation/rollup/retention/downsampling). Це одна із основних фіч оригінального Whisper.
- Має вбудовані функції різних агрегацій даних.
- Вміє кластеризуватись (є висока доступність), доступна реплікація даних, sharding і паралелізація запитів між вузлами. Все це працює разом із ZooKeeper для координації роботи вузлів.
- Всі плюси описані вище: високий коефіцієнт стиснення даних, швидке читання/запис і т.п.
1.2. ClickHouse Installation
Для установки бази даних існують офіційні репозиторії Yandex (які, між іншим, можуть не коректно працювати в Україні), ними і скористаємось:
# apt-get install apt-transport-https ca-certificates dirmngr
# apt-key adv --keyserver hkp://keyserver.ubuntu.com:80 --recv 8919F6BD2B48D754
# echo "deb https://packages.clickhouse.com/deb stable main" | sudo tee \
/etc/apt/sources.list.d/clickhouse.list
/etc/apt/sources.list.d/clickhouse.list
# apt-get update
# apt-get install -y clickhouse-server clickhouse-client
# service clickhouse-server start
# apt-get install -y clickhouse-server clickhouse-client
# service clickhouse-server start
Налаштуємо правила агрегації для майбутніх даних:
# mkdir -p /etc/clickhouse-server/conf.d
# vim /etc/clickhouse-server/conf.d/graphite_rollup.xml
<yandex>
<graphite_rollup>
<!-- retentions = 30s:6h,1m:7d,5m:90d -->
<!-- carbon -->
<pattern>
<regexp>^carbon\.</regexp>
<function>avg</function>
<retention>
<age>0</age>
<precision>30</precision>
</retention>
<retention>
<age>21600</age>
<precision>60</precision>
</retention>
<retention>
<age>604800</age>
<precision>300</precision>
</retention>
</pattern>
<!-- for all below retentions = 30s:14d,5m:90d,10m:180d,30m:2y -->
<!-- min -->
<pattern>
<regexp>\.min$</regexp>
<function>min</function>
<retention>
<age>0</age>
<precision>30</precision>
</retention>
<retention>
<age>1209600</age>
<precision>300</precision>
</retention>
<retention>
<age>7776000</age>
<precision>600</precision>
</retention>
<retention>
<age>15552000</age>
<precision>1800</precision>
</retention>
</pattern>
<!-- max -->
<pattern>
<regexp>\.max$</regexp>
<function>max</function>
<retention>
<age>0</age>
<precision>30</precision>
</retention>
<retention>
<age>1209600</age>
<precision>300</precision>
</retention>
<retention>
<age>7776000</age>
<precision>600</precision>
</retention>
<retention>
<age>15552000</age>
<precision>1800</precision>
</retention>
</pattern>
<!-- sum -->
<pattern>
<regexp>\.count$</regexp>
<function>sum</function>
<retention>
<age>0</age>
<precision>30</precision>
</retention>
<retention>
<age>1209600</age>
<precision>300</precision>
</retention>
<retention>
<age>7776000</age>
<precision>600</precision>
</retention>
<retention>
<age>15552000</age>
<precision>1800</precision>
</retention>
</pattern>
<!-- default_average -->
<default>
<function>avg</function>
<retention>
<age>0</age>
<precision>30</precision>
</retention>
<retention>
<age>1209600</age>
<precision>300</precision>
</retention>
<retention>
<age>7776000</age>
<precision>600</precision>
</retention>
<retention>
<age>15552000</age>
<precision>1800</precision>
</retention>
</default>
</graphite_rollup>
</yandex>
age - це мінімальний час з котрого активується наступна точність (precision). Досить специфічна логіка як на мене. Цей yaml-опис відповідає наступним конфігураційним файлам оригінального Graphite:
$ cat /etc/carbon/storage-schemas.conf
[carbon]
pattern = ^carbon\.
retentions = 30s:6h,1m:7d,5m:90d
[default_1min_for_1day]
pattern = .*
retentions = 30s:14d,5m:90d,10m:180d,30m:2y
$ cat /etc/carbon/storage-aggregation.conf
[min]
pattern = \.min$
xFilesFactor = 0.1
aggregationMethod = min
[max]
pattern = \.max$
xFilesFactor = 0.1
aggregationMethod = max
[sum]
pattern = \.count$
xFilesFactor = 0
aggregationMethod = sum
[default_average]
pattern = .*
xFilesFactor = 0.5
aggregationMethod = average
Останній взято з /usr/share/doc/graphite-carbon/examples/storage-aggregation.conf.example, детальніше про це я писав у попередній статті. Перетворити схему оригінального Graphite в ClickHouse можна використавши програму за наступним посиланням https://github.com/bzed/carbon-schema-to-clickhouse
Виходячи з назви метрики, котра буде надсилатись, Graphite буде використовувати відповідне правило агрегації.
$ echo "test.count 14 `date +%s`" | nc -q0 127.0.0.1 2003
Ця команда відправить метрику, котра буде агрегована по правилу sum, адже вона містить значення count в кінці. Але дані надсилати поки зарано, адже ще не налаштовано сarbon-clickhouse.
Додаємо в автозавантаження та запускаємо/перезапускаємо clickhouse-server:
# systemctl daemon-reload
# systemctl enable clickhouse-server
# systemctl restart clickhouse-server
Після чого створюємо таблиці для Graphite даних:
# clickhouse-client
:) CREATE DATABASE graphite;
:) CREATE TABLE graphite.graphite ( Path String, Value Float64, Time UInt32, Date Date, Timestamp UInt32 ) ENGINE = GraphiteMergeTree(Date, (Path, Time), 8192, 'graphite_rollup');
:) CREATE TABLE graphite.graphite_tree ( Date Date, Level UInt32, Path String, Deleted UInt8, Version UInt32 ) ENGINE = ReplacingMergeTree(Date, (Level, Path), 8192, Version);
Значення graphite_rollup в ENGINE має відповідати значенню в xml-тегу в graphite_rollup.xml.
2. INSTALLATION AND CONFIGURATION OF CARBON-CLICKHOUSE
Як я вже згадував, Carbon-clickhouse - демон, що приймає дані та записує їх до бази ClickHouse. Автор проекту збирає deb/rpm пакет програми, тому не бачу причини ним не скористатись:
# wget https://github.com/lomik/carbon-clickhouse/releases/download/v0.9.1/carbon-clickhouse_0.9.1_amd64.deb
# dpkg -i carbon-clickhouse_0.9.1_amd64.deb
Пакети зібрані не дуже якісно, тому після їх установки необхідно створити наступні директорії:
# mkdir -p /var/lib/carbon-clickhouse/data
# mkdir -p /var/log/carbon-clickhouse
Відредагуємо основний конфігураційний файл програми:
# vim /etc/carbon-clickhouse/carbon-clickhouse.conf
...
metric-interval = "30s"
...
path = "/var/lib/carbon-clickhouse/data"
...
[upload.graphite]
type = "points"
table = "graphite.graphite"
zero-timestamp = false
...
[upload.graphite_tree]
type = "tree"
table = "graphite.graphite_tree"
zero-timestamp = false
...
[[logging]]
logger = ""
file = "/var/log/carbon-clickhouse/carbon-clickhouse.log"
level = "error"
Опція zero-timestamp = true теоретично може зекономити багато простору на диску, адже Timestamp стовпчик часто не використовується, проте він обов'язковий для роботи GraphiteMergeTree engine.
Цікаво, що Сarbon-clickhouse має вбудований prometheus-інтерфейс, що дозволяє перенаправляти його дані для довготермінового зберігання без додаткових адаптерів:
...
[prometheus]
listen = ":2006"
enabled = false
drop-future = "0s"
drop-past = "0s"
...
Додамо програму в автозавантаження та запустимо:
# systemctl enable carbon-clickhouse
# systemctl start carbon-clickhouse
Для перевірки роботи Carbon-clickhouse та ClickHouse, відправимо тестову метрику:
# echo "test.count 14 `date +%s`" | nc -q0 127.0.0.1 2003
Та перевіримо її присутність в базі:
# clickhouse-client
ClickHouse client version 18.16.0.
Connecting to localhost:9000.
Connected to ClickHouse server version 18.16.0 revision 54412.
ubuntu :) select * from graphite.graphite where Path='test.count';
SELECT *
FROM graphite.graphite
WHERE Path = 'test.count'
┌─Path───────┬─Value─┬───────Time─┬───────Date─┬──Timestamp─┐
│ test.count │ 14 │ 1544979360 │ 2018-12-16 │ 1544979362 │
└────────────┴───────┴────────────┴────────────┴────────────┘
1 rows in set. Elapsed: 0.019 sec.
ubuntu :) select * from graphite.graphite_tree where Path='test.count';
SELECT *
FROM graphite.graphite_tree
WHERE Path = 'test.count'
┌───────Date─┬─Level─┬─Path───────┬─Deleted─┬────Version─┐
│ 2016-11-01 │ 2 │ test.count │ 0 │ 1544979363 │
└────────────┴───────┴────────────┴─────────┴────────────┘
1 rows in set. Elapsed: 0.007 sec.
Для всіх програм, що раніше надсилали статистику до Graphite ці заміни "під капотом" будуть абсолютно прозорими.
3. INSTALLATION OF GRAPHITE-CLICKHOUSE
Graphite-clickhouse - це драйвер читання даних з бази ClickHouse. Процедура його установки аналогічна:
# wget https://github.com/lomik/graphite-clickhouse/releases/download/v0.8.1/graphite-clickhouse_0.8.1_amd64.deb
# dpkg -i graphite-clickhouse_0.8.1_amd64.deb
Як і випадку із carbon-clickhouse, для роботи потрібно створити директорію для збереження логів:
# mkdir -p /var/log/graphite-clickhouse
Додамо інформацію щодо агрегації даних (ту ж саму, котру додавали до ClickHouse):
# vim /etc/graphite-clickhouse/graphite_rollup.xml
<graphite_rollup>
<!-- retentions = 30s:6h,1m:7d,5m:90d -->
<!-- carbon -->
<pattern>
<regexp>^carbon\.</regexp>
<function>avg</function>
<retention>
<age>0</age>
<precision>30</precision>
</retention>
<retention>
<age>21600</age>
<precision>60</precision>
</retention>
<retention>
<age>604800</age>
<precision>300</precision>
</retention>
</pattern>
<!-- for all below retentions = 30s:14d,5m:90d,10m:180d,30m:2y -->
<!-- min -->
<pattern>
<regexp>\.min$</regexp>
<function>min</function>
<retention>
<age>0</age>
<precision>30</precision>
</retention>
<retention>
<age>1209600</age>
<precision>300</precision>
</retention>
<retention>
<age>7776000</age>
<precision>600</precision>
</retention>
<retention>
<age>15552000</age>
<precision>1800</precision>
</retention>
</pattern>
<!-- max -->
<pattern>
<regexp>\.max$</regexp>
<function>max</function>
<retention>
<age>0</age>
<precision>30</precision>
</retention>
<retention>
<age>1209600</age>
<precision>300</precision>
</retention>
<retention>
<age>7776000</age>
<precision>600</precision>
</retention>
<retention>
<age>15552000</age>
<precision>1800</precision>
</retention>
</pattern>
<!-- sum -->
<pattern>
<regexp>\.count$</regexp>
<function>sum</function>
<retention>
<age>0</age>
<precision>30</precision>
</retention>
<retention>
<age>1209600</age>
<precision>300</precision>
</retention>
<retention>
<age>7776000</age>
<precision>600</precision>
</retention>
<retention>
<age>15552000</age>
<precision>1800</precision>
</retention>
</pattern>
<!-- default_average -->
<default>
<function>avg</function>
<retention>
<age>0</age>
<precision>30</precision>
</retention>
<retention>
<age>1209600</age>
<precision>300</precision>
</retention>
<retention>
<age>7776000</age>
<precision>600</precision>
</retention>
<retention>
<age>15552000</age>
<precision>1800</precision>
</retention>
</default>
</graphite_rollup>
Відредагуємо конфігураційний файл програми, де вкажемо адресу цього файлу, назву бази даних та таблиці, де зберігатимуться метрики:
# vim /etc/graphite-clickhouse/graphite-clickhouse.conf
...
[clickhouse]
url = "http://localhost:8123"
data-table = "graphite.graphite"
tree-table = "graphite.graphite_tree"
date-tree-table = ""
date-tree-table-version = 0
tagged-table = ""
tagged-autocomplete-days = 7
reverse-tree-table = ""
tag-table = ""
rollup-conf = "/etc/graphite-clickhouse/graphite_rollup.xml"
extra-prefix = ""
data-timeout = "1m0s"
tree-timeout = "1m0s"
connect-timeout = "1s"
...
[[logging]]
logger = ""
file = "/var/log/graphite-clickhouse/graphite-clickhouse.log"
level = "error"
encoding = "mixed"
encoding-time = "iso8601"
encoding-duration = "seconds"
Запустимо програму:
# systemctl enable graphite-clickhouse
# systemctl start graphite-clickhouse
# ps aux | grep graphite-clickhouse
root 1800 0.1 0.5 52612 8304 ? Ssl 18:59 0:00 /usr/bin/graphite-clickhouse -config /etc/graphite-clickhouse/graphite-clickhouse.conf
4. CARBONAPI
Carbonapi - API-сервер Graphite написаний на Go, майже останній елемент ланцюга програм, якщо не брати до уваги Grafana-у. Вміє працювати не лише з Graphite-clickhouse, а і наприклад з go-carbon.
Використовуючи офіційні репозиторії проекту, проінсталюємо програму:
# curl -s https://packagecloud.io/install/repositories/go-graphite/stable/script.deb.sh | bash
# apt install carbonapi -y
Створимо конфігураційний файл Carbonapi:
# mkdir /etc/carbonapi
# vim /etc/carbonapi/carbonapi.yaml
listen: "[::]:9091"
concurency: 20
cache:
# Type of caching. Valid: "mem", "memcache", "null"
type: "mem"
defaultTimeoutSec: 60
upstreams:
backends:
- "http://localhost:9090"
graphite:
# Host:port where to send internal metrics
# Empty = disabled
host: "localhost:2003"
interval: "10s"
prefix: "carbon.api"
logger:
- logger: ""
file: "stderr"
level: "error"
encoding: "console"
encodingTime: "iso8601"
encodingDuration: "seconds"
- logger: ""
file: "carbonapi.log"
level: "error"
encoding: "json"
Розширену версію конфігураційного файлу можна знайти за адресою https://github.com/go-graphite/carbonapi/blob/master/cmd/carbonapi/carbonapi.example.yaml.
Додамо програму в автозавантаження:
# systemctl enable carbonapi
# systemctl start carbonapi
5. INSTALLATION OF GRAFANA
Grafana - веб-панель для відображення графічних даних, котра в тому числі може працювати з Graphite API і підтримує його вбудовані функції. Не буду надто зупинятись на її установці:
# echo 'deb https://packagecloud.io/grafana/stable/debian/ stretch main' > /etc/apt/sources.list.d/grafana.list
# curl https://packagecloud.io/gpg.key | apt-key add -
# apt update
# apt install grafana -y
# systemctl daemon-reload
# systemctl enable grafana-server
# systemctl start grafana-server
Після чого переходимо на її сторінку налаштувань, де вказуємо порт Carbonapi як на малюнку.
6. WHAT ELSE TO READ?
GrapHouse
Компанія Yandex розвиває свій власний стек для Graphite і окрім ClickHouse розробляє також GrapHouse. Останній замінює одразу як Carbon-clickhouse, так і Graphite-clickhouse. У якості API може використовувати Graphite-web чи Graphite-api з додатковим плагіном. Інструкцію його налаштування можна знайти за посиланням https://github.com/yandex/graphouse/blob/master/doc/install.md, якщо буде потреба поділитись досвідом його налаштування - запрошую в коментарі. По деяким опосередкованим даним він дещо повільніший за стек на Go, описаний вище.
https://www.altinity.com/blog/2018/5/16/clickhouse-graphouse-introduction
https://github.com/yandex/graphouse/blob/master/doc/install.md
https://www.percona.com/live/17/sites/default/files/slides/clickhouse-as-timeseries-database.pdf
https://github.com/yandex/graphouse/blob/master/doc/install.md#graphite-api
https://graphite-api.readthedocs.io/en/latest/deployment.html#gunicorn-nginx
https://graphite-api.readthedocs.io/en/latest/installation.html#global-installation
https://markinbristol.wordpress.com/2015/09/20/setting-up-graphite-api-grafana-on-a-raspberry-pi/
StatsD Servers
Писати напряму в Carbon може бути не найкращою ідеєю на дуже великих навантаженнях, наприклад, коли програми надсилають тисячі повідомлень в секунду чи потрібно додатково агрегувати дані (вираховувати персентилі, відхилення і т.п.). У такому разі може допомогти StastD, що працюватиме у якості Proxy попереду Carbon. Оригінальна імплементація від Etsy, написана на JavaScript, не вирізняється високою швидкістю та і проект, здається, вже мертвий. Про неї я писав у попередній статті про Graphite. Щодо актуальних проектів StatsD серверів можна прочитати за посиланням https://medium.com/@_ipeacocks/statsd-which-implementation-is-still-alive-9f4e63001432
Важливо не забути відредагувати правила агрегації ClickHouse перед використанням StatsD в prod-середовищі. Їх вигляд залежить від того, який саме StatsD сервер буде використано, адже вони не дуже стандартизовані. Наприклад, у разі використання Telegraf, rollup для персентилів має бути налаштований так:
<!-- percentile -->
<pattern>
<regexp>\.(\d+)?_percentile$</regexp>
<function>max</function>
<retention>
<age>0</age>
<precision>30</precision>
</retention>
<retention>
<age>1209600</age>
<precision>300</precision>
</retention>
<retention>
<age>7776000</age>
<precision>600</precision>
</retention>
<retention>
<age>15552000</age>
<precision>1800</precision>
</retention>
</pattern>
А для Gostatsd від Atlassian стандартна схема більше ніж підходить https://blog.ipeacocks.info/2016/04/graphite-configuration-sending-metrics.html
Ну і т.п. Загалом не завадить розуміти, що значить кожен тип даних, що надсилає StatsD до Carbon:
https://github.com/etsy/statsd/blob/master/docs/metric_types.md
Moira
Grafana має вбудований інструментарій сповіщення у разі спрацювання тригерів. Вона використовує базу даних Graphite для всіх необхідних виборок, що може бути не дуже ефективно в разі складних запитів. Moira, opensource рішення від компанії Контур, пропонує інакше підійти до рішення цієї проблеми. Задля зменшення навантаження на основну базу Graphite, Moira аналізує копію даних, що зберігатиметься в Redis. Ця репліка створюється одночасною відправкою даних (за допомогою, наприклад, carbon-c-relay) на 2 бекенди: основний Graphite та додатковий Moira/Redis. Сервіс має гарний інтерфейс, активно розробляється, має готові докер контейнери, присутній потужний інструментарій інформування щодо проблем, має хорошу документацію. Тож я не бачу причин не спробувати Moira-у.
https://habr.com/company/skbkontur/blog/276403/
https://github.com/kolobaev/moira-tldr
OLAP Databases
https://habr.com/post/126810/
http://www.olap.ru/basic/alpero2i.asp
https://ruhighload.com/Колоночные+базы+данных
Carbonapi
https://www.usenix.org/conference/srecon17asia/program/presentation/smirnov
https://archive.fosdem.org/2017/schedule/event/graphite_at_scale/
Graphite/ClickHouse
https://github.com/feangulo/graphite-stresser
https://clickhouse.yandex/#independent-benchmarks
https://clickhouse.yandex/benchmark.html
https://hackernoon.com/clickhouse-an-analytics-database-for-the-21st-century-82d3828f79cc
https://rascal.su/blog/2017/09/25/настраиваем-graphite-с-хранилищем-метрик-в-clickhouse/
https://www.altinity.com/blog/2018/5/10/circular-replication-cluster-topology-in-clickhouse
https://www.percona.com/blog/2017/02/13/clickhouse-new-opensource-columnar-database/
https://www.slideshare.net/Altinity/migration-to-clickhouse-practical-guide-by-alexander-zaitsev
https://github.com/bzed/carbon-schema-to-clickhouse
https://habr.com/company/avito/blog/335410/
https://habr.com/company/avito/blog/343928/
https://graphite.readthedocs.io/en/latest/tags.html#carbon
https://github.com/lomik/graphite-clickhouse-tldr
https://github.com/kolobaev/graphite-clickhouse-tldr
https://github.com/lomik/graphite-clickhouse/wiki/RU
http://bulimov.ru/it/graphite-experience/
http://guruhub.com.uy/blog/graphite-functions
https://kevinmccarthy.org/2013/07/18/10-things-i-learned-deploying-graphite/
https://wikitech.wikimedia.org/wiki/Graphite
https://news.ycombinator.com/item?id=8908423
https://grisha.org/blog/2015/05/04/recording-time-series/
http://rus-linux.net/MyLDP/BOOKS/Architecture-Open-Source-Applications/Vol-1/graphite-01.html
Немає коментарів:
Дописати коментар