docs: initial project documentation

- architecture overview and stack
- project structure and development order
- API design (endpoints, models, runtimes)
- infrastructure overview (k8s cluster, S3, registry)
- decisions log with rationale
- progress tracker v1/v2
This commit is contained in:
“Naeel”
2026-03-06 09:51:01 +04:00
commit b29b6c3d10
7 changed files with 344 additions and 0 deletions
+95
View File
@@ -0,0 +1,95 @@
# API Design
## Базовый URL
```
https://sless.api.ngcloud.ru/v1
```
## Аутентификация
```
Authorization: Bearer <cloud-token>
```
## Ресурсы
### Functions
| Метод | Путь | Описание |
|-------|------|----------|
| GET | /functions | Список функций |
| POST | /functions | Создать функцию |
| GET | /functions/{id} | Получить функцию |
| PUT | /functions/{id} | Обновить функцию |
| DELETE | /functions/{id} | Удалить функцию |
### Versions (код функции)
| Метод | Путь | Описание |
|-------|------|----------|
| GET | /functions/{id}/versions | Список версий |
| POST | /functions/{id}/versions | Загрузить новый код (multipart zip) |
| GET | /functions/{id}/versions/{ver} | Получить версию |
| POST | /functions/{id}/versions/{ver}/activate | Активировать версию |
### Triggers
| Метод | Путь | Описание |
|-------|------|----------|
| GET | /functions/{id}/triggers | Список триггеров |
| POST | /functions/{id}/triggers | Создать триггер (HTTP/Cron) |
| DELETE | /functions/{id}/triggers/{tid} | Удалить триггер |
### Invocations (вызов и логи)
| Метод | Путь | Описание |
|-------|------|----------|
| POST | /functions/{id}/invoke | Синхронный вызов |
| GET | /functions/{id}/invocations | История вызовов |
| GET | /functions/{id}/invocations/{iid} | Детали вызова + логи |
## Поддерживаемые runtime (v1)
- `go1.21`
- `python3.11`
- `nodejs20`
## Модель Function
```json
{
"id": "fn-uuid",
"name": "my-function",
"description": "...",
"runtime": "python3.11",
"entrypoint": "handler.handle",
"memory_mb": 128,
"timeout_sec": 30,
"env_vars": {"KEY": "value"},
"active_version": "1",
"status": "active",
"created_at": "...",
"updated_at": "..."
}
```
## Модель Trigger
```json
{
"id": "tr-uuid",
"type": "http",
"url": "https://sless.api.ngcloud.ru/invoke/fn-uuid",
"created_at": "..."
}
```
```json
{
"id": "tr-uuid",
"type": "cron",
"schedule": "0 * * * *",
"created_at": "..."
}
```
+64
View File
@@ -0,0 +1,64 @@
# Архитектура системы
## Общее описание
Managed Serverless Functions Service для облачного провайдера nubes.ru.
Пользователь загружает код, сервис его собирает и запускает по HTTP-триггеру или расписанию.
## Стек
| Компонент | Технология | Где запущен |
|-----------|-----------|-------------|
| API сервер | Go | Kubernetes, namespace `sless` |
| PostgreSQL | PostgreSQL | Kubernetes, namespace `sless` |
| Redis | Redis | Kubernetes, namespace `sless` |
| RabbitMQ | RabbitMQ | Kubernetes, namespace `sless` (позже) |
| S3 | Ceph (облачный) | `ceph.tst.nubes.ru` |
| Container Registry | Внутренний registry кластера | namespace `registry` |
| Функции пользователей | k8s Jobs/Deployments | namespace `sless-fn-{id}` |
## Схема
```
Пользователь
REST API (Go) ←── Terraform provider
├── PostgreSQL — метаданные функций, версии, логи вызовов
├── S3 (Ceph) — хранение кода (zip архивы)
├── Redis — кеш, rate limiting
Builder — получает zip из S3, собирает Docker образ, пушит в registry
Runner (k8s) — деплоит функцию как Job/Deployment в k8s
RabbitMQ — async вызовы, cron triggers (v2)
```
## Аутентификация
Используется токен облака (Bearer token), который пользователь получает в UI облака.
Terraform provider передаёт его в заголовке `Authorization: Bearer <token>`.
Keycloak не используется.
## Мониторинг
Метрики функций → Victoria Metrics / Grafana (уже есть в облаке).
Grafana: https://grafana.ngcloud.ru/dashboards/...
## Kubernetes кластер
Сейчас используется существующий кластер (временно).
Планируется переезд на новый кластер — манифесты переносятся без изменений.
Ноды существующего кластера:
- `wheel-control-plane-fm9sr` — control-plane
- `wheel-workers-tv4qr-r45xs` — worker
- `wheel-workers-tv4qr-x8xw7` — worker
Ingress: nginx, external IP `5.172.178.182`
Storage: rawfile CSI (local-path, default)
+49
View File
@@ -0,0 +1,49 @@
# Структура проекта
## Репозиторий
`gitea-naeel.giteak8s.services.ngcloud.ru/naeel/sless`
## Директории
```
sless/
├── cmd/
│ └── api/
│ └── main.go # точка входа API сервера
├── internal/
│ ├── api/
│ │ ├── handler/ # HTTP хендлеры (functions, versions, triggers)
│ │ ├── middleware/ # auth, logging, rate limit
│ │ └── router.go # регистрация маршрутов
│ ├── model/ # доменные модели: Function, Version, Trigger, Invocation
│ ├── storage/
│ │ ├── postgres/ # CRUD функций, версий, логов вызовов
│ │ └── s3/ # загрузка/скачивание zip архивов кода
│ ├── builder/ # сборка Docker образа из кода пользователя
│ ├── runner/ # запуск функций в k8s (Jobs / Deployments)
│ └── config/ # конфиг из env переменных
├── migrations/ # SQL миграции (numbered: 001_, 002_, ...)
├── deployments/
│ └── k8s/ # манифесты: Deployment, Service, Ingress, RBAC
├── api/
│ └── openapi.yaml # OpenAPI 3.0 спецификация
├── doc/ # документация проекта (эта папка)
└── docker-compose.yml # локальная разработка: postgres, redis, minio
```
## Go module
```
module gitea-naeel.giteak8s.services.ngcloud.ru/naeel/sless
```
## Порядок разработки
1. `internal/config` + `internal/model` — базовые структуры данных
2. `migrations/` + `internal/storage/postgres` — схема БД и CRUD
3. `internal/api` — HTTP хендлеры, роутер, middleware
4. `internal/storage/s3` — загрузка кода функций
5. `internal/builder` — сборка Docker образов
6. `internal/runner` — запуск функций в k8s
7. `deployments/k8s` — манифесты для деплоя
+47
View File
@@ -0,0 +1,47 @@
# Решения и обоснования
## 2026-03-06 — Отдельная репа для сервиса
**Решение:** Serverless service в отдельной репе, не вместе с Terraform provider.
**Причина:** Разные зоны ответственности, разные релизы, потенциально разные команды.
---
## 2026-03-06 — Один бинарник для v1
**Решение:** Один Go бинарник вместо микросервисов.
**Причина:** Нагрузки изначально нет. Проще деплоить, проще отлаживать. Разделим при необходимости.
---
## 2026-03-06 — Аутентификация через облачный токен
**Решение:** Использовать Bearer token облака, без Keycloak.
**Причина:** Terraform provider уже работает с токенами облака. Keycloak — лишняя зависимость для v1.
---
## 2026-03-06 — S3 облачный, остальное в кубере
**Решение:** S3 (Ceph) использовать облачный (`ceph.tst.nubes.ru`), PostgreSQL/Redis — в кластере.
**Причина:** S3 имеет внешний доступ и уже готов. Для PostgreSQL/Redis сетевого связывания с облаком пока нет — настраивается через devops облака.
---
## 2026-03-06 — Текущий кластер для разработки
**Решение:** Использовать существующий k8s кластер (namespace `sless`), потом перенести на новый.
**Причина:** Новый кластер ещё не готов. Изоляция через namespace — безопасно для существующих сервисов.
---
## 2026-03-06 — RabbitMQ откладываем
**Решение:** В v1 только HTTP и Cron триггеры. RabbitMQ/event triggers — в v2.
**Причина:** Упрощение первой итерации.
+17
View File
@@ -0,0 +1,17 @@
# Ошибки и решения
> Сюда записываем проблемы с которыми столкнулись и как их решили.
## Шаблон записи
```
## YYYY-MM-DD — Короткое описание проблемы
**Проблема:** ...
**Причина:** ...
**Решение:** ...
```
---
+41
View File
@@ -0,0 +1,41 @@
# Инфраструктура
## Kubernetes кластер (существующий, временный)
- **Version:** v1.33.1
- **Ноды:** 1 control-plane + 2 workers
- **CNI:** Cilium
- **Ingress:** nginx, external IP `5.172.178.182`
- **Storage:** rawfile CSI (OpenEBS), StorageClass `local-path` (default)
- **cert-manager:** есть
- **Kyverno:** есть (политики — проверить при деплое)
## Namespace'ы для sless
| Namespace | Что там |
|-----------|---------|
| `sless` | API сервер, PostgreSQL, Redis |
| `sless-fn-{id}` | Функции пользователей (Jobs/Deployments) |
## S3
- **URL:** `http://ceph.tst.nubes.ru/`
- **Тип:** Ceph S3 compatible
- Доступ: внешний, через access/secret key
- Бакет для кода функций: `sless-functions`
## Container Registry
- Внутренний registry кластера в namespace `registry`
- Service: `registry.registry.svc.cluster.local:18080`
## Мониторинг
- Victoria Metrics — в кластере
- Grafana: `https://grafana.ngcloud.ru`
## Будущий кластер
Новый кластер готовится. После переезда:
- Манифесты переносятся без изменений
- Меняются только конфиги подключения к S3/PostgreSQL если нужно
+31
View File
@@ -0,0 +1,31 @@
# Прогресс разработки
## Статусы: ✅ готово | 🔄 в процессе | ⏳ не начато
---
## v1 — Базовый сервис
| # | Компонент | Статус | Заметки |
|---|-----------|--------|---------|
| 1 | Структура проекта, go mod init | ⏳ | |
| 2 | internal/config | ⏳ | |
| 3 | internal/model | ⏳ | |
| 4 | Миграции PostgreSQL | ⏳ | |
| 5 | internal/storage/postgres | ⏳ | |
| 6 | internal/api — роутер + хендлеры | ⏳ | |
| 7 | internal/storage/s3 | ⏳ | |
| 8 | internal/builder | ⏳ | |
| 9 | internal/runner (k8s) | ⏳ | |
| 10 | docker-compose.yml (local dev) | ⏳ | |
| 11 | deployments/k8s манифесты | ⏳ | |
## v2 — Расширения
| # | Компонент | Статус | Заметки |
|---|-----------|--------|---------|
| 1 | RabbitMQ event triggers | ⏳ | |
| 2 | Keycloak / облачный auth | ⏳ | |
| 3 | Метрики → Victoria Metrics | ⏳ | |
| 4 | Интеграция с облачными PostgreSQL/Redis | ⏳ | |
| 5 | Мониторинг UI | ⏳ | |