175 lines
5.9 KiB
Python
175 lines
5.9 KiB
Python
from __future__ import annotations
|
|
|
|
import uuid
|
|
|
|
from fastapi import APIRouter, Depends, HTTPException, Response, status
|
|
from sqlalchemy.ext.asyncio import AsyncSession
|
|
|
|
from cpv3.infrastructure.auth import get_current_user
|
|
from cpv3.db.session import get_db
|
|
from cpv3.modules.jobs.schemas import (
|
|
JobCreate,
|
|
JobEventCreate,
|
|
JobEventRead,
|
|
JobEventUpdate,
|
|
JobRead,
|
|
JobUpdate,
|
|
)
|
|
from cpv3.modules.jobs.service import JobService
|
|
from cpv3.modules.tasks.service import TaskService
|
|
from cpv3.modules.users.models import User
|
|
|
|
jobs_router = APIRouter(prefix="/api/jobs", tags=["jobs"])
|
|
events_router = APIRouter(prefix="/api/jobs", tags=["events"])
|
|
|
|
|
|
@jobs_router.get("/jobs/", response_model=list[JobRead])
|
|
async def list_jobs_endpoint(
|
|
current_user: User = Depends(get_current_user),
|
|
db: AsyncSession = Depends(get_db),
|
|
) -> list[JobRead]:
|
|
service = JobService(db)
|
|
jobs = await service.list_jobs(requester=current_user)
|
|
return [JobRead.model_validate(j) for j in jobs]
|
|
|
|
|
|
@jobs_router.post("/jobs/", response_model=JobRead, status_code=status.HTTP_201_CREATED)
|
|
async def create_job_endpoint(
|
|
body: JobCreate,
|
|
current_user: User = Depends(get_current_user),
|
|
db: AsyncSession = Depends(get_db),
|
|
) -> JobRead:
|
|
service = JobService(db)
|
|
job = await service.create_job(requester=current_user, data=body)
|
|
return JobRead.model_validate(job)
|
|
|
|
|
|
@jobs_router.get("/jobs/{job_id}/", response_model=JobRead)
|
|
async def retrieve_job_endpoint(
|
|
job_id: uuid.UUID,
|
|
current_user: User = Depends(get_current_user),
|
|
db: AsyncSession = Depends(get_db),
|
|
) -> JobRead:
|
|
service = JobService(db)
|
|
job = await service.get_job(job_id)
|
|
if job is None:
|
|
raise HTTPException(status_code=status.HTTP_404_NOT_FOUND, detail="Не найдено")
|
|
|
|
if not current_user.is_staff and job.user_id != current_user.id:
|
|
raise HTTPException(status_code=status.HTTP_403_FORBIDDEN, detail="Доступ запрещён")
|
|
|
|
return JobRead.model_validate(job)
|
|
|
|
|
|
@jobs_router.patch("/jobs/{job_id}/", response_model=JobRead)
|
|
async def patch_job_endpoint(
|
|
job_id: uuid.UUID,
|
|
body: JobUpdate,
|
|
current_user: User = Depends(get_current_user),
|
|
db: AsyncSession = Depends(get_db),
|
|
) -> JobRead:
|
|
service = JobService(db)
|
|
job = await service.get_job(job_id)
|
|
if job is None:
|
|
raise HTTPException(status_code=status.HTTP_404_NOT_FOUND, detail="Не найдено")
|
|
|
|
if not current_user.is_staff and job.user_id != current_user.id:
|
|
raise HTTPException(status_code=status.HTTP_403_FORBIDDEN, detail="Доступ запрещён")
|
|
|
|
if body.status == "CANCELLED":
|
|
task_service = TaskService(db)
|
|
job = await task_service.cancel_job(job)
|
|
return JobRead.model_validate(job)
|
|
|
|
job = await service.update_job(job, body)
|
|
return JobRead.model_validate(job)
|
|
|
|
|
|
@jobs_router.delete("/jobs/{job_id}/", status_code=status.HTTP_204_NO_CONTENT)
|
|
async def delete_job_endpoint(
|
|
job_id: uuid.UUID,
|
|
current_user: User = Depends(get_current_user),
|
|
db: AsyncSession = Depends(get_db),
|
|
) -> Response:
|
|
service = JobService(db)
|
|
job = await service.get_job(job_id)
|
|
if job is None:
|
|
raise HTTPException(status_code=status.HTTP_404_NOT_FOUND, detail="Не найдено")
|
|
|
|
if not current_user.is_staff and job.user_id != current_user.id:
|
|
raise HTTPException(status_code=status.HTTP_403_FORBIDDEN, detail="Доступ запрещён")
|
|
|
|
await service.deactivate_job(job)
|
|
return Response(status_code=status.HTTP_204_NO_CONTENT)
|
|
|
|
|
|
@events_router.get("/events/", response_model=list[JobEventRead])
|
|
async def list_events_endpoint(
|
|
current_user: User = Depends(get_current_user),
|
|
db: AsyncSession = Depends(get_db),
|
|
) -> list[JobEventRead]:
|
|
_ = current_user
|
|
service = JobService(db)
|
|
events = await service.list_job_events()
|
|
return [JobEventRead.model_validate(e) for e in events]
|
|
|
|
|
|
@events_router.post("/events/", response_model=JobEventRead, status_code=status.HTTP_201_CREATED)
|
|
async def create_event_endpoint(
|
|
body: JobEventCreate,
|
|
current_user: User = Depends(get_current_user),
|
|
db: AsyncSession = Depends(get_db),
|
|
) -> JobEventRead:
|
|
_ = current_user
|
|
service = JobService(db)
|
|
event = await service.create_job_event(body)
|
|
return JobEventRead.model_validate(event)
|
|
|
|
|
|
@events_router.get("/events/{event_id}/", response_model=JobEventRead)
|
|
async def retrieve_event_endpoint(
|
|
event_id: uuid.UUID,
|
|
current_user: User = Depends(get_current_user),
|
|
db: AsyncSession = Depends(get_db),
|
|
) -> JobEventRead:
|
|
_ = current_user
|
|
service = JobService(db)
|
|
event = await service.get_job_event(event_id)
|
|
if event is None:
|
|
raise HTTPException(status_code=status.HTTP_404_NOT_FOUND, detail="Не найдено")
|
|
|
|
return JobEventRead.model_validate(event)
|
|
|
|
|
|
@events_router.patch("/events/{event_id}/", response_model=JobEventRead)
|
|
async def patch_event_endpoint(
|
|
event_id: uuid.UUID,
|
|
body: JobEventUpdate,
|
|
current_user: User = Depends(get_current_user),
|
|
db: AsyncSession = Depends(get_db),
|
|
) -> JobEventRead:
|
|
_ = current_user
|
|
service = JobService(db)
|
|
event = await service.get_job_event(event_id)
|
|
if event is None:
|
|
raise HTTPException(status_code=status.HTTP_404_NOT_FOUND, detail="Не найдено")
|
|
|
|
event = await service.update_job_event(event, body)
|
|
return JobEventRead.model_validate(event)
|
|
|
|
|
|
@events_router.delete("/events/{event_id}/", status_code=status.HTTP_204_NO_CONTENT)
|
|
async def delete_event_endpoint(
|
|
event_id: uuid.UUID,
|
|
current_user: User = Depends(get_current_user),
|
|
db: AsyncSession = Depends(get_db),
|
|
) -> Response:
|
|
_ = current_user
|
|
service = JobService(db)
|
|
event = await service.get_job_event(event_id)
|
|
if event is None:
|
|
raise HTTPException(status_code=status.HTTP_404_NOT_FOUND, detail="Не найдено")
|
|
|
|
await service.deactivate_job_event(event)
|
|
return Response(status_code=status.HTTP_204_NO_CONTENT)
|