Рубріки: Досвід

Міграція з HTTP API на GRPC: мої «за» та «проти» на власному досвіді роботи над проєктом

Ігор Закутинський

Привіт! Мене звати Ігор Закутинський, я Head of Engineering GetProspect — українського інструменту лідогенерації, що дозволяє знаходити тисячі імейлів у LinkedIn за декілька кліків.

У цій статті я хочу поділитися власним досвідом міграції одного з сервісів проєкту з HTTP API на GRPC, що дозволило компанії оптимізувати ресурси та значно збільшити її продуктивність.

Короткий огляд платформи для лідогенерації GetProspect

Головним завдання нашого сервісу є пошук електронної адреси певного профілю в LinkedIn. Це відбувається завдяки алгоритму, шо аналізує дані, які вказує користувач у соцмережі. Після того, як всі імейли знайдені, завдяки GetProspect можна легко керувати своїми контактами у нашій CRM-системі. Для того, щоб база електронних пошт була максимально повною, користувач додатково може завантажувати у неї дані з таких джерел:

  • Google Chrome extension;
  • CSV-файл;
  • через API;
  • інтеграції зі сторонніми сервісами (наприклад Zapier);
  • Google-таблиці.

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

Чому ми використовуємо мікросервіси?

Навантаження є динамічним і важкопрогнозованим, тому основними вимогами до архітектури сервісу є доступність та масштабованість.

GetProspect реалізований по класичній мікросервісній архітектурі, де кожен мікросервіс відповідає таким критеріям:

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

Мікросервісна комунікація

Більшість сервісів мають взаємодіяти як з внутрішніми, так і з зовнішніми ресурсами. Тому одною з головних складових, що впливає на продуктивність системи, є мікросервісна комунікація. 

Наші мікросервіси використовують HTTP RESTfull API, як базовий протокол обміну даних. 

REST (Representational State Transfer) — це архітектурний стиль взаємодії розподілених компонентів в мережі.

Основні переваги REST API і чому ми його використовуємо:

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

HTTP REST API задовольняє основні потреби обміну даних між мікросервісами, але через конструктивні особливості не може використоуватись у всіх випадках.

Одним з основних завдань нашого інструменту лідогенерації є пошук імейлу користувача. Пошук електронної пошти базується на SMTP-діалозі з email-сервером та може тривати від кількох секунд до 10 хвилин. 

SMTP (Simple Mail Transfer Protocol) — це комунікаційний протокол для пересилання електронної пошти.

Процес пошуку та валідації email-адрес реалізований на окремому мікросервісі — Mail verification service, а логіка збереження та управління даними на API service

На першому етапі реалізація мала наступний вигляд:

Початкова схема реалізації (натисніть, щоб роздивитися)

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

Як видно зі схеми, API service ініціює пошук імейл-адреси на Mail verification service за допомогою HTTP-запита, і через певний час, коли буде завершено процес пошуку, Mail verification service повертає результат також через HTTP-запит на API Service.

Тобто для того, щоб знайти email-адресу виконувалось як мінімум два HTTP-запити (насправді їх було дещо більше 😉), що породжувало декілька проблем:

  • По-перше, вплив на швидкість та продуктивність. Кожен HTTP-запит ініціює нове клієнт-сервер-з’єднання, що створює велике навантаження.
  • По-друге, це те, що запити не мали спільного контексту, оскільки в REST-архітектурі відсутнє збереження стану запиту (stateless), тобто сервер виконує кожен клієнтський запит не залежно від попередніх.

В якості оптимізації ми розглянули використання GRPC для комунікації цих двох мікросервісів, оскільки в ньому архітектурно вирішені недоліки, про які я писав вище.  

Що таке GRPC? Чому ми його обрали для мікросервісної комунікації?

GRPC це сучасний протокол RPC, реалізований зверху HTTP/2.

HTTP/2  — це протокол рівня 7 (рівень додатків), який працює зверху протоколу TCP (рівень 4 — транспортний рівень), який працює зверху протоколу IP (рівень 3 — мережевий рівень). 

GRPC має багато переваг традиційним HTTP/REST/JSON, наприклад:

  • двійковий протокол (HTTP/2);
  • мультиплексування багатьох запитів на одному з’єднанні (HTTP/2);
  • стиснення заголовку (HTTP/2);
  • суворо типізований сервіс і повідомлення (Protobuf);
  • серіалізація/десеріалізація даних.

Повідомлення GRPC серіалізуються за допомогою Protobuf — ефективного двійкового формату повідомлень. Protobuf дуже швидко виконує серіалізацію на сервері та клієнті. 

Protobuf швидко виконує серіалізацію на сервері та клієнті

За допомогою Protobuf-серіалізації нам вдалось значно зменшити об’єм корисних даних, а отже збільшити пропускну здатність між API-сервісом та сервісом, який процесить пошук email-адрес. Також значно спростилась логіка пошуку. На боці API service процес пошуку імейла виглядає як виклик асинхронної функції (віддаленої процедури у випадку з gRPC 😉).

Тест продуктивності: GRPC vs HTTP Restful API

Я вирішив провести тест, для якого використовував два AWS EC2 c5.2xLarge instance, на яких були запущені Node.js application — клієнт та сервер.

В даному тесті клієнт робить простий запит на сервер або викликає процедуру, а сервер просто повертає значення без будь-якої складної логіки, оскільки метою є визначення продуктивності протоколу. В тесті визначається кількість можливих запитів за одиницю часу (1 секунду, а також час на виконання 100к запитів або ж викликів процедур).

gRPC server, який використовувався для тесту:

Натисніть, щоб роздивитися

gRPC client, який використовувався для тесту:

Натисніть, щоб роздивитися

Для тесту HTTP Rest API реалізована аналогічна логіка на Fastify та Axios.  

Результати тесту:

HTTP Post request gRPC procedure call
100k async requests, sec 32.342 4.370
Requests per second 2147 26102
CPU usage – ms/req 491 ms / per request 211 ms / per request

Як видно з графіку, пропускна здатність GRPC більш ніж у вісім разів вища за HTTP API, що значно підвищує продуктивність на великих об’ємах запитів. Також слід відмітити те, що CPU час на 1 gRPC процедуру більш ніж в два рази менший, ніж на аналогічний HTTP-запит. 

Балансування навантаження

Оскільки загальне навантаження на сервіс постійно змінюється, то виникає необхідність масштабування кожного окремого мікросервісу, і відповідно балансування навантаження між ними. Балансування GRPC-сервісів, є дещо складнішим за балансування сервісів з HTTP-сервером. 

Існує два основних підходи до GRPC-балансування: 

  • на боці клієнта;
  • балансування через proxy-сервер.

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

  • складність реалізації клієнта;
  • клієнт відстежує навантаження та доступність сервера;
  • необхідність реалізації та підтримки алгоритму балансування.

Ці проблеми значно ускладнюються при зростанні кількості клієнтів.

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

Балансування через Haproxy / Натисніть, щоб роздивитися

Безпека в GRPC-мікросервісах

GRPC підтримує SSL/TLS encryption, що дозволяє шифрувати дані, якими обмінюється клієнт та сервер. Також GRPC надає простий Auth API, який дозволяє надати авторизаційні дані під час створення каналу або виклику функції.

Приклад авторизації через SSL/TLS сертифікати:

const cert = fs.readFileSync('path/to/cert');

const ssl = grpc.credentials.createSsl(cert);

const stub = new service.Verification('grpc.service.com', ssl);

Слабкі сторони GRPC

Браузерна підтримка

На жаль, на сьогодні не існує повноцінної браузерної підтримки GRPC, тому його не слід використовати для служб, які викликаються безпосередньо з браузерних додатків.

Недоступний для читання людиною

Запити HTTP Rest API відправляються в текстовому вигляді (JSON), що дозволяє розробникам їх легко читати та редагувати. gRPC використовує двійковий протокол Protobuf, що є значно ефективнішим, але не читається людиною, що ускладнює та сповільнює процес відладки та розробки.

Висновки

На сьогодні GRPC є перспективним рішенням для мікросервісів, де необхідна висока пропускна здатність. Його використання дозволило нам опимізувати bottleneck нашої системи, там значно скоротити витрати на трафік та збільшити продуктивність. 

Тим не менш, через складність в реалізації, а також відсутність повноціної браузерної підтримки ми не можемо розглядати GRPC як повноціного конкурента HTTP REST API. 

Діліться вашими думками, чи мігрували ви з HTTP API на GRPC, і якими були результати?

Якщо ви знайшли помилку, будь ласка, виділіть фрагмент тексту та натисніть Ctrl+Enter.

Останні статті

ChatGPT, моторошна долина та трохи Фройда

Днями я завзято нила про щось ChatGPT (експериментую між сеансами з живим терапевтом). І от…

17.04.2025

Я прийшла за покупками, а не крутити колесо

«Крутіть колесо, щоб отримати знижку до 50%!» «Натисніть тут, щоб відкрити таємничу пропозицію!» «Зареєструйтесь зараз,…

16.04.2025

Майже навайбкодив десктопний монітор CI пайплайнів

Дуже хочеться робити якісь десктопні апки. Сумую за часами коли всі програми були offline-first, і…

15.04.2025

Як працюють транзакційні комісії в мережах Bitcoin і Ethereum

Надсилаючи криптовалюту, багато новачків ставлять запитання: як працюють комісії та чому вони відрізняються в різних…

14.04.2025

Обережно, тепер вас можуть обдурити на співбесіді з роботодавцем

Нова афера набирає обертів — ось детальний розбір того, як фальшиві потенційні роботодавці намагаються вкрасти…

11.04.2025

Цілі застосунки в соцмережі? На останньому ETHKyiv Impulse довели, що це можливо

Соцмережа з можливістю вбудовувати повноцінні додатки прямо в пости — звучить як фантастика, але Farcaster…

10.04.2025