crappy
This commit is contained in:
2
main.py
2
main.py
@@ -6,7 +6,7 @@ import routers
|
|||||||
origins = [
|
origins = [
|
||||||
'http://localhost:5173'
|
'http://localhost:5173'
|
||||||
]
|
]
|
||||||
app = FastAPI()
|
app = FastAPI(separate_input_output_schemas=False)
|
||||||
|
|
||||||
app.add_middleware(
|
app.add_middleware(
|
||||||
CORSMiddleware,
|
CORSMiddleware,
|
||||||
|
|||||||
@@ -33,7 +33,7 @@ class Deal(BaseModel):
|
|||||||
is_completed = Column(Boolean, nullable=False, server_default='0', default=False, comment='Завершена')
|
is_completed = Column(Boolean, nullable=False, server_default='0', default=False, comment='Завершена')
|
||||||
|
|
||||||
services = relationship('DealService', back_populates='deal')
|
services = relationship('DealService', back_populates='deal')
|
||||||
|
products = relationship('DealProduct', back_populates='deal')
|
||||||
|
|
||||||
class DealStatusHistory(BaseModel):
|
class DealStatusHistory(BaseModel):
|
||||||
__tablename__ = 'deals_status_history'
|
__tablename__ = 'deals_status_history'
|
||||||
|
|||||||
@@ -13,3 +13,15 @@ class DealService(BaseModel):
|
|||||||
service = relationship('Service')
|
service = relationship('Service')
|
||||||
|
|
||||||
quantity = Column(Integer, nullable=False, comment='Кол-во услуги')
|
quantity = Column(Integer, nullable=False, comment='Кол-во услуги')
|
||||||
|
|
||||||
|
|
||||||
|
class DealProduct(BaseModel):
|
||||||
|
__tablename__ = 'deal_products'
|
||||||
|
deal_id = Column(Integer, ForeignKey('deals.id'), nullable=False, comment='ID Сделки', primary_key=True)
|
||||||
|
deal = relationship('Deal', back_populates='products')
|
||||||
|
|
||||||
|
product_id = Column(Integer, ForeignKey('products.id'), nullable=False, comment='ID Продукта', primary_key=True)
|
||||||
|
product = relationship('Product')
|
||||||
|
|
||||||
|
quantity = Column(Integer, nullable=False, comment='Кол-во продукта')
|
||||||
|
|
||||||
|
|||||||
@@ -53,11 +53,82 @@ async def get_summary(
|
|||||||
|
|
||||||
|
|
||||||
@deal_router.post(
|
@deal_router.post(
|
||||||
'/services/add',
|
'/services/add/multiple',
|
||||||
response_model=DealAddServicesResponse,
|
response_model=DealAddServicesResponse,
|
||||||
|
operation_id='addMultipleDealServices'
|
||||||
)
|
)
|
||||||
async def services_add(
|
async def services_add(
|
||||||
request: DealAddServicesRequest,
|
request: DealAddServicesRequest,
|
||||||
session: Annotated[AsyncSession, Depends(get_session)]
|
session: Annotated[AsyncSession, Depends(get_session)]
|
||||||
):
|
):
|
||||||
return await DealService(session).add_services(request)
|
return await DealService(session).add_services(request)
|
||||||
|
|
||||||
|
|
||||||
|
@deal_router.post(
|
||||||
|
'/services/add',
|
||||||
|
response_model=DealAddServiceResponse,
|
||||||
|
operation_id='addDealService'
|
||||||
|
)
|
||||||
|
async def services_add(
|
||||||
|
request: DealAddServiceRequest,
|
||||||
|
session: Annotated[AsyncSession, Depends(get_session)]
|
||||||
|
):
|
||||||
|
return await DealService(session).add_service(request)
|
||||||
|
|
||||||
|
|
||||||
|
@deal_router.post(
|
||||||
|
'/services/update-quantity',
|
||||||
|
response_model=DealUpdateServiceQuantityResponse,
|
||||||
|
operation_id='updateDealServiceQuantity'
|
||||||
|
)
|
||||||
|
async def services_update(
|
||||||
|
request: DealUpdateServiceQuantityRequest,
|
||||||
|
session: Annotated[AsyncSession, Depends(get_session)]
|
||||||
|
):
|
||||||
|
return await DealService(session).update_service_quantity(request)
|
||||||
|
|
||||||
|
@deal_router.post(
|
||||||
|
'/services/delete',
|
||||||
|
response_model=DealDeleteServiceResponse,
|
||||||
|
operation_id='deleteDealService'
|
||||||
|
)
|
||||||
|
async def services_delete(
|
||||||
|
request: DealDeleteServiceRequest,
|
||||||
|
session: Annotated[AsyncSession, Depends(get_session)]
|
||||||
|
):
|
||||||
|
return await DealService(session).delete_service(request)
|
||||||
|
|
||||||
|
@deal_router.post(
|
||||||
|
'/services/delete/multiple',
|
||||||
|
response_model=DealDeleteServicesResponse,
|
||||||
|
operation_id='deleteMultipleDealServices'
|
||||||
|
)
|
||||||
|
async def services_delete(
|
||||||
|
request: DealDeleteServicesRequest,
|
||||||
|
session: Annotated[AsyncSession, Depends(get_session)]
|
||||||
|
):
|
||||||
|
return await DealService(session).delete_services(request)
|
||||||
|
|
||||||
|
|
||||||
|
@deal_router.get(
|
||||||
|
'/get-all',
|
||||||
|
response_model=DealGetAllResponse,
|
||||||
|
operation_id='getAllDeals'
|
||||||
|
)
|
||||||
|
async def get_all(
|
||||||
|
session: Annotated[AsyncSession, Depends(get_session)]
|
||||||
|
):
|
||||||
|
return await DealService(session).get_all()
|
||||||
|
|
||||||
|
|
||||||
|
# endpoint to get deal by id
|
||||||
|
@deal_router.get(
|
||||||
|
'/get/{deal_id}',
|
||||||
|
response_model=DealSchema,
|
||||||
|
operation_id='getDealById'
|
||||||
|
)
|
||||||
|
async def get_deal_by_id(
|
||||||
|
deal_id: int,
|
||||||
|
session: Annotated[AsyncSession, Depends(get_session)]
|
||||||
|
):
|
||||||
|
return await DealService(session).get_by_id(deal_id)
|
||||||
|
|||||||
@@ -3,6 +3,7 @@ from typing import List
|
|||||||
from schemas.base import CustomModelCamel, OkMessageSchema
|
from schemas.base import CustomModelCamel, OkMessageSchema
|
||||||
|
|
||||||
|
|
||||||
|
# region Entities
|
||||||
class ClientDetailsSchema(CustomModelCamel):
|
class ClientDetailsSchema(CustomModelCamel):
|
||||||
address: str | None = None
|
address: str | None = None
|
||||||
phone_number: str | None = None
|
phone_number: str | None = None
|
||||||
@@ -16,19 +17,37 @@ class ClientSchema(CustomModelCamel):
|
|||||||
details: ClientDetailsSchema | None = None
|
details: ClientDetailsSchema | None = None
|
||||||
|
|
||||||
|
|
||||||
|
# endregion
|
||||||
|
|
||||||
|
# region Requests
|
||||||
class ClientSearchRequest(CustomModelCamel):
|
class ClientSearchRequest(CustomModelCamel):
|
||||||
name: str
|
name: str
|
||||||
|
|
||||||
|
|
||||||
class ClientSearchResponse(CustomModelCamel):
|
|
||||||
clients: List[ClientSchema]
|
|
||||||
|
|
||||||
|
|
||||||
class ClientUpdateDetailsRequest(CustomModelCamel):
|
class ClientUpdateDetailsRequest(CustomModelCamel):
|
||||||
client_id: int
|
client_id: int
|
||||||
details: ClientDetailsSchema
|
details: ClientDetailsSchema
|
||||||
|
|
||||||
|
|
||||||
|
class ClientCreateRequest(CustomModelCamel):
|
||||||
|
data: ClientSchema
|
||||||
|
|
||||||
|
|
||||||
|
class ClientUpdateRequest(CustomModelCamel):
|
||||||
|
data: ClientSchema
|
||||||
|
|
||||||
|
|
||||||
|
class ClientDeleteRequest(CustomModelCamel):
|
||||||
|
client_id: int
|
||||||
|
|
||||||
|
|
||||||
|
# endregion
|
||||||
|
|
||||||
|
# region Responses
|
||||||
|
class ClientSearchResponse(CustomModelCamel):
|
||||||
|
clients: List[ClientSchema]
|
||||||
|
|
||||||
|
|
||||||
class ClientUpdateDetailsResponse(CustomModelCamel):
|
class ClientUpdateDetailsResponse(CustomModelCamel):
|
||||||
ok: bool
|
ok: bool
|
||||||
|
|
||||||
@@ -41,21 +60,10 @@ class ClientCreateResponse(OkMessageSchema):
|
|||||||
pass
|
pass
|
||||||
|
|
||||||
|
|
||||||
class ClientCreateRequest(CustomModelCamel):
|
|
||||||
data: ClientSchema
|
|
||||||
|
|
||||||
|
|
||||||
class ClientUpdateRequest(CustomModelCamel):
|
|
||||||
data: ClientSchema
|
|
||||||
|
|
||||||
|
|
||||||
class ClientUpdateResponse(OkMessageSchema):
|
class ClientUpdateResponse(OkMessageSchema):
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
|
||||||
class ClientDeleteRequest(CustomModelCamel):
|
|
||||||
client_id: int
|
|
||||||
|
|
||||||
|
|
||||||
class ClientDeleteResponse(OkMessageSchema):
|
class ClientDeleteResponse(OkMessageSchema):
|
||||||
pass
|
pass
|
||||||
|
# endregion
|
||||||
|
|||||||
@@ -1,8 +1,9 @@
|
|||||||
import datetime
|
import datetime
|
||||||
from typing import List
|
from typing import List
|
||||||
|
|
||||||
from schemas.base import CustomModelCamel
|
from schemas.base import CustomModelCamel, OkMessageSchema
|
||||||
from schemas.client import ClientSchema
|
from schemas.client import ClientSchema
|
||||||
|
from schemas.service import ServiceSchema
|
||||||
|
|
||||||
|
|
||||||
# region Entities
|
# region Entities
|
||||||
@@ -23,10 +24,20 @@ class DealSummary(CustomModelCamel):
|
|||||||
|
|
||||||
|
|
||||||
class DealServiceSchema(CustomModelCamel):
|
class DealServiceSchema(CustomModelCamel):
|
||||||
id: int
|
service: ServiceSchema
|
||||||
quantity: int
|
quantity: int
|
||||||
|
|
||||||
|
|
||||||
|
class DealSchema(CustomModelCamel):
|
||||||
|
id: int
|
||||||
|
name: str
|
||||||
|
client_id: int
|
||||||
|
created_at: datetime.datetime
|
||||||
|
current_status: int
|
||||||
|
services: List[DealServiceSchema]
|
||||||
|
# total_price: int
|
||||||
|
|
||||||
|
|
||||||
# endregion Entities
|
# endregion Entities
|
||||||
|
|
||||||
# region Requests
|
# region Requests
|
||||||
@@ -56,6 +67,36 @@ class DealAddServicesRequest(CustomModelCamel):
|
|||||||
services: list[DealServiceSchema]
|
services: list[DealServiceSchema]
|
||||||
|
|
||||||
|
|
||||||
|
class DealGetAllResponse(CustomModelCamel):
|
||||||
|
deals: List[DealSchema]
|
||||||
|
|
||||||
|
|
||||||
|
class DealUpdateServiceQuantityRequest(CustomModelCamel):
|
||||||
|
deal_id: int
|
||||||
|
service_id: int
|
||||||
|
quantity: int
|
||||||
|
|
||||||
|
|
||||||
|
class DealAddServiceRequest(CustomModelCamel):
|
||||||
|
deal_id: int
|
||||||
|
service_id: int
|
||||||
|
quantity: int
|
||||||
|
|
||||||
|
|
||||||
|
class DealDeleteServiceRequest(CustomModelCamel):
|
||||||
|
deal_id: int
|
||||||
|
service_id: int
|
||||||
|
|
||||||
|
|
||||||
|
class DealDeleteServicesResponse(OkMessageSchema):
|
||||||
|
pass
|
||||||
|
|
||||||
|
|
||||||
|
class DealDeleteServicesRequest(CustomModelCamel):
|
||||||
|
deal_id: int
|
||||||
|
service_ids: List[int]
|
||||||
|
|
||||||
|
|
||||||
# endregion Requests
|
# endregion Requests
|
||||||
|
|
||||||
# region Responses
|
# region Responses
|
||||||
@@ -79,4 +120,17 @@ class DealSummaryResponse(CustomModelCamel):
|
|||||||
class DealAddServicesResponse(CustomModelCamel):
|
class DealAddServicesResponse(CustomModelCamel):
|
||||||
ok: bool
|
ok: bool
|
||||||
message: str
|
message: str
|
||||||
|
|
||||||
|
|
||||||
|
class DealUpdateServiceQuantityResponse(CustomModelCamel):
|
||||||
|
ok: bool
|
||||||
|
message: str
|
||||||
|
|
||||||
|
|
||||||
|
class DealAddServiceResponse(OkMessageSchema):
|
||||||
|
pass
|
||||||
|
|
||||||
|
|
||||||
|
class DealDeleteServiceResponse(OkMessageSchema):
|
||||||
|
pass
|
||||||
# endregion Responses
|
# endregion Responses
|
||||||
|
|||||||
@@ -1,14 +1,12 @@
|
|||||||
import datetime
|
import datetime
|
||||||
from typing import Union, Annotated
|
from typing import Union
|
||||||
|
|
||||||
from fastapi import Depends
|
|
||||||
from sqlalchemy import select, update
|
from sqlalchemy import select, update
|
||||||
from sqlalchemy.orm import joinedload
|
from sqlalchemy.orm import joinedload
|
||||||
|
|
||||||
from models import Client, ClientDetails, User
|
from models import Client, ClientDetails, User
|
||||||
from services.auth import get_current_user
|
|
||||||
from services.base import BaseService
|
|
||||||
from schemas.client import *
|
from schemas.client import *
|
||||||
|
from services.base import BaseService
|
||||||
|
|
||||||
|
|
||||||
class ClientService(BaseService):
|
class ClientService(BaseService):
|
||||||
|
|||||||
100
services/deal.py
100
services/deal.py
@@ -1,6 +1,6 @@
|
|||||||
import models.secondary
|
import models.secondary
|
||||||
from typing import Union
|
from typing import Union
|
||||||
|
import models.deal
|
||||||
from fastapi import HTTPException
|
from fastapi import HTTPException
|
||||||
from sqlalchemy import select, func
|
from sqlalchemy import select, func
|
||||||
from sqlalchemy.orm import joinedload, selectinload
|
from sqlalchemy.orm import joinedload, selectinload
|
||||||
@@ -156,3 +156,101 @@ class DealService(BaseService):
|
|||||||
)
|
)
|
||||||
await self.session.commit()
|
await self.session.commit()
|
||||||
return DealAddServicesResponse(ok=True, message='Услуги успешно добавлены')
|
return DealAddServicesResponse(ok=True, message='Услуги успешно добавлены')
|
||||||
|
|
||||||
|
async def get_all(self) -> DealGetAllResponse:
|
||||||
|
deals_query = await self.session.scalars(select(Deal).options(joinedload(Deal.client)))
|
||||||
|
deals = deals_query.all()
|
||||||
|
result = []
|
||||||
|
for deal in deals:
|
||||||
|
result.append(DealSchema.model_validate(deal))
|
||||||
|
return DealGetAllResponse(deals=result)
|
||||||
|
|
||||||
|
async def get_by_id(self, deal_id: int) -> DealSchema:
|
||||||
|
deal = await self.session.scalar(
|
||||||
|
select(Deal)
|
||||||
|
.options(
|
||||||
|
joinedload(Deal.client),
|
||||||
|
selectinload(Deal.services)
|
||||||
|
.joinedload(models.secondary.DealService.service)
|
||||||
|
.joinedload(Service.category))
|
||||||
|
.where(Deal.id == deal_id)
|
||||||
|
)
|
||||||
|
if not deal:
|
||||||
|
raise HTTPException(status_code=404, detail="Сделка не найдена")
|
||||||
|
return DealSchema.model_validate(deal)
|
||||||
|
|
||||||
|
async def update_service_quantity(self,
|
||||||
|
request: DealUpdateServiceQuantityRequest) -> DealUpdateServiceQuantityResponse:
|
||||||
|
try:
|
||||||
|
deal_service = await self.session.scalar(
|
||||||
|
select(models.secondary.DealService)
|
||||||
|
.where(models.secondary.DealService.deal_id == request.deal_id,
|
||||||
|
models.secondary.DealService.service_id == request.service_id)
|
||||||
|
)
|
||||||
|
if not deal_service:
|
||||||
|
raise HTTPException(status_code=404, detail="Сделка не найдена")
|
||||||
|
deal_service.quantity = request.quantity
|
||||||
|
await self.session.commit()
|
||||||
|
return DealUpdateServiceQuantityResponse(ok=True, message='Количество успешно обновлено')
|
||||||
|
except Exception as e:
|
||||||
|
await self.session.rollback()
|
||||||
|
return DealUpdateServiceQuantityResponse(ok=False, message=str(e))
|
||||||
|
|
||||||
|
async def add_service(self, request: DealAddServiceRequest) -> DealAddServiceResponse:
|
||||||
|
try:
|
||||||
|
deal = await self.session.scalar(select(Deal).where(Deal.id == request.deal_id))
|
||||||
|
if not deal:
|
||||||
|
raise HTTPException(status_code=404, detail="Сделка не найдена")
|
||||||
|
service = await self.session.scalar(select(Service).where(Service.id == request.service_id))
|
||||||
|
if not service:
|
||||||
|
raise HTTPException(status_code=404, detail="Услуга не найдена")
|
||||||
|
# Preventing duplicates
|
||||||
|
deal_service = await self.session.scalar(
|
||||||
|
select(models.secondary.DealService)
|
||||||
|
.where(models.secondary.DealService.deal_id == request.deal_id,
|
||||||
|
models.secondary.DealService.service_id == request.service_id)
|
||||||
|
)
|
||||||
|
if deal_service:
|
||||||
|
raise HTTPException(status_code=400, detail="Услуга уже добавлена")
|
||||||
|
deal_service = models.secondary.DealService(
|
||||||
|
deal_id=request.deal_id,
|
||||||
|
service_id=request.service_id,
|
||||||
|
quantity=request.quantity
|
||||||
|
)
|
||||||
|
self.session.add(deal_service)
|
||||||
|
await self.session.commit()
|
||||||
|
return DealAddServiceResponse(ok=True, message='Услуга успешно добавлена')
|
||||||
|
except Exception as e:
|
||||||
|
await self.session.rollback()
|
||||||
|
return DealAddServiceResponse(ok=False, message=str(e))
|
||||||
|
|
||||||
|
async def delete_service(self, request: DealDeleteServiceRequest) -> DealDeleteServiceResponse:
|
||||||
|
try:
|
||||||
|
deal_service = await self.session.scalar(
|
||||||
|
select(models.secondary.DealService)
|
||||||
|
.where(models.secondary.DealService.deal_id == request.deal_id,
|
||||||
|
models.secondary.DealService.service_id == request.service_id)
|
||||||
|
)
|
||||||
|
if not deal_service:
|
||||||
|
raise HTTPException(status_code=404, detail="Сделка не найдена")
|
||||||
|
await self.session.delete(deal_service)
|
||||||
|
await self.session.commit()
|
||||||
|
return DealDeleteServiceResponse(ok=True, message='Услуга успешно удалена')
|
||||||
|
except Exception as e:
|
||||||
|
await self.session.rollback()
|
||||||
|
return DealDeleteServiceResponse(ok=False, message=str(e))
|
||||||
|
|
||||||
|
async def delete_services(self, request: DealDeleteServicesRequest) -> DealDeleteServicesResponse:
|
||||||
|
try:
|
||||||
|
deal_services = await self.session.scalars(
|
||||||
|
select(models.secondary.DealService)
|
||||||
|
.where(models.secondary.DealService.deal_id == request.deal_id,
|
||||||
|
models.secondary.DealService.service_id.in_(request.service_ids))
|
||||||
|
)
|
||||||
|
for deal_service in deal_services:
|
||||||
|
await self.session.delete(deal_service)
|
||||||
|
await self.session.commit()
|
||||||
|
return DealDeleteServicesResponse(ok=True, message='Услуги успешно удалены')
|
||||||
|
except Exception as e:
|
||||||
|
await self.session.rollback()
|
||||||
|
return DealDeleteServicesResponse(ok=False, message=str(e))
|
||||||
|
|||||||
Reference in New Issue
Block a user