Чи існують бази даних у Kubernetes?

Чи існують бази даних у Kubernetes?

Якось так історично склалося, що IT-індустрія з будь-якого приводу розбивається на два умовні табори: які за і проти. Причому предмет суперечок може бути довільним. Яка ОС краща: Win чи Linux? На смартфоні Android чи iOS? Зберігати все у хмарах або заливати на холодні RAID-сховища та класти гвинти у сейф? Чи мають PHP-шники право називатися програмістами? Ці суперечки носять часом винятково екзистенційний характер і не мають під собою жодної іншої, крім спортивного інтересу, бази.

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

І, здавалося б, була б це проста суперечка між двома сторонами однієї медалі. Такий же безглуздий і нещадний, як споконвічне протистояння Win vs Linux, в якому адекватні люди цілком існують десь посередині. Ось тільки у випадку контейнеризації не все так просто. Зазвичай у таких суперечках не буває правої сторони, але у разі «застосовувати» чи «не застосовувати» контейнери для зберігання БД все стає з ніг на голову. Тому що в певному сенсі мають рацію і прихильники і противники подібного підходу.

Світла сторона

Коротко описати аргументацію Світлої Сторони можна однією фразою: "Алло, 2к19 за вікном!" Звучить як популізм, безперечно, але якщо вникати в ситуацію детально, там є свої плюси. Їх зараз і розберемо.

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

Правильно дані. Серце будь-якого проекту - його дані: це може бути як типова СУБД - MySQL, Postgre, MongoDB, так і сховища, що використовуються для пошуку (ElasticSearch), key-value сховища для кешування - наприклад, redis, і т.д. говоритимемо про криві варіанти реалізації бекенда, коли БД падає через погано написані запити, а натомість поговоримо про забезпечення відмовостійкості цієї самої БД під клієнтським навантаженням. Адже коли ми контейнеризуємо наш додаток і дозволяємо йому вільно масштабуватися для обробки будь-якої кількості запитів, що входять, це закономірно збільшує і навантаження на базу даних.

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

Набагато логічніше кластеризувати як сам додаток, а й послуги, відповідальні за зберігання даних. При кластеризації і розгортанні веб-серверів, що незалежно працюють і розподіляють між собою, в k8s ми вже вирішуємо проблему синхронізації даних — тих же коментарів до постів, якщо наводити приклад якогось ЗМІ або блогоплатформи. У нас у будь-якому випадку заводиться внутрішньокластерне, нехай навіть віртуальне, представлення БД як ExternalService. Питання в тому, що сама БД поки не кластеризована — розгорнуті в кубику веб-сервери забирають інформацію про зміни із нашої статичної бойової бази, яка крутиться окремо.

Відчуваєте каверзу? Ми використовуємо k8s або Swarm для того, щоб розподілити навантаження та уникнути падіння основного веб-сервера, але ми не робимо цього для БД. Але якщо впаде БД, то у всій нашій кластеризованій інфраструктурі немає сенсу — користь нам від порожніх веб-сторінок, які повертають помилку доступу до бази даних?

Саме тому кластеризувати потрібно не лише веб-сервери, як це зазвичай і робиться, а й інфраструктуру бази даних. Тільки таким чином ми можемо забезпечити повноцінно працюючу в одній упряжці, але при цьому незалежну структуру. При цьому навіть якщо в нас «валиться» половина з нашого бекенду під навантаженням — решта виживе, і система синхронізації БД між собою в межах кластера і можливість нескінченного масштабування та розгортання нових кластерів допоможе швидко вийти на необхідні потужності — були б стійки у дата-центрі .

Крім того, розподілена в кластерах модель БД дозволяє забирати цю саму БД туди, де вона необхідна; якщо ми говоримо про глобальний сервіс, то досить нелогічно крутити веб-кластер десь у районі Сан-Франциско і при цьому ганяти пакети при зверненні до бази даних у Підмосков'ї та назад.

Також контейнеризація БД дозволяє збудувати всі елементи системи на одному рівні абстракції. Що, у свою чергу, уможливлює управління цією системою прямо з коду, розробниками, без активного залучення адмінів. Подумалося розробникам, що потрібна окрема СУБД нового підпроекту — легко! написали yaml-файл, завантажили до кластера і готово.

Та й само собою, внутрішня експлуатація спрощується у рази. Скажіть, скільки разів ви зажмурювалися в моменти, коли новий член команди пхав руки в бойову БД по роботі? Яка у вас, за фактом, одна і ось прямо зараз крутиться? Звичайно, всі ми тут люди дорослі, і в нас десь є свіженький бекап, а ще далі - за полицею з бабусиними огірками та старими лижами - ще один бекап, можливо навіть на холодному сховищі, бо одного разу вже ваш офіс горів. Але все одно, кожне введення нового члена команди, який має доступ до бойової інфраструктури і, звичайно ж, до бойової бази даних, це відро валідолу для всіх оточуючих. Ну хто його, новачка, знає, може він косорукий? Страшно, погодьтеся.

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

А тепер настав час перевзутися у противників кластеризації БД.

Темна сторона

Розмірковуючи, чому ж не варто контейнеризувати базу даних і продовжувати крутити її на одному центральному сервері, не опускатимемося до риторики ортодоксів та тверджень виду «діди крутили БД на залозі, і ми будемо!» Натомість давайте спробуємо придумати ситуацію, в якій контейнеризація справді приносила б відчутні дивіденди.

Погодьтеся, проектів, яким реально потрібна база в контейнері, можна перерахувати на пальцях однієї руки не найкращого фрезерувальника. Здебільшого навіть використання k8s або Docker Swarm буває надмірно — досить часто до цих інструментів вдаються через загальну хайповість технологій і установок «всевишніх» в особі гендирів загнати все в хмари і контейнери. Ну тому що зараз це модно і все так роблять.

Мінімум у половині випадків використання кубернетису або просто докера на проекті надмірно. Питання в тому, що не всі команди чи аутсорс-компанії, найняті обслуговувати інфраструктуру клієнта, усвідомлюють це. Гірше — коли контейнери нав'язуються, бо це постає у певну кількість монет клієнту.

Взагалі, існує думка, що докер/кубик-мафія тупо підминає під себе клієнтів, які дають ці інфраструктурні питання на аутсорс. Адже для того, щоб працювати з кластерами, потрібні інженери, які здатні на це розуміють взагалі архітектуру впровадженого рішення. Якось ми вже описували наш кейс з виданням Republic — там ми навчили команду клієнта працювати в реаліях кубернетису, і всі залишилися задоволені. І це було чимало. Найчастіше «впроваджувачі» k8s беруть інфраструктуру клієнта в заручники — адже тепер тільки вони розуміють, як там усе працює, на стороні клієнта фахівців немає.

А тепер уявіть, що таким чином ми віддаємо не лише веб-серверну частину на відкуп аутсорсу, а й обслуговування БД. Ми говорили, що БД – це серце, а втрата серця фатальна для будь-якого живого організму. Коротше, перспективи не найкращі. Так що замість хайпового кубернетису багатьом проектам варто просто не скаржитися на нормальний тариф на AWS, який вирішить усі проблеми з навантаженням на їх сайт/проект. Але AWS вже не модно, а понти дорожчі за гроші — на жаль, і в IT-середовищі теж.

Окей. Можливо, кластеризація проекту реально потрібна, але якщо зі stateless-додатками все зрозуміло, то як тоді організувати гідне забезпечення мережевої зв'язності кластеризованої бази даних?

Якщо ми говоримо про безшовне інженерне рішення, яким і є перехід на k8s, то головний наш головний біль — це реплікація даних у БД, що кластеризується. Якісь СУБД спочатку досить лояльно ставляться до розподілу даних між окремими екземплярами. Багато інших не настільки привітні. І досить часто основним аргументом у виборі СУБД для нашого проекту стає не здатність реплікуватися з мінімальними ресурсними та інженерними витратами. Особливо якщо проект не планувався як мікросервісний, а просто еволюціонував у цей бік.

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

Продовжуючи тему віртуальних ФС: Docker Volumes, на жаль, не безпроблемні. Загалом у такій справі як довгострокове надійне зберігання даних хотілося б обходитися максимально простими технічно схемами. І додавання нового шару абстракції з ФС контейнера до ФС батьківського хоста — вже ризик. Але коли ще й у роботі системи забезпечення контейнеризації виникають складнощі з транслюванням даних між цими шарами, тоді зовсім біда. На даний момент більшість відомих прогресивному людству проблем начебто викорінено. Але самі розумієте, що складніший механізм, то простіше він ламається.

У світлі всіх цих «пригод» набагато вигідніше і простіше тримати БД в одному місці, і навіть якщо вам знадобилася контейнеризація програми — нехай вона крутиться сама по собі і через розподільний шлюз отримує одночасний зв'язок з БД, який читатиметься і писатиметься лише один раз і в одному місці. Такий підхід знижує ймовірність помилок та розсинхронізацій до мінімальних значень.

До чого ми ведемо? До того, що контейнеризація БД доречна там, де є реальна необхідність. Не можна запхати базу фул-аппа і крутити її так, ніби у вас два десятки мікросервісів - це так не працює. І це слід чітко розуміти.

Замість висновку

Якщо ви чекаєте виразного висновку «віртуалізувати чи ні БД», то засмутимо: його тут не буде. Тому що при створенні будь-якого інфраструктурного рішення треба керуватися не модою та прогресом, а насамперед здоровим глуздом.

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

Джерело: habr.com

Додати коментар або відгук