This commit is contained in:
aaron 2025-02-15 16:23:23 +08:00
parent cdd070131f
commit ab5d42fb65
4 changed files with 117 additions and 127 deletions

View File

@ -8,7 +8,7 @@ from app.models.database import get_db
from app.api.deps import get_current_user from app.api.deps import get_current_user
from app.models.user import UserDB from app.models.user import UserDB
from app.core.response import success_response, error_response, ResponseModel from app.core.response import success_response, error_response, ResponseModel
from app.models.community_building import CommunityBuildingDB
router = APIRouter() router = APIRouter()
@router.post("", response_model=ResponseModel) @router.post("", response_model=ResponseModel)
@ -26,10 +26,22 @@ async def create_address(
) )
).update({"is_default": False}) ).update({"is_default": False})
# 查询社区名字和楼栋名字
community = db.query(CommunityDB).filter(
CommunityDB.id == address.community_id
).first()
community_building = db.query(CommunityBuildingDB).filter(
CommunityBuildingDB.id == address.community_building_id
).first()
db_address = AddressDB( db_address = AddressDB(
user_id=current_user.userid, user_id=current_user.userid,
community_name=community.name,
community_building_name=community_building.building_name,
**address.model_dump() **address.model_dump()
) )
db.add(db_address) db.add(db_address)
db.commit() db.commit()
db.refresh(db_address) db.refresh(db_address)
@ -80,7 +92,9 @@ async def update_address(
if not db_address: if not db_address:
return error_response(code=404, message="地址不存在") return error_response(code=404, message="地址不存在")
update_data = address.model_dump(exclude_unset=True) update_data = address.model_dump(exclude_unset=True)
if update_data.get("is_default"): if update_data.get("is_default"):
db.query(AddressDB).filter( db.query(AddressDB).filter(
and_( and_(
@ -92,6 +106,18 @@ async def update_address(
for key, value in update_data.items(): for key, value in update_data.items():
setattr(db_address, key, value) setattr(db_address, key, value)
# 查询社区名字和楼栋名字
community = db.query(CommunityDB).filter(
CommunityDB.id == address.community_id
).first()
community_building = db.query(CommunityBuildingDB).filter(
CommunityBuildingDB.id == address.community_building_id
).first()
db_address.community_name = community.name
db_address.community_building_name = community_building.building_name
db.commit() db.commit()
db.refresh(db_address) db.refresh(db_address)
return success_response(data=AddressInfo.model_validate(db_address)) return success_response(data=AddressInfo.model_validate(db_address))

View File

@ -29,6 +29,7 @@ from app.models.community_building import CommunityBuildingDB
from app.models.station import StationDB from app.models.station import StationDB
from app.models.point import PointRecordDB, PointRecordType from app.models.point import PointRecordDB, PointRecordType
from app.core.utils import CommonUtils from app.core.utils import CommonUtils
import logging
router = APIRouter() router = APIRouter()
@ -126,7 +127,7 @@ async def pre_order(
return success_response(data=price_info) return success_response(data=price_info)
@router.post("", response_model=ResponseModel) @router.post("", response_model=ResponseModel)
async def create_shipping_order( async def create_order(
order: OrderCreate, order: OrderCreate,
db: Session = Depends(get_db), db: Session = Depends(get_db),
current_user: UserDB = Depends(get_current_user) current_user: UserDB = Depends(get_current_user)
@ -159,11 +160,21 @@ async def create_shipping_order(
# 更新优惠券状态 # 更新优惠券状态
user_coupon.status = CouponStatus.USED user_coupon.status = CouponStatus.USED
# 查询地址信息
address = db.query(AddressDB).filter(
AddressDB.id == order.addressid
).first()
# 创建订单 # 创建订单
db_order = ShippingOrderDB( db_order = ShippingOrderDB(
orderid=orderid, orderid=orderid,
userid=current_user.userid, userid=current_user.userid,
addressid=order.addressid, address_customer_name=address.name,
address_customer_phone=address.phone,
address_customer_gender=address.gender,
address_community_name=address.community_name,
address_community_building_name=address.community_building_name,
address_detail=address.address_detail,
package_count=price_info.package_count, package_count=price_info.package_count,
original_amount=original_amount, original_amount=original_amount,
coupon_discount_amount=coupon_discount, coupon_discount_amount=coupon_discount,
@ -177,9 +188,15 @@ async def create_shipping_order(
# 创建订单包裹 # 创建订单包裹
for package in order.price_request.packages: for package in order.price_request.packages:
station = db.query(StationDB).filter(
StationDB.id == package.station_id
).first()
db_package = ShippingOrderPackageDB( db_package = ShippingOrderPackageDB(
orderid=orderid, orderid=orderid,
station_id=package.station_id, station_id=package.station_id,
station_name=station.name,
pickup_codes=package.pickup_codes pickup_codes=package.pickup_codes
) )
db.add(db_package) db.add(db_package)
@ -237,21 +254,7 @@ async def get_order_detail(
"""获取订单详情""" """获取订单详情"""
# 使用 join 查询获取订单和相关地址信息 # 使用 join 查询获取订单和相关地址信息
order = db.query( order = db.query(
ShippingOrderDB, ShippingOrderDB
AddressDB.name.label('address_name'),
AddressDB.phone.label('address_phone'),
AddressDB.address_detail.label('address_detail'),
CommunityBuildingDB.building_name.label('building_name'),
CommunityDB.name.label('community_name')
).join(
AddressDB,
ShippingOrderDB.addressid == AddressDB.id
).join(
CommunityBuildingDB,
AddressDB.community_building_id == CommunityBuildingDB.id
).join(
CommunityDB,
CommunityBuildingDB.community_id == CommunityDB.id
).filter( ).filter(
ShippingOrderDB.orderid == orderid ShippingOrderDB.orderid == orderid
).first() ).first()
@ -260,7 +263,7 @@ async def get_order_detail(
return error_response(code=404, message="订单不存在") return error_response(code=404, message="订单不存在")
# 检查权限 # 检查权限
if order.ShippingOrderDB.userid != current_user.userid and UserRole.ADMIN not in current_user.roles: if order.userid != current_user.userid and UserRole.ADMIN not in current_user.roles:
return error_response(code=403, message="无权查看此订单") return error_response(code=403, message="无权查看此订单")
# 查询包裹信息,包含驿站名称 # 查询包裹信息,包含驿站名称
@ -275,15 +278,15 @@ async def get_order_detail(
).all() ).all()
# 如果有配送员 id则获取配送员信息 # 如果有配送员 id则获取配送员信息
if order.ShippingOrderDB.deliveryman_user_id: if order.deliveryman_user_id:
deliveryman_user = db.query(UserDB).filter( deliveryman_user = db.query(UserDB).filter(
UserDB.userid == order.ShippingOrderDB.deliveryman_user_id UserDB.userid == order.deliveryman_user_id
).first() ).first()
deliveryman_user_name = deliveryman_user.nickname deliveryman_user_name = deliveryman_user.nickname
deliveryman_user_avatar = deliveryman_user.optimized_avatar deliveryman_user_avatar = deliveryman_user.optimized_avatar
deliveryman_user_phone = deliveryman_user.phone deliveryman_user_phone = deliveryman_user.phone
delivery_count = db.query(ShippingOrderDB).filter( delivery_count = db.query(ShippingOrderDB).filter(
ShippingOrderDB.deliveryman_user_id == order.ShippingOrderDB.deliveryman_user_id, ShippingOrderDB.deliveryman_user_id == order.deliveryman_user_id,
ShippingOrderDB.status == OrderStatus.COMPLETED ShippingOrderDB.status == OrderStatus.COMPLETED
).count() ).count()
else: else:
@ -294,29 +297,28 @@ async def get_order_detail(
# 构建响应数据 # 构建响应数据
order_data = { order_data = {
"orderid": order.ShippingOrderDB.orderid, "orderid": order.orderid,
"userid": order.ShippingOrderDB.userid, "userid": order.userid,
"addressid": order.ShippingOrderDB.addressid, "package_count": order.package_count,
"package_count": order.ShippingOrderDB.package_count, "original_amount": order.original_amount,
"original_amount": order.ShippingOrderDB.original_amount, "coupon_discount_amount": order.coupon_discount_amount,
"coupon_discount_amount": order.ShippingOrderDB.coupon_discount_amount, "coupon_id": order.coupon_id,
"coupon_id": order.ShippingOrderDB.coupon_id, "final_amount": order.final_amount,
"final_amount": order.ShippingOrderDB.final_amount, "status": order.status,
"status": order.ShippingOrderDB.status, "complete_images": order.complete_images.split(",") if order.complete_images else None,
"complete_images": order.ShippingOrderDB.complete_images.split(",") if order.ShippingOrderDB.complete_images else None, "create_time": order.create_time,
"create_time": order.ShippingOrderDB.create_time, "delivery_method": order.delivery_method,
"delivery_method": order.ShippingOrderDB.delivery_method, "deliveryman_user_id": order.deliveryman_user_id,
"deliveryman_user_id": order.ShippingOrderDB.deliveryman_user_id,
"deliveryman_nickname": deliveryman_user_name, "deliveryman_nickname": deliveryman_user_name,
"deliveryman_avatar": deliveryman_user_avatar, "deliveryman_avatar": deliveryman_user_avatar,
"deliveryman_phone": deliveryman_user_phone, "deliveryman_phone": deliveryman_user_phone,
"delivery_count": delivery_count, "delivery_count": delivery_count,
# 地址相关信息 # 地址相关信息
"address_name": order.address_name, "address_name": order.address_customer_name,
"address_phone": order.address_phone, "address_phone": order.address_customer_phone,
"address_detail": order.address_detail, "address_detail": order.address_detail,
"building_name": order.building_name, "building_name": order.address_community_building_name,
"community_name": order.community_name "community_name": order.address_community_name
} }
# 构建包裹信息,包含驿站名称 # 构建包裹信息,包含驿站名称
@ -344,21 +346,9 @@ async def get_user_orders(
): ):
"""获取用户订单列表""" """获取用户订单列表"""
try: try:
# 查询订单和地址信息 # 查询订单
query = db.query( query = db.query(
ShippingOrderDB, ShippingOrderDB
AddressDB,
CommunityBuildingDB,
CommunityDB
).join(
AddressDB,
ShippingOrderDB.addressid == AddressDB.id
).join(
CommunityBuildingDB,
AddressDB.community_building_id == CommunityBuildingDB.id
).join(
CommunityDB,
CommunityBuildingDB.community_id == CommunityDB.id
).filter( ).filter(
ShippingOrderDB.userid == current_user.userid ShippingOrderDB.userid == current_user.userid
) )
@ -376,24 +366,20 @@ async def get_user_orders(
).offset(skip).limit(limit).all() ).offset(skip).limit(limit).all()
orders = [] orders = []
for order, address, building, community in results: for order in results:
# 查询订单包裹信息 # 查询订单包裹信息
packages = db.query( packages = db.query(
ShippingOrderPackageDB, ShippingOrderPackageDB
StationDB.name.label('station_name')
).join(
StationDB,
ShippingOrderPackageDB.station_id == StationDB.id
).filter( ).filter(
ShippingOrderPackageDB.orderid == order.orderid ShippingOrderPackageDB.orderid == order.orderid
).all() ).all()
# 格式化包裹信息 # 格式化包裹信息
package_list = [{ package_list = [{
"id": package.ShippingOrderPackageDB.id, "id": package.id,
"station_id": package.ShippingOrderPackageDB.station_id, "station_id": package.station_id,
"station_name": package.station_name, "station_name": package.station_name,
"pickup_codes": package.ShippingOrderPackageDB.pickup_codes "pickup_codes": package.pickup_codes
} for package in packages] } for package in packages]
orders.append({ orders.append({
@ -409,15 +395,11 @@ async def get_user_orders(
"final_amount": order.final_amount, "final_amount": order.final_amount,
"packages": package_list, "packages": package_list,
"address": { "address": {
"id": address.id, "name": order.address_customer_name,
"name": address.name, "phone": order.address_customer_phone,
"phone": address.phone, "community_name": order.address_community_name,
"community_id": community.id, "building_name": order.address_community_building_name,
"community_name": community.name, "address_detail": order.address_detail
"building_id": building.id,
"building_name": building.building_name,
"building_number": building.building_number,
"address_detail": address.address_detail
} }
}) })
@ -502,21 +484,7 @@ async def get_deliveryman_orders(
"""获取配送员订单列表""" """获取配送员订单列表"""
# 基础查询 # 基础查询
query = db.query( query = db.query(
ShippingOrderDB, ShippingOrderDB
AddressDB,
CommunityBuildingDB,
CommunityDB
).join(
AddressDB,
ShippingOrderDB.addressid == AddressDB.id
).join(
CommunityBuildingDB,
AddressDB.community_building_id == CommunityBuildingDB.id
).join(
CommunityDB,
CommunityBuildingDB.community_id == CommunityDB.id
).filter(
CommunityDB.id == deliveryman.community_id
) )
# 状态筛选 # 状态筛选
@ -566,15 +534,11 @@ async def get_deliveryman_orders(
"delivery_method": order.delivery_method, "delivery_method": order.delivery_method,
"packages": package_list, "packages": package_list,
"address": { "address": {
"id": address.id, "name": order.address_customer_name,
"name": address.name, "phone": order.address_customer_phone,
"phone": address.phone, "community_name": order.address_community_name,
"community_id": community.id, "building_name": order.address_community_building_name,
"community_name": community.name, "address_detail": order.address_detail
"building_id": building.id,
"building_name": building.building_name,
"building_number": building.building_number,
"address_detail": address.address_detail
} }
}) })
@ -793,19 +757,7 @@ async def get_orders(
try: try:
# 构建基础查询 # 构建基础查询
query = db.query( query = db.query(
ShippingOrderDB, ShippingOrderDB
AddressDB,
CommunityBuildingDB,
CommunityDB
).join(
AddressDB,
ShippingOrderDB.addressid == AddressDB.id
).join(
CommunityBuildingDB,
AddressDB.community_building_id == CommunityBuildingDB.id
).join(
CommunityDB,
CommunityBuildingDB.community_id == CommunityDB.id
) )
# 添加用户ID过滤 # 添加用户ID过滤
@ -862,15 +814,11 @@ async def get_orders(
"final_amount": order.final_amount, "final_amount": order.final_amount,
"packages": package_list, "packages": package_list,
"address": { "address": {
"id": address.id, "name": order.address_customer_name,
"name": address.name, "phone": order.address_customer_phone,
"phone": address.phone, "community_name": order.address_community_name,
"community_id": community.id, "building_name": order.address_community_building_name,
"community_name": community.name, "address_detail": order.address_detail
"building_id": building.id,
"building_name": building.building_name,
"building_number": building.building_number,
"address_detail": address.address_detail
} }
}) })

View File

@ -12,6 +12,7 @@ class AddressDB(Base):
id = Column(Integer, primary_key=True, autoincrement=True) id = Column(Integer, primary_key=True, autoincrement=True)
user_id = Column(Integer, ForeignKey("users.userid"), index=True) user_id = Column(Integer, ForeignKey("users.userid"), index=True)
community_id = Column(Integer, index=True) community_id = Column(Integer, index=True)
community_name = Column(String(100), nullable=True)
community_building_id = Column(Integer, ForeignKey("community_buildings.id"), nullable=True) community_building_id = Column(Integer, ForeignKey("community_buildings.id"), nullable=True)
community_building_name = Column(String(100), nullable=True) community_building_name = Column(String(100), nullable=True)
address_detail = Column(String(200)) address_detail = Column(String(200))
@ -26,17 +27,15 @@ class AddressDB(Base):
class AddressCreate(BaseModel): class AddressCreate(BaseModel):
community_id: int community_id: int
community_building_id: Optional[int] = None community_building_id: Optional[int] = None
community_building_name: Optional[str] = Field(None, max_length=100)
address_detail: str = Field(..., max_length=200) address_detail: str = Field(..., max_length=200)
name: str = Field(..., max_length=50) name: str = Field(..., max_length=50)
phone: str = Field(..., pattern="^1[3-9]\d{9}$") phone: str = Field(..., pattern="^1[3-9]\d{9}$")
gender: Gender = Gender.UNKNOWN gender: Gender = Gender.UNKNOWN
is_default: bool = False is_default: bool = True
class AddressUpdate(BaseModel): class AddressUpdate(BaseModel):
community_id: Optional[int] = None community_id: Optional[int] = None
community_building_id: Optional[int] = None community_building_id: Optional[int] = None
community_building_name: Optional[str] = Field(None, max_length=100)
address_detail: Optional[str] = Field(None, max_length=200) address_detail: Optional[str] = Field(None, max_length=200)
name: Optional[str] = Field(None, max_length=50) name: Optional[str] = Field(None, max_length=50)
phone: Optional[str] = Field(None, pattern="^1[3-9]\d{9}$") phone: Optional[str] = Field(None, pattern="^1[3-9]\d{9}$")
@ -46,6 +45,7 @@ class AddressUpdate(BaseModel):
class AddressInfo(BaseModel): class AddressInfo(BaseModel):
id: int id: int
community_id: int community_id: int
community_name:Optional[str]
community_name: Optional[str] = None community_name: Optional[str] = None
community_building_id: Optional[int] community_building_id: Optional[int]
community_building_name: Optional[str] community_building_name: Optional[str]

View File

@ -5,6 +5,7 @@ from sqlalchemy.sql import func
from pydantic import BaseModel, Field from pydantic import BaseModel, Field
from .database import Base from .database import Base
import enum import enum
from app.models.user import Gender
from app.core.imageprocessor import process_image, ImageFormat from app.core.imageprocessor import process_image, ImageFormat
class OrderStatus(str, enum.Enum): class OrderStatus(str, enum.Enum):
@ -25,7 +26,18 @@ class ShippingOrderDB(Base):
orderid = Column(String(32), primary_key=True) orderid = Column(String(32), primary_key=True)
userid = Column(Integer, ForeignKey("users.userid"), index=True) userid = Column(Integer, ForeignKey("users.userid"), index=True)
addressid = Column(Integer, ForeignKey("delivery_addresses.id"), index=True)
# 配送地址信息
address_customer_name = Column(String(50), nullable=False, default='') # 客户名称快照
address_customer_phone = Column(String(11), nullable=False, default='') # 客户电话快照
address_customer_gender = Column(Enum(Gender), nullable=False, default=Gender.UNKNOWN) # 客户性别快照
address_community_name = Column(String(50), nullable=False, default='') # 小区名称快照
address_community_building_name = Column(String(50), nullable=False, default='') # 楼栋名称快照
address_detail = Column(String(100), nullable=False, default='') # 详细地址快照
delivery_method = Column(Enum(DeliveryMethod), nullable=False)
package_count = Column(Integer, nullable=False) package_count = Column(Integer, nullable=False)
original_amount = Column(Float, nullable=False) original_amount = Column(Float, nullable=False)
coupon_discount_amount = Column(Float, default=0) coupon_discount_amount = Column(Float, default=0)
@ -36,11 +48,6 @@ class ShippingOrderDB(Base):
cancel_reason = Column(String(200), nullable=True) # 取消原因 cancel_reason = Column(String(200), nullable=True) # 取消原因
complete_images = Column(String(1000), nullable=True) # 完成订单的图片URL多个URL用逗号分隔 complete_images = Column(String(1000), nullable=True) # 完成订单的图片URL多个URL用逗号分隔
create_time = Column(DateTime(timezone=True), server_default=func.now()) create_time = Column(DateTime(timezone=True), server_default=func.now())
delivery_method = Column(
Enum(DeliveryMethod),
nullable=False,
default=DeliveryMethod.DELIVERY_AT_DOORSTEP
)
deliveryman_user_id = Column(Integer, ForeignKey("users.userid"), nullable=True) deliveryman_user_id = Column(Integer, ForeignKey("users.userid"), nullable=True)
cancel_user_id = Column(Integer, ForeignKey("users.userid"), nullable=True) cancel_user_id = Column(Integer, ForeignKey("users.userid"), nullable=True)
pay_status = Column(Boolean, default=False) # 支付状态 pay_status = Column(Boolean, default=False) # 支付状态
@ -60,6 +67,7 @@ class ShippingOrderPackageDB(Base):
id = Column(Integer, primary_key=True, autoincrement=True) id = Column(Integer, primary_key=True, autoincrement=True)
orderid = Column(String(32), ForeignKey("shipping_orders.orderid"), index=True) orderid = Column(String(32), ForeignKey("shipping_orders.orderid"), index=True)
station_id = Column(Integer, ForeignKey("stations.id"), index=True) station_id = Column(Integer, ForeignKey("stations.id"), index=True)
station_name = Column(String(50), nullable=False)
pickup_codes = Column(String(100), nullable=False) pickup_codes = Column(String(100), nullable=False)
create_time = Column(DateTime(timezone=True), server_default=func.now()) create_time = Column(DateTime(timezone=True), server_default=func.now())
@ -84,7 +92,14 @@ class OrderCreate(BaseModel):
class OrderInfo(BaseModel): class OrderInfo(BaseModel):
orderid: str orderid: str
userid: int userid: int
addressid: int
address_customer_name: str
address_customer_phone: str
address_community_name: str
address_community_building_name: str
address_detail: str
address_customer_gender: Gender
package_count: int package_count: int
original_amount: float original_amount: float
coupon_discount_amount: float coupon_discount_amount: float
@ -113,6 +128,7 @@ class OrderPackageInfo(BaseModel):
id: int id: int
orderid: str orderid: str
station_id: int station_id: int
station_name: str
pickup_codes: str pickup_codes: str
create_time: datetime create_time: datetime