Files
UpAndDown/README.md
T
2026-01-23 08:11:16 +03:00

504 lines
28 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# TODO:
- ~~Сделать реальные исполнители(executors) для регистрации, авторизации, логаута~~
- ~~Покрыть тестами класс User и AuthRegistrationExecutor~~
- ~~Добавить clang-format(через CLion)~~
- ~~Перевести GetByUUID GetByLogin на const ref/string_view в IUserDAO - также не vector, а span(погуглить)~~ - span не применим
- ~~Привести к единому виду функции IUserDAO~~
- ~~Пройтись по коду и максимально наставить const~~
- ~~Указать возможные исключения в интерфейсах DAO - почему может выбросить исключение~~
- ~~Вынести User в структуру. Hashed Password структура должна изначально состоять в другой структуре~~
- ~~SharedPtr - передавать по константной ссылке.~~
- ~~Вынести обработку исключений в RootExecutor~~
- ~~Уменьшить дублирование кода в исключениях~~
- ~~Покрыть логами~~
- ~~Сделать один класс исключений, имеющих метод HTTP code - код и сообщение записывать уже в ловушке~~
- ~~Сделать интеграционный тест по ручкам~~
- ~~Заменить internal_server_error на bad_request и перепроверить коды ошибок~~
- ~~Создание и удаление вспомогательных классов должно быть вынесено в фикстуру~~
- ~~К следующему занятию сделать ручку из кейса 3 + восстановить фикстуры из тестов~~
- Посмотреть по поводу блокировок или тред пулла при использовании базы
- Посмотреть пулл соединений(Object pool) при использовании базы данных(посмотреть api MySQL-Connector)
- Посмотреть и подумать, что лучше - корутины или многопоточность?
- UseCase'ы по работе с личным кабинетом
- Научиться поднимать базы данных под каждый тест - научиться Docker - docker-compose - а если тест что-то должен заполнить, то он заполняет в самом начале()
- Возможно, сделать тесты на CI/CD - приоритет - низкий
- Найти слабые места в C++ -- std::forward, universal reference, просмотреть про decltype(почитать статьи)
- Написать фронтенд для MVP
- Разобрать decltype и auto по статье
До 27.01.2026
- Подобрать сервер по параметрам. Использовать linux.
- Перевести string на string_view
- ~~Попробовать nodiscard к executoru~~
- Добить 2 ручки
- Сделать тесты для ручек
# План
1)Добить бэкенд(2 ручки) (до февраля)
2)Сделать деплой(до марта)
3)Сделать фронтенд для MVP
4)Делаем веб-чат и роль доктора
5)Читать книгу Мейерса "Эффективный и современный C++" до ???
# UseCase'ы приложения:
# Up And Down - система для учета и отслеживания состояния для людей, больных БАР
## UseCase №1
### 1.Название: Зарегистрировать пользователя
### 2.Актор: Пользователь-пациент
### 3.Цель: Внести данные о новом пользователе в систему
### 4.Предусловия:
* Пользователь не авторизован в системе
* Пользователь с данным login'ом отсутствует в системе
### 5.Основной поток:
#### А1.Пользователь при входе в систему выбрасывается из системы
* Пользователь заходит в приложение на любую страницу
* Из-за отсутсвия авторизации приложение перенаправляет его на страницу авторизации и регистрации
* Пользователь кликает по ссылке, ведущей на странице регистрации
* На странице регистрации пользователь вводит логин и пароль
* Пользователь нажимает кнопку "Зарегистрироваться"
* Система выводит сообщение, что пользователь зарегистрирован в приложении
### 6.Потоки исключений:
#### B1.Пользователь с таким логином уже есть в системе
* Процедура регистрации проваливается
* Выводится нотификация с сообщением об ошибке по причине наличия такого же логина в системе
#### B2.Пользователь оставил пустым логин или пустой/неправильный пароль
* При попытке регистрации подсвечиваются незаполненные поля, или поле пароля, если пароль неправильный
* Выводится сообщение об ошибке
### 7.Постусловия
* Пользователь с указанным логином сохранен в БД
### 8.API-Маршруты
* `POST /api/v1/Auth/Register` - Регистрация пользователя
### 9.Контракт
#### Register-Request
```
{
"login": "ivan_89",
"password": "S3cureP@ssw0rd"
}
```
##### Требования к валидации:
* login: 3-50 символов, ^[A-Za-z0-9_]+$, уникальное значение
* password: ≥ 5 символов
##### Response - 201 - Created
```
{
"user": {
"uuid": "51351bb1-7563-479d-a8e9-201d0ff934c2"
"login": "ivan_89"
}
}
```
##### Errors
* `409 USER_EXISTS` — пользователь с таким логином уже есть(`B1`)
* `422 VALIDATION_FAILED` — пустой логин/неправильный пароль(`B2`)
* `400 BAD_REQUEST` — сервер не смог десереализовать JSON
### 10. Используемые сущности ДБ
* users(uuid(PK), login(unique), hashed_password)
## UseCase №2
### 1.Название: Авторизация пользователя
### 2.Актор: Пользователь-пациент
### 3.Цель: Предоставить пользователю возможность получить его данные в виде дневника болезни
### 4.Предусловия:
* Пользователь должен быть зарегистрирован в системе
* Пользователь должен быть не авторизован в системе
### 5.Основной поток:
#### А1.Пользователь при входе в систему выбрасывается из системы
* Пользователь заходит в приложение на любую страницу
* Из-за отсутствия авторизации приложение перенаправляет его на страницу авторизации
* Пользователь вводит свой логин и пароль
* Пользователь получает токен, который открывает ему доступ к получению собственных данных
#### А2.Пользователь осуществляет выход из системы
* Пользователь кликает на кнопку логаута
* На сервере происходил отзыв токена
* Пользователь вновь считается неавторизованным
### 6.Альтернативные потоки:
#### B1.Введен неправильный логин или неправильный пароль
* Пользователь не получает токен, авторизация провалена
* Выводится сообщение об ошибке
#### B2.Поле логин или пароль оставлены пустыми
* При попытке авторизации не происходит запрос токена. Авторизация провалена
* Пустые поля подкрашиваются, как ошибочно заполненные
* Выводится сообщение об ошибке
#### B3.Пользователь не был зарегистрирован в приложении на момент логаута
* Сервер не может отозвать токен и возвращает ошибку
### 7.Постусловия
* Сессия пользователя в виде токена сохраняется на сервере
* Пользователь перенаправлен на основную страницу, где выводится его дневник болезни
### 8.API-Маршруты
* `POST /api/v1/Auth/Login` - Вход пользователя в систему и получение токена
* `POST /api/v1/Auth/Logout` - Отозвать токен и выйти из системы.
### 9.Контракт
#### Login-Request
```
{
"login": "ivan_89",
"password": "S3cureP@ssw0rd"
}
```
##### Response - 200 - OK
```
{
"token": af32df3bas739f272bd109c823
}
```
##### Errors
* `401 BAD_CREDENTIALS` — неверный логин/пароль (B1)
* `422 VALIDATION_FAILED` — пустые поля (B2)
* `400 BAD_REQUEST` — сервер не смог десереализовать JSON
#### Logout-Request
```
{
"token": af32df3bas739f272bd109c823
}
```
##### Response - 200 - OK
```
null
```
##### Errors
* `400 BAD_REQUEST` — Такого токена не существует(B3)
### 10. Используемые сущности ДБ
* users(uuid(PK), login(unique), hashed_password)
## UseCase №3
### 1.Название: Переход на главную страницу
### 2.Актор: Пользователь-пациент
### 3.Цель: Предоставить пользователю поверхностный вывод данных о нем и инструменты для глубокого просмотра данных и их модификации
### 4.Предусловия:
* Пользователь имеет актуальный токен, подтверждающий его авторизацию в системе
* Пользователь тем или иным способом перешел на главную страницу
### 5.Основной поток:
#### A1.Записи в дневнике есть
* Система перенаправляет пользователя на его основную страницу
* Система запрашивает и выводит последние записи и схемы лечения его дневника
* Система делает доступными операции с дневником
#### A2.Записей в дневнике нет
* Заместо вывода записей в дневнике, система выводит заглушку, информирующую пользователя, что дневник пуст
* Система делает доступными операции с дневником
### 6.Потоки исключений:
#### B1.Записи по какой-то причине не подгрузились
* Система выводит нотификацию об ошибке и ее причине
* Заместо вывода записей, система выводит на этом месте заглушку, информирующую о неправильной работе приложения и предоставляющей для нажатия кнопку перезагрузки страницы
### 7.Постусловия
* Пользователь видит свои последние записи и может по ним кликнуть, чтобы увидеть подробную информацию
* Пользователю доступны операции добавления, модификации и удаления записей, а также схем лечения
### 8.API-Маршруты
* `GET /api/v1/User/Diaries` - получить кусок дневника пользователя (требует Authorization: Bearer <token>) query-параметры: from (int, по умолч. 0), count (int, по умолч. 20)
* `GET /api/v1/UserTreatmentSchemes` - получить список схем пользователя (требует Authorization: Bearer <token>) query-параметры: from (int, по умолч. 0), count (int, по умолч. 20)
### 9.Контракт
#### Diaries-Request
##### Response - 200 - OK
```
{
diaries: [
{
"uuid": "e89b6a0c-4b0f-4722-a410-1e0c1864bf8a",
"time": "100000034", // в ms
"mania_level": 1,
"depression_level": 2,
"mood_level": 3,
"activity_level": 4,
"appetite_level": 5,
"dream_level": 6,
"anxiety_level": 7,
"comment": "Накрыл психоз. Выпил одну таблетку аминазина"
"user_treatment_scheme_uuid": bf6d1555-39e9-4d73-8928-4763627f4dd5
}
]
}
```
##### Errors
* `401 TOKEN_REQUIRED|TOKEN_EXPIRED` — токен недействителен, либо отсутствует
* `500 DATA_LOAD_FAILED` — ошибка при загрузке данных (`B1`)
#### UserTreatmentSchemes-Request
##### Response - 200 - OK
```
{
"user_treatment_schemes": [
{
"uuid": "248313cb-a75e-4331-8379-d3f2fc36b68d"
"treatment_name": "Bipolar I Scheme Urgent",
"instructions": "Схема для быстрого и жесткого купирования психозов. Аминазин пить каждый день.",
"medications": [
"eda5a5f7-167a-44b9-900d-c5c6acfc249b"
]
}
]
}
```
##### Errors
* `401 TOKEN_REQUIRED|TOKEN_EXPIRED` — токен недействителен, либо отсутствует
* `500 DATA_LOAD_FAILED` — ошибка при загрузке данных (B1)
### 10. Используемые сущности ДБ
* diaries(uuid(PK), time , mania_level , depression_level , mood_level , activity_level , appetite_level , dream_level , anxiety_level, user_treatment_schemes_uuid)
* mania(level(PK))
* depressions(level(PK))
* moods(level(PK))
* activities(level(PK))
* appetites(level(PK))
* dreams(level(PK))
* anxiety(level(PK))
* treatment_schemes(user_treatment_schemes_uuid(PK), medication_uuid(PK))
* user_treatment_schemes(uuid(PK), user_uuid, treatment_name, instructions)
* medications(uuid(PK), name, dose, unit, is_urgent)
## UseCase №4
### 1.Название: Добавление новой записи в дневник
### 2.Актор: Пользователь-пациент
### 3.Цель: Ведение дневника болезни для врача
### 4.Предусловия:
* Пользователь авторизован в системе
* Пользователь находится на главной странице
### 5.Основной поток:
#### А1.Пользователь создает новую запись в дневнике
* Если отсутствуют, то подключаются идентификаторы мании, депрессии, настроения, активности, аппетита, сна, тревоги
* Пользователь кликает по соответствующей кнопке добавления записи в дневник
* Вызывается меню с формой заполнения записи
* Пользователь описывает свое текущее состояние на модальном окне и указывает используемую схему лечения
### 6.Потоки исключений:
#### B1.Пользователь оставил пустым любое из полей, кроме comment
* Запись о неполном состоянии нельзя создать. Кнопка создания записи заблокирована
#### B2. Идентификаторы состояний не подгрузились
* На поле вводаставится заглушка, делающая невозможным его заполнение.
### 7.Постусловия
* Пользователь добавил запись с указанной датой и прочими состояниями в БД
### 8.API-Маршруты
* `POST /api/v1/User/Diaries` - Создание записи в дневнике
### 9.Контракт
#### Diaries-Request
```
{
`user_uuid`: "51351bb1-7563-479d-a8e9-201d0ff934c2",
`time`: "172493000",
`mania_level`: "6",
`depression_level`: "6",
`mood_level`: "7",
`activity_level`: "4",
`appetite_level`: "5",
`dream_level`: "5",
`anxiety_level`: "9",
`comment`: "Сильная тревога. Пришлось выпить аминазин",
`user_treatment_schemes_uuid`: "51351bb1-7563-479d-a8e9-201d0ff934c2",
}
```
##### Требования к валидации:
* Все поля, кроме `comment` обязательны к заполнению
* `user_treatment_schemes_uuid` должен указывать на существующую схему лечения
##### Response - 201 - Created
```
{
`uuid`: "61351bb1-7563-479d-a8e9-201d0ff934c2",
`user_uuid`: "71351bb1-7563-479d-a8e9-201d0ff934c2",
`time` "172493000",
`mania_level`: "6",
`depression_level`: "6",
`mood_level`: "7",
`activity_level`: "4",
`appetite_level`: "5",
`dream_level`: "5",
`anxiety_level`: "9",
`comment`: "Сильная тревога. Пришлось выпить аминазин",
`user_treatment_scheme`: "51351bb1-7563-479d-a8e9-201d0ff934c2"
}
```
##### Errors
* `400 BAD_REQUEST` — отсутствуют обязательные поля
* `400 BAD_REQUEST` — сервер не смог десереализовать JSON
* `422 UNPROCECCABLE_ENTITY` - Во `time` значение размерностей ниже, чем день, должно быть равно 0
* `422 TREATMENT_SCHEME_IS_NOT_EXISTS` - такой схемы лечения болезни не существует
### 10. Используемые сущности ДБ
* diaries(uuid(PK), time , mania_level , depression_level , mood_level , activity_level , appetite_level , dream_level , anxiety_level, user_treatment_schemes_uuid)
* mania(level(PK))
* depressions(level(PK))
* moods(level(PK))
* activities(level(PK))
* appetites(level(PK))
* dreams(level(PK))
* anxiety(level(PK))
* user_treatment_schemes(uuid(PK))
## UseCase №5
### 1.Название: Изменение существующей записи в дневнике
### 2.Актор: Пользователь-пациент
### 3.Цель: Внесение правок в ошибочно заполненный дневник
### 4.Предусловия:
* Пользователь авторизован в системе
* Пользователю доступно для использования окно создания/редактирования дневника
### 5.Основной поток:
#### А1.Пользователь редактирует новую запись в дневнике
* Если отсутствуют, то подключаются идентификаторы мании, депрессии, настроения, активности, аппетита, сна, тревоги
* Пользователь кликает по кнопке редактирования уже существующей записи о своем состоянии в дневнике
* В последующем меню пользователю предоставляется возможность изменить данные о своем состоянии, а также схему лечения
### 6.Потоки исключений:
#### B1.В приложении отсутствуют схемы лечений
* Выполнение добавления записи невозможно, поэтому кнопка вызова меню блокируется
#### B2.Пользователь оставил пустым любое из полей, кроме comment
* Запись о неполном состоянии нельзя создать. Кнопка создания записи заблокирована
#### B3. Идентификаторы состояний не подгрузились
* На поле вводаставится заглушка, делающая невозможным его заполнение.
#### B4. Попытка изменения даты
* Пользователь попытался сделать запрос с измененной датой
### 7.Постусловия
* Пользователь изменил запись соглсано условиям выше в БД
### 8.API-Маршруты
* `PUT /api/v1/User/Diaries/:diary_guid` - Изменение записи в дневнике
### 9.Контракт
#### Diaries-Request
```
{
`uuid`: "61351bb1-7563-479d-a8e9-201d0ff934c2",
`user_uuid`: "51351bb1-7563-479d-a8e9-201d0ff934c2",
`time`: "172493000",
`mania_level`: "6",
`depression_level`: "6",
`mood_level`: "7",
`activity_level`: "4",
`appetite_level`: "5",
`dream_level`: "5",
`anxiety_level`: "9",
`comment`: "Сильная тревога. Пришлось выпить аминазин",
`user_treatment_schemes_uuid`: "51351bb1-7563-479d-a8e9-201d0ff934c2",
}
```
##### Требования к валидации:
* Все поля, кроме `comment` обязательны к заполнению
* `user_treatment_schemes_uuid` должен указывать на существующую схему лечения
##### Response - 201 - Updated
```
{
`uuid`: "61351bb1-7563-479d-a8e9-201d0ff934c2",
`user_uuid`: "71351bb1-7563-479d-a8e9-201d0ff934c2",
`time` "172493000",
`mania_level`: "6",
`depression_level`: "6",
`mood_level`: "7",
`activity_level`: "4",
`appetite_level`: "5",
`dream_level`: "5",
`anxiety_level`: "9",
`comment`: "Сильная тревога. Пришлось выпить аминазин",
`user_treatment_scheme`: {
"uuid": "248313cb-a75e-4331-8379-d3f2fc36b68d"
"treatment_name": "Bipolar I Scheme Urgent",
"instructions": "Схема для быстрого и жесткого купирования психозов. Аминазин пить каждый день.",
"medications": [
"eda5a5f7-167a-44b9-900d-c5c6acfc249b"
]
},
}
```
##### Errors
* `400 BAD_REQUEST` — отсутствуют обязательные поля
* `400 BAD_REQUEST` — сервер не смог десереализовать JSON
* `422 UNPROCECCABLE_ENTITY` - `time` не должно быть изменено
* `422 TREATMENT_SCHEME_IS_NOT_EXISTS` - такой схемы лечения болезни не существует
### 10. Используемые сущности ДБ
* diaries(uuid(PK), time , mania_level , depression_level , mood_level , activity_level , appetite_level , dream_level , anxiety_level, user_treatment_schemes_uuid)
* mania(level(PK))
* depressions(level(PK))
* moods(level(PK))
* activities(level(PK))
* appetites(level(PK))
* dreams(level(PK))
* anxiety(level(PK))
* user_treatment_schemes(uuid(PK))
## UseCase №6
### 1.Название: Удаление существующей записи в дневнике
### 2.Актор: Пользователь-пациент
### 3.Цель: Удаление ненужной записи в дневнике
### 4.Предусловия:
* Пользователь авторизован в системе
* Пользователю доступен вывод целевой записи, которую необходимо удалить
### 5.Основной поток:
#### А1.Пользователь Удаляет существующую запись в дневнике
* Пользователь нажимает на кнопку удаления записи
* Системы просит подтвердить удаление
* Пользователь подтверждает свое действие. Запись удалена
### 6.Потоки исключений:
#### B1.Пользователь отказывается подтвердить действие
* Запись не удаляется
#### B2.Пользователь удаляет несуществующую запись
* Выдается соответствующий ответ с ошибкой
### 7.Постусловия
* Целевая запись отсутствует в БД
### 8.API-Маршруты
* `DELETE /api/v1/User/Diaries/:diary_guid` - удаление записи в дневнике
### 9.Контракт
#### Diaries-Request
##### Требования к валидации:
* `:diary_guid` должен указывать на существующую страницу дневника
##### Response - 204 - Deleted
```
null
```
##### Errors
* `404 NOT_FOUND` - такой схемы лечения болезни никогда не существовало или она уже удалена
### 10. Используемые сущности ДБ
* diaries(uuid(PK))
## UseCase №7
### 1.Название: Создание схемы лечения
### 2.Актор: Пользователь
### 3.Цель: Предоставление пользователю способа лечения
### 4.Предусловия:
* Пользователь авторизован в системе
* Пользователю доступен функционал создания схем лечения
### 5.Основной поток:
#### А1.Пользователь создает схему лечения
* Пользователь указывает название схемы
* Пользователь пишет к схема инструкцию
* Пользователь добавляет к схеме лекарства
### 6.Потоки исключений:
#### B1.Пользователь отказался заполнять схему леккарствами
* Схему нельзя создать в таком виде. На попытку создать схему выходит окно ошибок
### 7.Постусловия
* Схема создана и доступна для выбора в качестве лечения
### 8.API-маршруты
* `POST /api/v1/TreatmentScheme` - создание схемы лечения
### 9.Контракт
#### Diaries-Request
```
{
"treatment_name": "Bipolar I Scheme Urgent",
"instructions": "Схема для быстрого и жесткого купирования психозов. Аминазин пить каждый день.",
"medications": [
"eca5a5f7-167a-44b9-900d-c5c6acfc249b",
"eda5a5f7-167a-44b9-900d-c5c6acfc249b"
]
}
```
##### Требования к валидации:
* `treatment_name` обязателен к заполнению
* `medications` должен содержать хотя бы одно лекарство
##### Response - 200 - Updated
```
{
"uuid": "eda5a5f7-167a-44b9-900d-c5c6acfc249b"
"treatment_name": "Bipolar I Scheme Urgent",
"instructions": "Схема для быстрого и жесткого купирования психозов. Аминазин пить каждый день.",
"medications": [
"eca5a5f7-167a-44b9-900d-c5c6acfc249b",
"eda5a5f7-167a-44b9-900d-c5c6acfc249b"
]
}
```
##### Errors
* `400 BAD_REQUEST` — сервер не смог десереализовать JSON
* `400 BAD_REQUEST` — Обязательные поля заполнены неправильно
### 10. Используемые сущности ДБ
* user_treatment_schemes(uuid, user_uuid, treatment_name, instructions)
* medications(uuid, name, dose, unit, is_urgent)
* treatment_schemes(user_treatment_schemes_uuid, medication_uuid)