From abe0ccb3900db2ea2d75d0338e38cf5954f1c929 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=A5=D0=B0=D0=BB=D0=B8=D0=BC=D0=BE=D0=B2=20=D0=A0=D1=83?= =?UTF-8?q?=D1=81=D1=82=D0=B0=D0=BC?= Date: Fri, 13 Feb 2026 23:00:43 +0300 Subject: [PATCH] Readme --- README.md | 351 +++++++++++++++++++++++++++++++++++++++++++++++++++++- 1 file changed, 350 insertions(+), 1 deletion(-) diff --git a/README.md b/README.md index 594f42e..81f0d0f 100644 --- a/README.md +++ b/README.md @@ -1 +1,350 @@ -# nashel-backend +# Nashel Backend + +Бэкенд для маркетплейса услуг "Nashel" — платформа для поиска мастеров и исполнителей. + +## 🏗️ Архитектура + +Проект построен на архитектуре **Clean Architecture** с модульным подходом: + +``` +nashel-backend/ +├── src/ +│ ├── BuildingBlocks/ # Общие блоки для всех модулей +│ │ ├── Application/ # Общие абстракции и поведения +│ │ ├── Domain/ # Базовые доменные сущности +│ │ └── Infrastructure/ # Общая инфраструктура +│ ├── Modules/ # Модули бизнес-логики +│ │ ├── Identity/ # Модуль авторизации и профилей +│ │ └── Order/ # Модуль заказов +│ └── Host/ # Точка входа приложения +└── tests/ # Тесты +``` + +### Модульность + +Каждый модуль (Identity, Order) является автономным и содержит: +- **Domain** — бизнес-логика, сущности, репозитории +- **Application** — Use Cases, команды, запросы, валидация +- **Infrastructure** — реализация репозиториев, EF Core +- **Presentation** — API endpoints + +## 🚀 Технологический стек + +- **.NET 10** — фреймворк +- **ASP.NET Core** — веб-фреймворк +- **Entity Framework Core** — ORM +- **PostgreSQL** — база данных +- **MediatR** — паттерн CQRS/Mediator +- **FluentValidation** — валидация +- **JWT** — аутентификация +- **Docker** — контейнеризация +- **Swagger/OpenAPI** — документация API + +## 📦 Установка и запуск + +### Требования + +- .NET 10 SDK +- Docker и Docker Compose +- PostgreSQL + +### Запуск через Docker Compose + +```bash +# Клонирование репозитория +git clone +cd nashel-backend + +# Запуск всех сервисов +docker-compose up -d + +# Просмотр логов +docker-compose logs -f app + +# Остановка сервисов +docker-compose down +``` + +### Локальный запуск + +```bash +# Восстановление зависимостей +dotnet restore + +# Настройка переменных окружения +cp src/Host/appsettings.json src/Host/appsettings.Development.json +# Отредактируйте ConnectionStrings__DefaultConnection + +# Применение миграций +dotnet ef database update --project src/Host --startup-project src/Host + +# Запуск +dotnet run --project src/Host +``` + +## 🔧 Переменные окружения + +| Переменная | Описание | Пример | +|------------|----------|--------| +| `ASPNETCORE_ENVIRONMENT` | Окружение | `Development`, `Production` | +| `ConnectionStrings__DefaultConnection` | Строка подключения к БД | `Host=db;Port=5432;Database=nashel;Username=postgres;Password=postgres` | +| `JWT__Secret` | Секретный ключ JWT | `your-super-secret-key` | +| `JWT__Issuer` | Издатель токена | `nashel-api` | +| `JWT__Audience` | Аудитория токена | `nashel-client` | +| `JWT__ExpirationMinutes` | Время жизни токена (мин) | `60` | + +## 📚 API Документация + +Swagger доступен по адресу: `http://localhost:5000/swagger` + +### Основные эндпоинты + +#### Аутентификация + +```http +POST /api/auth/register +Content-Type: application/json + +{ + "phone": "+79001234567", + "firstName": "Иван", + "lastName": "Иванов", + "password": "password123", + "confirmPassword": "password123", + "isCompany": false, + "companyName": "ООО 'Ромашка'", + "inn": "1234567890" +} +``` + +```http +POST /api/auth/login +Content-Type: application/json + +{ + "phone": "+79001234567", + "password": "password123" +} +``` + +#### Профиль пользователя + +```http +GET /api/profile +Authorization: Bearer {access_token} + +PUT /api/profile +Authorization: Bearer {access_token} +Content-Type: application/json + +{ + "firstName": "Иван", + "lastName": "Иванов", + "patronymic": "Иванович", + "companyName": "ООО 'Ромашка'", + "inn": "1234567890" +} + +POST /api/profile/change-phone +Authorization: Bearer {access_token} +Content-Type: application/json + +{ + "newPhone": "+79009876543" +} + +POST /api/profile/become-performer +Authorization: Bearer {access_token} + +POST /api/profile/avatar +Authorization: Bearer {access_token} +Content-Type: multipart/form-data + +avatar: + +PUT /api/profile/competencies +Authorization: Bearer {access_token} +Content-Type: application/json + +{ + "Competencies": ["сантехника", "электрика"] +} +``` + +#### Компетенции + +```http +GET /api/competencies/search?q=сантех +Authorization: Bearer {access_token} +``` + +## 🎯 Реализованный функционал + +### Модуль Identity + +#### Аутентификация и авторизация +- ✅ Регистрация пользователей (частные лица и компании) +- ✅ Вход в систему (JWT токены) +- ✅ Обновление токенов +- ✅ Выход из системы +- ✅ Ролевая модель (Client, Master, Candidate, Company, Admin) + +#### Профиль пользователя +- ✅ Получение профиля +- ✅ Редактирование профиля +- ✅ Изменение номера телефона +- ✅ Загрузка аватара с кропом +- ✅ Управление компетенциями +- ✅ Стать исполнителем + +#### Компетенции +- ✅ Поиск компетенций по подстроке +- ✅ Общий пул компетенций для всех исполнителей +- ✅ Автоматическое создание новых компетенций + +#### Компании +- ✅ Регистрация компаний с ИНН +- ✅ Управление данными компании +- ✅ Отдельная логика для компаний + +### Модуль Order (в разработке) +- ⏳ Создание заказов +- ⏳ Поиск заказов на карте +- ⏳ SLA таймер для отклика на заказы + +## 🗄️ База данных + +### Схема + +``` +accounts (аккаунты пользователей) +├── id (PK) +├── phone (уникальный) +├── password_hash +├── roles (массив ролей) +└── profile_id (FK) + +user_profiles (профили пользователей) +├── id (PK) +├── account_id (FK) +├── first_name +├── last_name +├── patronymic +├── company_name +├── inn (для компаний) +├── avatar_url +└── competency_profiles (связь с компетенциями) + +competencies (компетенции/навыки) +├── id (PK) +├── name (уникальное, в нижнем регистре) + +competency_profiles (связь профилей и компетенций) +├── id (PK) +├── profile_id (FK) +├── competency_id (FK) +``` + +### Миграции + +```bash +# Создание новой миграции +dotnet ef migrations add AddNewFeature --project src/Infrastructure --startup-project src/Host + +# Применение миграций +dotnet ef database update --project src/Infrastructure --startup-project src/Host + +# Откат последней миграции +dotnet ef database update --project src/Infrastructure --startup-project src/Host +``` + +## 🔐 Безопасность + +- Хеширование паролей (BCrypt) +- JWT токены с refresh token +- Валидация входных данных (FluentValidation) +- CORS политика +- Rate limiting (в планах) + +## 🧪 Тестирование + +```bash +# Запуск всех тестов +dotnet test + +# Запуск тестов с покрытием +dotnet test --collect:"XPlat Code Coverage" + +# Запуск конкретного теста +dotnet test --filter "FullyQualifiedName~TestName" +``` + +## 📝 Конвенции кода + +### CQRS Pattern + +Используем MediatR для реализации CQRS: + +```csharp +// Команда (Command) +public record UpdateProfileCommand(...) : IRequest; + +// Обработчик команды (Handler) +public class UpdateProfileCommandHandler : IRequestHandler +{ + public async Task Handle(UpdateProfileCommand request, CancellationToken cancellationToken) + { + // Логика + } +} +``` + +### Валидация + +Используем FluentValidation: + +```csharp +public class UpdateProfileCommandValidator : AbstractValidator +{ + public UpdateProfileCommandValidator() + { + RuleFor(x => x.FirstName).NotEmpty().MinimumLength(2); + RuleFor(x => x.LastName).NotEmpty().MinimumLength(2); + } +} +``` + +## 🚨 Обработка ошибок + +- Глобальный exception handler +- Стандартные HTTP статусы (400, 401, 403, 404, 500) +- Подробные сообщения об ошибках в Development режиме +- Обобщенные сообщения в Production режиме + +## 📦 Статические файлы + +Загруженные аватары хранятся в `wwwroot/uploads/` и доступны по URL: +``` +http://localhost:5000/uploads/{filename} +``` + +## 🔄 CI/CD + +- GitHub Actions для автоматического тестирования +- Docker Hub для хранения образов +- Автоматический деплой (в планах) + +## 📞 Контакты + +- **Проект:** Nashel +- **Версия:** 1.0.0 +- **Лицензия:** MIT + +## 🤝 Вклад в проект + +1. Fork репозитория +2. Создайте ветку для фичи (`git checkout -b feature/AmazingFeature`) +3. Закоммитьте изменения (`git commit -m 'Add some AmazingFeature'`) +4. Запушьте в ветку (`git push origin feature/AmazingFeature`) +5. Откройте Pull Request +