|
|
# Polotsk Transit API
|
|
|
|
|
|
Система управления информацией об общественном транспорте города Полоцка с REST API, веб-панелью администратора и поддержкой offline-синхронизации.
|
|
|
|
|
|
## 🚀 Возможности
|
|
|
|
|
|
### MVP (Версия 1.0 - статические данные)
|
|
|
- ✅ REST API для маршрутов и остановок
|
|
|
- ✅ Геопространственные запросы (PostGIS)
|
|
|
- ✅ Расчет ETA на основе расписания
|
|
|
- ✅ Offline-синхронизация для мобильных приложений
|
|
|
- ✅ Веб-панель администратора
|
|
|
- ✅ Кеширование через Redis
|
|
|
- ✅ Аутентификация по API ключам
|
|
|
- ✅ Rate limiting
|
|
|
|
|
|
### Технологический стек
|
|
|
|
|
|
**Backend:**
|
|
|
- Node.js + Express
|
|
|
- PostgreSQL + PostGIS
|
|
|
- Redis
|
|
|
- Docker
|
|
|
|
|
|
**Frontend (Admin Panel):**
|
|
|
- React + Vite
|
|
|
- Tailwind CSS
|
|
|
- React Leaflet (карты)
|
|
|
- Axios
|
|
|
|
|
|
## 📋 Требования
|
|
|
|
|
|
- Docker и Docker Compose
|
|
|
- Node.js 18+ (для разработки без Docker)
|
|
|
- Статический IP или динамический DNS
|
|
|
- ~2GB свободного места на диске
|
|
|
|
|
|
## 🛠 Установка и запуск
|
|
|
|
|
|
### 1. Клонирование и настройка
|
|
|
|
|
|
```bash
|
|
|
# Создайте .env файл из примера
|
|
|
cp .env.example .env
|
|
|
|
|
|
# Настройте переменные окружения
|
|
|
nano .env
|
|
|
```
|
|
|
|
|
|
Важные переменные в `.env`:
|
|
|
```env
|
|
|
# Обязательно измените в продакшене!
|
|
|
DB_PASSWORD=your_secure_password_here
|
|
|
API_KEY_SALT=generate_random_salt_with_openssl
|
|
|
ADMIN_PASSWORD=your_secure_admin_password_here
|
|
|
|
|
|
# Для разработки/деплоя через встроенный proxy оставьте как есть
|
|
|
CORS_ORIGIN=http://localhost:3001
|
|
|
API_URL=/api/v1
|
|
|
```
|
|
|
|
|
|
Генерация безопасного salt:
|
|
|
```bash
|
|
|
openssl rand -base64 32
|
|
|
```
|
|
|
|
|
|
### 2. Запуск с Docker (рекомендуется)
|
|
|
|
|
|
```bash
|
|
|
# Сборка и запуск всех сервисов
|
|
|
docker-compose up -d
|
|
|
|
|
|
# Проверка статуса
|
|
|
docker-compose ps
|
|
|
|
|
|
# Просмотр логов
|
|
|
docker-compose logs -f
|
|
|
```
|
|
|
|
|
|
Сервисы будут доступны:
|
|
|
- **API**: http://localhost:3000
|
|
|
- **Admin Panel**: http://localhost:3001
|
|
|
- **PostgreSQL**: localhost:5432
|
|
|
- **Redis**: localhost:6379
|
|
|
|
|
|
Мастер-аккаунт создается автоматически при старте backend:
|
|
|
- login: `admin`
|
|
|
- password: значение `ADMIN_PASSWORD` из `.env` (если не задано, fallback `admin123`)
|
|
|
|
|
|
### 3. Проверка работоспособности
|
|
|
|
|
|
```bash
|
|
|
# Проверка API
|
|
|
curl http://localhost:3000/health
|
|
|
|
|
|
# Проверка базы данных
|
|
|
docker exec -it polotsk-transit-db psql -U transit_admin -d polotsk_transit -c "SELECT COUNT(*) FROM routes;"
|
|
|
```
|
|
|
|
|
|
### 4. Разработка без Docker
|
|
|
|
|
|
**Backend:**
|
|
|
```bash
|
|
|
cd backend
|
|
|
npm install
|
|
|
cp .env.example .env
|
|
|
|
|
|
# Убедитесь, что PostgreSQL и Redis запущены локально
|
|
|
# Настройте DATABASE_URL и REDIS_URL в .env
|
|
|
|
|
|
npm run dev
|
|
|
```
|
|
|
|
|
|
**Frontend:**
|
|
|
```bash
|
|
|
cd frontend
|
|
|
npm install
|
|
|
cp .env.example .env
|
|
|
|
|
|
npm run dev
|
|
|
```
|
|
|
|
|
|
## 📱 Использование API
|
|
|
|
|
|
### Аутентификация
|
|
|
|
|
|
Все запросы требуют API ключ в заголовке:
|
|
|
```bash
|
|
|
curl -H "X-API-Key: dev_key_12345678" http://localhost:3000/api/v1/routes
|
|
|
```
|
|
|
|
|
|
### Основные эндпоинты
|
|
|
|
|
|
**Маршруты:**
|
|
|
```bash
|
|
|
GET /api/v1/routes # Все маршруты
|
|
|
GET /api/v1/routes/:id # Маршрут с остановками
|
|
|
POST /api/v1/routes # Создать маршрут
|
|
|
PUT /api/v1/routes/:id # Обновить маршрут
|
|
|
DELETE /api/v1/routes/:id # Удалить маршрут
|
|
|
```
|
|
|
|
|
|
**Остановки:**
|
|
|
```bash
|
|
|
GET /api/v1/stops # Все остановки
|
|
|
GET /api/v1/stops/:id # Конкретная остановка
|
|
|
GET /api/v1/stops/nearby?lat=55.4869&lon=28.7856&radius=500 # Ближайшие
|
|
|
POST /api/v1/stops # Создать остановку
|
|
|
PUT /api/v1/stops/:id # Обновить остановку
|
|
|
DELETE /api/v1/stops/:id # Удалить остановку
|
|
|
```
|
|
|
|
|
|
**ETA (расчет времени прибытия):**
|
|
|
```bash
|
|
|
POST /api/v1/eta/calculate
|
|
|
{
|
|
|
"stopId": 1,
|
|
|
"routeId": 1
|
|
|
}
|
|
|
|
|
|
GET /api/v1/eta/stop/:stopId # ETA для всех маршрутов на остановке
|
|
|
```
|
|
|
|
|
|
**Синхронизация (для offline-режима):**
|
|
|
```bash
|
|
|
GET /api/v1/sync # Полная синхронизация
|
|
|
GET /api/v1/sync?lastSync=2025-11-19T10:00:00Z # Инкрементальная
|
|
|
GET /api/v1/sync/status # Статус системы
|
|
|
```
|
|
|
|
|
|
### Примеры запросов
|
|
|
|
|
|
**Создание маршрута:**
|
|
|
```bash
|
|
|
curl -X POST http://localhost:3000/api/v1/routes \
|
|
|
-H "X-API-Key: dev_key_12345678" \
|
|
|
-H "Content-Type: application/json" \
|
|
|
-d '{
|
|
|
"route_number": "1",
|
|
|
"name": "Центр - Вокзал",
|
|
|
"type": "bus",
|
|
|
"color": "#0066CC",
|
|
|
"description": "Основной маршрут через центр города"
|
|
|
}'
|
|
|
```
|
|
|
|
|
|
**Создание остановки:**
|
|
|
```bash
|
|
|
curl -X POST http://localhost:3000/api/v1/stops \
|
|
|
-H "X-API-Key: dev_key_12345678" \
|
|
|
-H "Content-Type: application/json" \
|
|
|
-d '{
|
|
|
"name": "Площадь Свободы",
|
|
|
"latitude": 55.4869,
|
|
|
"longitude": 28.7856,
|
|
|
"address": "ул. Ленина, 1"
|
|
|
}'
|
|
|
```
|
|
|
|
|
|
**Поиск ближайших остановок:**
|
|
|
```bash
|
|
|
curl -H "X-API-Key: dev_key_12345678" \
|
|
|
"http://localhost:3000/api/v1/stops/nearby?lat=55.4869&lon=28.7856&radius=500"
|
|
|
```
|
|
|
|
|
|
## 🔐 Безопасность домашнего сервера
|
|
|
|
|
|
### Обязательные меры безопасности
|
|
|
|
|
|
1. **Cloudflare Tunnel** (рекомендуется):
|
|
|
```bash
|
|
|
# Установка cloudflared
|
|
|
curl -L https://github.com/cloudflare/cloudflared/releases/latest/download/cloudflared-linux-amd64 -o cloudflared
|
|
|
sudo mv cloudflared /usr/local/bin/
|
|
|
sudo chmod +x /usr/local/bin/cloudflared
|
|
|
|
|
|
# Аутентификация
|
|
|
cloudflared tunnel login
|
|
|
|
|
|
# Создание туннеля
|
|
|
cloudflared tunnel create polotsk-transit
|
|
|
|
|
|
# Запуск
|
|
|
cloudflared tunnel run polotsk-transit
|
|
|
```
|
|
|
|
|
|
2. **Настройка SSL в Nginx:**
|
|
|
```bash
|
|
|
# Получение сертификата Let's Encrypt
|
|
|
sudo certbot --nginx -d api.yourdomain.com -d admin.yourdomain.com
|
|
|
|
|
|
# Сертификаты автоматически обновятся
|
|
|
```
|
|
|
|
|
|
3. **Fail2ban:**
|
|
|
```bash
|
|
|
sudo apt install fail2ban
|
|
|
sudo systemctl enable fail2ban
|
|
|
sudo systemctl start fail2ban
|
|
|
```
|
|
|
|
|
|
4. **Мониторинг:**
|
|
|
```bash
|
|
|
# Установка Prometheus + Grafana (опционально)
|
|
|
# Или простой мониторинг через Docker stats
|
|
|
docker stats
|
|
|
```
|
|
|
|
|
|
### Создание API ключей
|
|
|
|
|
|
API ключи можно создать через базу данных:
|
|
|
|
|
|
```sql
|
|
|
INSERT INTO api_keys (key, app_name, rate_limit)
|
|
|
VALUES ('your_secure_key_here', 'iOS App', 10000);
|
|
|
```
|
|
|
|
|
|
Или через скрипт:
|
|
|
```javascript
|
|
|
const crypto = require('crypto');
|
|
|
const apiKey = crypto.randomBytes(32).toString('hex');
|
|
|
console.log(apiKey);
|
|
|
```
|
|
|
|
|
|
## 📊 Админ-панель
|
|
|
|
|
|
Откройте http://localhost:3001 в браузере.
|
|
|
|
|
|
**Функции:**
|
|
|
- Управление маршрутами
|
|
|
- Создание и редактирование остановок на карте
|
|
|
- Просмотр статистики
|
|
|
- Управление расписаниями (в разработке)
|
|
|
|
|
|
## 🗄 Структура базы данных
|
|
|
|
|
|
```sql
|
|
|
routes # Маршруты
|
|
|
stops # Остановки (с PostGIS геометрией)
|
|
|
route_stops # Связь маршрутов и остановок
|
|
|
schedules # Расписания
|
|
|
vehicles # Транспортные средства
|
|
|
historical_delays # Статистика задержек
|
|
|
alerts # Уведомления
|
|
|
api_keys # API ключи
|
|
|
sync_log # Лог изменений для синхронизации
|
|
|
```
|
|
|
|
|
|
## 🔄 Обновления
|
|
|
|
|
|
```bash
|
|
|
# Остановка сервисов
|
|
|
docker-compose down
|
|
|
|
|
|
# Обновление кода
|
|
|
git pull
|
|
|
|
|
|
# Перезапуск
|
|
|
docker-compose up -d --build
|
|
|
```
|
|
|
|
|
|
## 🐛 Troubleshooting
|
|
|
|
|
|
**База данных не стартует:**
|
|
|
```bash
|
|
|
docker-compose logs postgres
|
|
|
docker-compose down -v # Удалит volumes, ОСТОРОЖНО!
|
|
|
docker-compose up -d
|
|
|
```
|
|
|
|
|
|
**API не отвечает:**
|
|
|
```bash
|
|
|
docker-compose logs backend
|
|
|
docker-compose restart backend
|
|
|
```
|
|
|
|
|
|
**Frontend не собирается:**
|
|
|
```bash
|
|
|
cd frontend
|
|
|
npm install
|
|
|
npm run build
|
|
|
```
|
|
|
|
|
|
**PostGIS ошибки:**
|
|
|
```bash
|
|
|
docker exec -it polotsk-transit-db psql -U transit_admin -d polotsk_transit
|
|
|
SELECT PostGIS_Version();
|
|
|
```
|
|
|
|
|
|
## 📝 Следующие шаги (Roadmap)
|
|
|
|
|
|
### Версия 2.0 - Краудсорсинг GPS
|
|
|
- [ ] Endpoint для получения GPS от пользователей
|
|
|
- [ ] Агрегация и фильтрация GPS данных
|
|
|
- [ ] WebSocket для реалтайм-обновлений
|
|
|
- [ ] Функция "Я еду в маршруте" в приложениях
|
|
|
|
|
|
### Версия 3.0 - Продвинутые функции
|
|
|
- [ ] IoT GPS-трекеры интеграция
|
|
|
- [ ] Машинное обучение для предсказания задержек
|
|
|
- [ ] Push-уведомления
|
|
|
- [ ] Аналитика и отчеты
|
|
|
|
|
|
## 🤝 Контакты и поддержка
|
|
|
|
|
|
Создано для города Полоцка 🇧🇾
|
|
|
|
|
|
## 📄 Лицензия
|
|
|
|
|
|
MIT License - используйте свободно!
|