Spaces:
Sleeping
Sleeping
| from datetime import datetime | |
| from uuid import uuid4 | |
| from fastapi import APIRouter, Body, HTTPException, Query, status | |
| from sqlalchemy.exc import IntegrityError | |
| from sqlalchemy.orm import selectinload | |
| from pydantic import UUID4 | |
| from fastapi_pagination import Page, paginate | |
| from workout_api.atleta.schemas import AtletaIn, AtletaOut, AtletaUpdate, AtletaCustomOut | |
| from workout_api.atleta.models import AtletaModel | |
| from workout_api.categorias.models import CategoriaModel | |
| from workout_api.centro_treinamento.models import CentroTreinamentoModel | |
| from workout_api.contrib.dependencies import DatabaseDependency | |
| from sqlalchemy.future import select | |
| router = APIRouter() | |
| async def post( | |
| db_session: DatabaseDependency, | |
| atleta_in: AtletaIn = Body(...) | |
| ): | |
| categoria_nome = atleta_in.categoria.nome | |
| centro_treinamento_nome = atleta_in.centro_treinamento.nome | |
| categoria = (await db_session.execute( | |
| select(CategoriaModel).filter_by(nome=categoria_nome)) | |
| ).scalars().first() | |
| if not categoria: | |
| raise HTTPException( | |
| status_code=status.HTTP_400_BAD_REQUEST, | |
| detail=f'A categoria {categoria_nome} não foi encontrada.' | |
| ) | |
| centro_treinamento = (await db_session.execute( | |
| select(CentroTreinamentoModel).filter_by(nome=centro_treinamento_nome)) | |
| ).scalars().first() | |
| if not centro_treinamento: | |
| raise HTTPException( | |
| status_code=status.HTTP_400_BAD_REQUEST, | |
| detail=f'O centro de treinamento {centro_treinamento_nome} não foi encontrado.' | |
| ) | |
| try: | |
| atleta_model = AtletaModel( | |
| **atleta_in.model_dump(exclude={'categoria', 'centro_treinamento'}), | |
| categoria_id=categoria.pk_id, | |
| centro_treinamento_id=centro_treinamento.pk_id, | |
| created_at=datetime.utcnow() | |
| ) | |
| db_session.add(atleta_model) | |
| await db_session.commit() | |
| await db_session.refresh(atleta_model) | |
| except IntegrityError: | |
| await db_session.rollback() | |
| raise HTTPException( | |
| status_code=status.HTTP_303_SEE_OTHER, | |
| detail=f"Já existe um atleta cadastrado com o cpf: {atleta_in.cpf}" | |
| ) | |
| except Exception as e: | |
| await db_session.rollback() | |
| raise HTTPException( | |
| status_code=status.HTTP_500_INTERNAL_SERVER_ERROR, | |
| detail=f'Ocorreu um erro ao inserir os dados no banco: {e}' | |
| ) | |
| return AtletaOut.model_validate(atleta_model) | |
| async def query( | |
| db_session: DatabaseDependency, | |
| nome: str | None = Query(None, description="Filtrar atleta por nome"), | |
| cpf: str | None = Query(None, description="Filtrar atleta por CPF") | |
| ) -> Page[AtletaCustomOut]: | |
| stmt = select(AtletaModel).options( | |
| selectinload(AtletaModel.categoria), | |
| selectinload(AtletaModel.centro_treinamento) | |
| ) | |
| if nome: | |
| stmt = stmt.where(AtletaModel.nome.ilike(f"%{nome}%")) | |
| if cpf: | |
| stmt = stmt.where(AtletaModel.cpf == cpf) | |
| atletas: list[AtletaModel] = (await db_session.execute(stmt)).scalars().all() | |
| atletas_custom = [ | |
| AtletaCustomOut( | |
| nome=atleta.nome, | |
| categoria=atleta.categoria.nome, | |
| centro_treinamento=atleta.centro_treinamento.nome | |
| ) for atleta in atletas | |
| ] | |
| return paginate(atletas_custom) | |
| async def get(id: UUID4, db_session: DatabaseDependency) -> AtletaOut: | |
| atleta_model: AtletaModel | None = ( | |
| await db_session.execute(select(AtletaModel).filter_by(id=id)) | |
| ).scalars().first() | |
| if not atleta_model: | |
| raise HTTPException( | |
| status_code=status.HTTP_404_NOT_FOUND, | |
| detail=f'Atleta não encontrado no id: {id}' | |
| ) | |
| return AtletaOut.model_validate(atleta_model) | |
| async def patch(id: UUID4, db_session: DatabaseDependency, atleta_up: AtletaUpdate = Body(...)) -> AtletaOut: | |
| atleta_model: AtletaModel | None = ( | |
| await db_session.execute(select(AtletaModel).filter_by(id=id)) | |
| ).scalars().first() | |
| if not atleta_model: | |
| raise HTTPException( | |
| status_code=status.HTTP_404_NOT_FOUND, | |
| detail=f'Atleta não encontrado no id: {id}' | |
| ) | |
| atleta_update = atleta_up.model_dump(exclude_unset=True) | |
| for key, value in atleta_update.items(): | |
| setattr(atleta_model, key, value) | |
| await db_session.commit() | |
| await db_session.refresh(atleta_model) | |
| return AtletaOut.model_validate(atleta_model) | |
| async def delete(id: UUID4, db_session: DatabaseDependency) -> None: | |
| atleta_model: AtletaModel | None = ( | |
| await db_session.execute(select(AtletaModel).filter_by(id=id)) | |
| ).scalars().first() | |
| if not atleta_model: | |
| raise HTTPException( | |
| status_code=status.HTTP_404_NOT_FOUND, | |
| detail=f'Atleta não encontrado no id: {id}' | |
| ) | |
| await db_session.delete(atleta_model) | |
| await db_session.commit() | |