Студент vs Мікросервіси: Як я поєднав NestJS та Python, щоб не писати черговий інтернет-магазин

💡 Усі статті, обговорення, новини про DevOps — в одному місці. Приєднуйтесь до DevOps спільноти!

Всім привіт! Мене звати Богдан, мені 18 років, і я студент Львівської Політехніки.

Поки мої одногрупники здавали лабораторні, я вирішив піти складнішим шляхом. Замість того, щоб писати черговий To-Do List чи інтернет-магазин на React (яких і так мільйон), я захотів розібратися, як будуються справжні, масштабовані системи.

Я поставив собі челендж: створити платформу SkillSwapAI — сервіс для обміну навичками та пошуку менторів, де «під капотом» працює повноцінна мікросервісна архітектура.

Спойлер: це було боляче, я витратив усю стипендію на сервери, але воно того варте.

Чому я обрав такий стек?

Я міг би написати все на Node.js. Але Python — це стандарт для AI. Я хотів використати найкращі інструменти для кожної задачі:

  • Frontend: Next.js 14 (App Router) — для SEO та зручного рендерингу.
  • Core Backend: NestJS — для стабільності, типізації та чіткої структури (модулі, гарди, DI).
  • AI Engine: Python (FastAPI) — окремий мікросервіс для генерації персональних планів навчання та рекомендацій скілів (інтеграція з OpenAI).
  • Infrastructure: Docker, Docker Compose, AWS S3 (для файлів), PostgreSQL (Neon.tech).

Архітектура: Як це працює

Основна ідея в розподілі відповідальності:

  1. Клієнт (Next.js) відправляє запити на API Gateway (NestJS).
  2. NestJS обробляє бізнес-логіку (автентифікація, робота з базою).
  3. Якщо користувачу потрібен план навчання або рекомендація, NestJS робить внутрішній запит до Python-сервісу.
  4. Python обробляє дані, звертається до OpenAI і повертає результат.
  5. Всі файли (аватарки) завантажуються прямо в AWS S3, щоб не забивати контейнери.

Головний біль: Real-time та WebSockets

Найбільшим викликом став реал-тайм чат. Здавалося б, просто підключи Socket.io і все. Але синхронізувати стан між клієнтом і сервером виявилося складніше.

Я зіткнувся з класичним Race Condition: повідомлення відправлялося швидше, ніж встановлювалося стабільне з’єднання сокета при першому завантаженні. Іноді доводилося оновлювати сторінку, щоб побачити історію. Довелося глибоко закопатися в життєвий цикл Socket.io та React useEffect, щоб зрозуміти, як правильно ініціалізувати з’єднання і обробляти події.

Що в результаті?

Зараз проект задеплоєний і працює (хоч і в стадії MVP).

Це був шалений досвід, який навчив мене думати не функціями («як написати цикл»), а системами («як один сервіс поговорить з іншим, якщо один з них впаде»).

Я продовжую вдосконалювати код (планую додати черги повідомлень через Redis) і паралельно шукаю свою першу команду (Junior Full-Stack), де зможу рости далі як інженер.

Якщо вам цікаво глянути код, покритикувати архітектуру або дати пораду — буду дуже вдячний!

👉 GitHub: github.com/3cgbdg/SkillSwapAI

👉 Відео-демо роботи (5 хв): www.loom.com/...​6dc9c42b580b802bd0dc3c7ed

Дякую, що дочитали! Буду радий фідбеку в коментарях.

👍ПодобаєтьсяСподобалось5
До обраногоВ обраному2
LinkedIn
Дозволені теги: blockquote, a, pre, code, ul, ol, li, b, i, del.
Ctrl + Enter
Дозволені теги: blockquote, a, pre, code, ul, ol, li, b, i, del.
Ctrl + Enter

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

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

А для чого вам пітон в цій схемі? Хіба з джаваскріпта підключитися до OpenAI не можна?

Слушне запитання. Технічно — так, NestJS міг би сам стукати до OpenAI. Але я виніс це в окремий Python-сервіс стратегічно, щоб мати нативну підтримку ML-бібліотек (Pandas, NumPy) для майбутніх фіч аналітики та RAG.

Нікого не слухайте, це цікавий проект, і далеко не кожному студенту таке під силу. Ви рухаєтесь куди треба👍

Дякую за підтримку, Алексе! Це дуже мотивує не зупинятися.

Так в чому собсна проблема? Глянувши одним оком, ви про сто робите запити на умовний локалхост з районом. В чому дружба?

Ілле, для досвідченого інженера це справді виглядає як базові HTTP-запити. Але для мене, як для студента, челендж полягав у правильній оркестрації контейнерів, налаштуванні мережі в Docker (щоб сервіси бачили один одного не як localhost) та обробці кейсів, коли один із сервісів недоступний. Це був мій спосіб вийти за рамки моноліту і зрозуміти розподілені системи на практиці.

Дякую за пораду, Андрію! Kubernetes це наступний крок у моєму roadmap. Поки що освоїв Docker Compose, але розумію, що для справжнього продакшену потрібна серйозна оркестрація. Обов’язково спробую!

Підписатись на коментарі