/
FlysAt
/
DataFoundry
Обзор
Документация
Войти
/
FlysAt
/
DataFoundry
Код
Запросы
0
Задачи
Вики
Пакеты
0
Релизы
0
CI/CD
Аналитика
Безопасность
master
backend/src/api/services/order.py
118 строк
4 KB
AlexanderShmygol
fixed collection type
16 май 2026, 18:47
16 май 2026, 18:47
2422d88
Код
Авторство
О чём код?
from fastapi import HTTPException, status from sqlalchemy.ext.asyncio import AsyncSession from src.api.repositories.order import OrderRepository from src.models.order import OperationType, Order, OrderStatus from src.models.user import User from src.schemas.order import OrderCreateSchema, OrderStatusUpdateSchema, OrderUpdateSchema class OrderService: def __init__(self, db: AsyncSession) -> None: self.orders = OrderRepository(db) @staticmethod def _ensure_customer(user: User) -> None: if "customer" not in user.roles: raise HTTPException( status_code=status.HTTP_403_FORBIDDEN, detail="Only customer can manage orders", ) @staticmethod def _ensure_executor(user: User) -> None: if "executor" not in user.roles: raise HTTPException( status_code=status.HTTP_403_FORBIDDEN, detail="Only executor can view available orders", ) @staticmethod def _can_executor_send_to_review(order: Order, user: User, target_status: OrderStatus) -> bool: return order.current_executor_id == user.id and target_status == OrderStatus.REVIEW async def create_order(self, payload: OrderCreateSchema, current_user: User) -> Order: self._ensure_customer(current_user) initial_status = ( OrderStatus.PENDING if payload.operation_type == OperationType.COLLECTION else OrderStatus.CANCELLED ) order = Order( title=payload.title, description=payload.description, deadline=payload.deadline, data_volume=payload.data_volume, operation_type=payload.operation_type, budget=payload.budget, operation_tags=payload.operation_tags, description_tags=payload.description_tags, quality_requirement=payload.quality_requirement, license_name=payload.license_name, visibility=payload.visibility, status=initial_status, customer_id=current_user.id, ) return await self.orders.create(order) async def list_orders(self) -> list[Order]: return await self.orders.list_all() async def list_my_orders(self, current_user: User, statuses: list[OrderStatus] | None) -> list[Order]: self._ensure_customer(current_user) return await self.orders.list_by_customer(current_user.id, statuses) async def list_available_orders( self, current_user: User, operation_type: OperationType | None, ) -> list[Order]: self._ensure_executor(current_user) return await self.orders.list_available(operation_type) async def get_order(self, order_id: int) -> Order: order = await self.orders.get_by_id(order_id) if not order: raise HTTPException(status_code=404, detail="Order not found") return order async def update_order( self, order_id: int, payload: OrderUpdateSchema, current_user: User, ) -> Order: order = await self.get_order(order_id) if order.customer_id != current_user.id: raise HTTPException(status_code=403, detail="You can update only your orders") for field, value in payload.model_dump(exclude_unset=True).items(): setattr(order, field, value) return await self.orders.save(order) async def update_order_status( self, order_id: int, payload: OrderStatusUpdateSchema, current_user: User, ) -> Order: order = await self.get_order(order_id) is_owner = order.customer_id == current_user.id can_executor_send_to_review = self._can_executor_send_to_review(order, current_user, payload.status) if not is_owner and not can_executor_send_to_review: raise HTTPException( status_code=403, detail="Only owner can change status, assigned executor can only move order to review", ) order.status = payload.status return await self.orders.save(order) async def delete_order(self, order_id: int, current_user: User) -> None: order = await self.get_order(order_id) if order.customer_id != current_user.id: raise HTTPException(status_code=403, detail="You can delete only your orders") await self.orders.delete(order)