Initial commit: VoIdeaAI - voice-first AI idea assistant

This commit is contained in:
2026-05-13 12:51:42 +03:00
commit 688d043dad
421 changed files with 47915 additions and 0 deletions
+145
View File
@@ -0,0 +1,145 @@
# OAuth Schema - VoIdea
**Дата:** 2026-05-10
**Статус:** Backlog (для фиксации ADR)
---
## Обзор
Схема авторизации: один пользователь = один провайдер. Нельзя привязать Google если уже есть Яндекс.
---
## Правила
### Основное правило
> Один пользователь = один провайдер (email или OAuth)
Это означает:
- Если зарегистрировался через Яндекс → только Яндекс
- Если зарегистрировался через Google → только Google
- Если зарегистрировался через email → только email + пароль
### Нельзя
- Привязать Google к аккаунту зарегистрированному через Яндекс
- Добавить второй OAuth провайдер
- Изменить email после регистрации через OAuth
---
## Структура данных
### Users table
```sql
CREATE TABLE users (
id UUID PRIMARY KEY,
email VARCHAR(255) UNIQUE,
password_hash VARCHAR(255), -- NULL если OAuth-only
-- OAuth данные (один провайдер)
oauth_provider VARCHAR(20), -- yandex|google|apple|null
oauth_id VARCHAR(255), -- ID в системе провайдера
-- Метаданные
email_verified BOOLEAN DEFAULT FALSE,
created_at TIMESTAMP DEFAULT NOW(),
updated_at TIMESTAMP DEFAULT NOW(),
-- Constraints
CONSTRAINT users_oauth_xor_email CHECK (
(oauth_provider IS NOT NULL AND email IS NOT NULL) OR
(oauth_provider IS NULL AND email IS NOT NULL AND password_hash IS NOT NULL)
)
);
CREATE UNIQUE INDEX uq_users_oauth ON users(oauth_provider, oauth_id) WHERE oauth_provider IS NOT NULL;
```
### Почему один провайдер
1. **Безопасность** — меньше точек входа
2. **Простота** — не нужно merge аккаунтов
3. **Ясность** — пользователь знает что использует
4. **Privacy** — данные не смешиваются между провайдерами
---
## OAuth Flow
### Яндекс
```
1. Пользователь нажимает "Войти через Яндекс"
2. Редирект на Яндекс OAuth
3. Callback с code
4. Получение access_token
5. Получение данных пользователя
6. Поиск/создание user по oauth_provider + oauth_id
7. Создание JWT session
```
### Google
Аналогично Яндексу, с заменой endpoint-ов.
---
## Регистрация через email
```sql
-- При регистрации через email
INSERT INTO users (email, password_hash, oauth_provider, oauth_id)
VALUES ('user@example.com', 'hash123', NULL, NULL);
```
### Вход через email
```sql
-- Проверка пароля
SELECT * FROM users WHERE email = 'user@example.com' AND password_hash = verify('hash123');
```
---
## Защита от привязки чужого аккаунта
### Проблема
Злоумышленник может попытаться привязать Google к чужому email.
### Решение
1. **Email verification** — требуется подтверждение
2. **Password check** — для существующих пользователей
3. **Separate tables** — OAuth и email разделены логически
---
## Будущее (Apple OAuth)
### Apple будет реализован позже
Для Apple потребуется:
- App Store Developer Account
- Private Key для подписи
- Тот же принцип: один пользователь = один провайдер
---
## TODO
- [ ] Реализовать OAuth service
- [ ] Интегрировать Яндекс OAuth
- [ ] Интегрировать Google OAuth
- [ ] Зарезервировать место для Apple (не реализовывать)
- [ ] Тесты
- [ ] Документация
---
*Создано: 2026-05-10*
*См. также: docs/adr/003-oauth-schema.md*