Skip to content

e345ee/distributed-compute-gateway

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

1 Commit
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

Распределенные вычисления

Python FastAPI Docker React TypeScript Vite Nginx Prometheus Grafana

Это небольшой стенд распределенной системы. Пользователь работает только с gateway: создает задачу через HTTP API, получает TCP-порт и подключается к нему. Сама задача запускается не на gateway, а в отдельном контейнере на одном из worker-узлов.

Проще говоря: gateway принимает запрос, выбирает свободный worker, worker поднимает контейнер с вычислителем, а gateway прокидывает TCP-трафик от пользователя до этого контейнера.

Архитектура

Схема архитектуры

В системе есть несколько частей:

  • gateway - единая точка входа. Хранит список workers и jobs, выбирает worker, выделяет порт и запускает TCP proxy.
  • worker - внутренний сервис, который запускает и удаляет контейнеры с задачами через Docker.
  • job-runner - контейнер с простой TCP-программой. Он отвечает на команды ping, stats, load, stop, help.
  • frontend - простой веб-интерфейс для просмотра состояния системы.
  • Prometheus и Grafana - мониторинг gateway, workers и активных jobs.

Пользователь не ходит напрямую в worker и job-runner. Снаружи видны только gateway API, frontend, мониторинг и диапазон TCP-портов для jobs.

Как это работает

  1. Пользователь отправляет POST /api/jobs на gateway.
  2. Gateway смотрит зарегистрированные workers.
  3. Выбирается worker с наименьшей загрузкой.
  4. Gateway резервирует свободный порт из диапазона 5000-5099.
  5. Worker запускает отдельный контейнер job-runner.
  6. Gateway запускает TCP proxy с выделенного порта на контейнер задачи.
  7. Пользователь подключается к этому порту через nc или другой TCP-клиент.

Пример пути для одной задачи:

client -> gateway:5000 -> TCP proxy -> job-runner:7001

На уровне TCP это два отдельных соединения: клиент соединяется с gateway, а gateway отдельно соединяется с job-runner.

TCP-соединения через gateway

Проверка сокетов показывает ту же картину:

Активные TCP-сокеты

Service discovery

Workers сами регистрируются на gateway после запуска:

POST /internal/workers/register

Потом они регулярно отправляют heartbeat:

POST /internal/workers/heartbeat

В heartbeat worker передает свой worker_id, capacity и текущее количество активных jobs. Если heartbeat долго не приходит, gateway считает worker недоступным и больше не отправляет на него новые задачи.

API

Основные пользовательские endpoints:

POST   /api/jobs
GET    /api/jobs
GET    /api/jobs/{job_id}
DELETE /api/jobs/{job_id}
GET    /api/workers
GET    /api/system/status
GET    /health
GET    /ready
GET    /metrics

После создания job gateway возвращает примерно такой ответ:

{
  "job_id": "job-8f34f05916",
  "status": "running",
  "worker_id": "worker-2",
  "port": 5001,
  "protocol": "tcp",
  "connect": "tcp://localhost:5001"
}

Команды внутри TCP-сессии:

ping
stats
load 1
help
stop

Структура проекта

.
├── docker-compose.yml
├── Makefile
├── gateway/
├── worker/
├── job-runner/
├── frontend/
├── monitoring/
├── load-tests/
├── media/
└── report/

Как запустить

Нужны Docker, Docker Compose и Python 3.

Собрать образы:

docker compose build

Запустить проект:

docker compose up -d

Проверить контейнеры:

docker compose ps

Локальные адреса:

Gateway API: http://localhost:18080
Frontend:    http://localhost:8081
Prometheus:  http://localhost:9090
Grafana:     http://localhost:3000
Job ports:   localhost:5000-5099

Проверить gateway:

curl http://localhost:18080/health
curl http://localhost:18080/ready
curl http://localhost:18080/api/workers

Создать задачу:

curl -X POST http://localhost:18080/api/jobs

Подключиться к задаче по TCP. Порт нужно взять из ответа gateway:

nc localhost 5000

Внутри соединения можно отправить:

ping
stats
load 1
help

Удалить задачу:

curl -X DELETE http://localhost:18080/api/jobs/JOB_ID

Тесты

Поставить зависимости для тестовых скриптов:

python3 -m venv .venv
source .venv/bin/activate
pip install -r load-tests/requirements.txt

Создать много jobs и посмотреть распределение по workers:

python3 load-tests/create_jobs.py --gateway http://localhost:18080 --count 30 --concurrency 5 --delete

Создать одну job и проверить TCP-команды:

python3 load-tests/tcp_test.py --gateway http://localhost:18080 --host localhost

То же самое можно запустить через Makefile:

make test-load
make tcp-test

Остановка

Остановить сервисы:

docker compose down --remove-orphans

Остановить сервисы и удалить сохраненное состояние gateway:

docker compose down -v --remove-orphans

Если после ручных проверок остались контейнеры jobs:

docker rm -f $(docker ps -aq --filter label=distributed-computing-platform.job=true)

About

A distributed computing prototype with a gateway, worker nodes, TCP proxying, Docker-based job containers, and monitoring.

Resources

Stars

2 stars

Watchers

0 watching

Forks

Releases

No releases published

Packages

 
 
 

Contributors