Files
docs/apps/backend-scenarios/login-jwt.md
T

5.0 KiB
Raw Blame History

title
title
Логин по email и выдача JWT (Backend)

Сценарий 1.1: Логин и JWT

Бизнес-цель

Пользователь сайта или приложения входит по email и паролю. Система проверяет учётные данные, обновляет отметку последнего входа и выдаёт JWT, чтобы дальнейшие запросы к API выполнялись от имени этого пользователя без хранения сессии на сервере (stateless API).

Точки входа

Тип Метод + URL Класс
HTTP POST /user/login App\Controller\UserController::login
HTTP GET /user/logout App\Controller\UserController::logout (ответ-заглушка; инвалидация токена на сервере не показана в коде)
HTTP GET /user/ App\Controller\UserController::index — текущий пользователь по JWT (#[IsGranted('ROLE_USER')])

Асинхронные сообщения и CLI для этого сценария не используются.

Пошаговый алгоритм (flow)

  1. Клиент отправляет JSON с полями username (фактически email) и password (см. OpenAPI в контроллере).
  2. UserController::login вручную парсит тело; при отсутствии полей отвечает 400 с текстом Missing credentials.
  3. Значения кладутся в App\Dto\UserLoginDto; срабатывает Symfony Validator по атрибутам DTO.
  4. Вызывается App\Service\User\AuthenticationService::jsonAuth($dto):
    • в App\Repository\UserRepository выполняется поиск User по email = md5(введённый email) (в БД в колонке users.email хранится хэш, а не открытый email);
    • пароль проверяется через UserPasswordHasherInterface::isPasswordValid.
  5. При неверной паре или отсутствии пользователя контроллер возвращает 400 с сообщением о неверных учётных данных.
  6. При успехе вызывается $user->updateLoggedIn(), EntityManager::flush() — в БД обновляется поле loggedIn.
  7. Lexik JWT: JWTTokenManagerInterface::create($user) формирует токен; в ответ уходит JSON: successful, token, user (массив из User::toArray()uid, bdate, roles, regionId, loggedIn).

Mermaid

sequenceDiagram
    participant C as Клиент
    participant UC as UserController
    participant V as Validator
    participant AS as AuthenticationService
    participant UR as UserRepository
    participant EM as EntityManager
    participant JWT as JWTTokenManagerInterface

    C->>UC: POST /user/login {username, password}
    UC->>V: validate(UserLoginDto)
    V-->>UC: ок / ошибки
    UC->>AS: jsonAuth(dto)
    AS->>UR: findOneBy email = md5(dto.email)
    UR-->>AS: User | null
    AS-->>UC: {user, isPasswordValid}
    alt неверный пароль или нет пользователя
        UC-->>C: 400
    else успех
        UC->>EM: flush (updateLoggedIn)
        UC->>JWT: create(User)
        UC-->>C: 200 {token, user}
    end

Внешние зависимости

Система Участие
PostgreSQL таблица users (App\Entity\User)
Lexik JWT генерация и последующая валидация токена
Bitrix / Инфоклиника / Redis / SMS не задействованы в этом сценарии

Обработка ошибок и edge cases

  • Нет полей credentials400, Missing credentials.
  • Ошибки валидации DTO400, successful: false, errors (строка нарушений).
  • Неверный email/пароль — единый ответ 400 с текстом «Не правильное имя пользователя или пароль».
  • Согласованность с JWT: App\Service\DecoderJWT\JWTDecoderService::getUser() восстанавливает пользователя по username из payload и полю email в БД — это тот же «логин», что хранится в User после регистрационных сценариев (часто md5(...)).

Ссылки на классы

  • apps/backend/src/Controller/UserController.php
  • apps/backend/src/Service/User/AuthenticationService.php
  • apps/backend/src/Dto/UserLoginDto.php
  • apps/backend/src/Entity/User.php
  • apps/backend/src/Repository/UserRepository.php
  • Конфигурация security/JWT: apps/backend/config/packages/security.yaml, lexik_jwt_authentication.yaml

См. также backend-ddd.md.