Содержание ТЗ
Техническое заданиеВерсия 1.0 · 18.10.2026
11. Яндекс ID: вход и регистрация
OAuth-вход через Яндекс ID: поток, настройка приложения, безопасность и приёмка.
Версия: 0.1 Дата: 18.10.2026
1. Что реализовано
- OAuth 2.0 Authorization Code для Яндекс ID.
- Кнопки «Продолжить с Яндекс ID» на страницах
/login/и/signup/. - Создание нового пользователя при первом входе через Яндекс.
- Привязка
provider= yandex,provider_user_idк пользователю. - Сессия easy-connect в httpOnly cookie после успешного callback.
- Защита от login CSRF: одноразовый
stateв httpOnly cookie. - Возврат на исходную страницу через
next(только внутренние пути). - Ошибки OAuth возвращаются на
/login/?oauth_error=...с понятным текстом. - Если credentials не заданы, кнопка неактивна, а API возвращает 503.
2. Поток
Пользователь → /login/ → «Продолжить с Яндекс ID»
→ GET /api/v1/auth/oauth/yandex/start?next=/app/
→ cookie ec_oauth_state {state,next}
→ 302 на https://oauth.yandex.ru/authorize
→ Яндекс: согласие и выбор аккаунта
→ GET /api/v1/auth/oauth/yandex/callback?code=...&state=...
→ проверка state cookie
→ POST https://oauth.yandex.ru/token
→ GET https://login.yandex.ru/info?format=json
→ найти/создать пользователя
→ создать сессию + cookie
→ 302 на WEB_URL + next
3. Настройка Яндекс OAuth
- Откройте https://oauth.yandex.ru/client/new (нужен аккаунт Яндекса).
- Создайте приложение:
- название:
easy-connect; - платформа: «Веб-сервисы»;
- Redirect URI:
- для локальной разработки:
http://localhost:5101/api/v1/auth/oauth/yandex/callback; - для preview:
https://easy-connect.134.0.112.10.nip.io/api/v1/auth/oauth/yandex/callback; - для production:
https://easy-connect.ru/api/v1/auth/oauth/yandex/callback.
- для локальной разработки:
- название:
- В доступах приложения включите:
login:email— email пользователя;login:info— имя, логин, аватар.
- Скопируйте
ClientIDиClient secret. - Заполните env на сервере:
WEB_URL=https://easy-connect.134.0.112.10.nip.io
YANDEX_CLIENT_ID=...
YANDEX_CLIENT_SECRET=...
YANDEX_REDIRECT_URI=https://easy-connect.134.0.112.10.nip.io/api/v1/auth/oauth/yandex/callback
- Перезапустите API:
cd /opt/easy-connect/server
docker compose --env-file .env.production -f docker-compose.prod.yml up -d api
- Проверьте:
curl -s https://easy-connect.134.0.112.10.nip.io/api/v1/config
# "yandexEnabled": true
После этого кнопка Яндекс ID становится активной. Если credentials не
заполнены, yandexEnabled=false, кнопка неактивна, а /start возвращает 503.
4. Переменные окружения
| Переменная | Назначение |
|---|---|
WEB_URL | Куда вернуть пользователя после OAuth (сайт, не API) |
YANDEX_CLIENT_ID | ClientID приложения |
YANDEX_CLIENT_SECRET | Client secret |
YANDEX_REDIRECT_URI | Точный callback URL, зарегистрированный в Яндексе |
COOKIE_SECURE | true на HTTPS |
APP_ORIGIN | Origin сайта (fallback для WEB_URL) |
YANDEX_REDIRECT_URI должен точно совпадать с указанным в приложении
Яндекса, включая схему, домен и путь.
5. Безопасность
state— 24 случайных байта, хранится в httpOnly cookie 10 минут.- Сравнение state — constant-time.
- Cookie сессии и state:
HttpOnly,SameSite=Lax,Secureна HTTPS. - Токены Яндекса не сохраняются в БД: используется только профиль.
- Пароль OAuth-пользователя — случайная строка, вход по паролю невозможен.
- Если email уже занят паролем, автоматическая привязка не выполняется:
возвращается ошибка
yandex_email_exists, чтобы исключить захват аккаунта. Пользователь входит паролем. - Внешние URL в
nextзапрещены: разрешены только внутренние пути. - Логи не содержат кода, токена и профиля.
6. Ограничения MVP
- Нет привязки Яндекс ID к уже существующему аккаунту из настроек (следующий этап).
- Нет подтверждения email для парольных аккаунтов, поэтому авто-привязка по email сознательно отключена.
- Нет входа через VK ID (следующий этап).
- Нет refresh-токена Яндекса в БД — он не нужен для входа.
- Аватар Яндекса не сохраняется.
7. Приёмка
- Приложение Яндекса создано, callback добавлен.
- Env заполнены, API перезапущен.
-
/api/v1/configвозвращаетyandexEnabled: true. - Кнопка на
/login/и/signup/активна. - Новый пользователь входит через Яндекс и попадает в
/app/. - Существующий email → понятная ошибка, без автопривязки.
- Отказ в доступе →
/login/?oauth_error=yandex_denied. - Подмена state → ошибка
yandex_state. - Выход и повторный вход работают.
- Мобильная версия кнопки и страниц.