Files
SIB/backend/app/api/shuttles/__init__.py

181 lines
6.1 KiB
Python

from fastapi import APIRouter, Depends, Query, HTTPException, UploadFile, File, Form
from sqlmodel import Session, select
from typing import Optional, List
import os
import shutil
from uuid import uuid4, UUID
from app.core.database import get_session
from app.models.shuttle import Shuttle
from app.api.deps import get_current_admin
from app.services.image_handler import save_image, delete_image
router = APIRouter(prefix="/api/shuttles", tags=["shuttles"])
@router.get("", response_model=List[Shuttle])
async def get_shuttles(
origin: Optional[str] = Query(None),
destination: Optional[str] = Query(None),
company_name: Optional[str] = Query(None),
trip_type: Optional[str] = Query(None),
is_active: Optional[bool] = Query(None),
session: Session = Depends(get_session)
):
"""Get all shuttles with optional filters."""
statement = select(Shuttle)
if is_active is not None:
statement = statement.where(Shuttle.is_active == is_active)
if origin:
statement = statement.where(Shuttle.origin.contains(origin))
if destination:
statement = statement.where(Shuttle.destination.contains(destination))
if company_name:
statement = statement.where(Shuttle.company_name.contains(company_name))
if trip_type:
statement = statement.where(Shuttle.trip_type == trip_type)
shuttles = session.exec(statement).all()
return shuttles
@router.post("", response_model=Shuttle)
async def create_shuttle(
route_name: str = Form(...),
origin: str = Form(...),
destination: str = Form(...),
vehicle_type: str = Form(...),
company_name: Optional[str] = Form(None),
trip_type: str = Form("one_way"),
price_per_person: Optional[float] = Form(None),
price_private_trip: Optional[float] = Form(None),
estimated_duration: str = Form(...),
contact_whatsapp: str = Form(...),
phone_number: Optional[str] = Form(None),
english_speaking: bool = Form(False),
description: Optional[str] = Form(None),
departure_times: Optional[str] = Form(None),
is_active: bool = Form(True),
image: Optional[UploadFile] = File(None),
session: Session = Depends(get_session),
_: bool = Depends(get_current_admin)
):
"""Create a new shuttle trip (Admin only)."""
image_url = None
if image:
image_url = save_image(image, "vehicles")
shuttle = Shuttle(
route_name=route_name,
origin=origin,
destination=destination,
vehicle_type=vehicle_type,
company_name=company_name,
trip_type=trip_type,
price_per_person=price_per_person,
price_private_trip=price_private_trip,
estimated_duration=estimated_duration,
contact_whatsapp=contact_whatsapp,
phone_number=phone_number,
english_speaking=english_speaking,
description=description,
departure_times=departure_times,
image_url=image_url,
is_active=is_active
)
session.add(shuttle)
session.commit()
session.refresh(shuttle)
return shuttle
@router.put("/{shuttle_id}", response_model=Shuttle)
async def update_shuttle(
shuttle_id: UUID,
route_name: str = Form(...),
origin: str = Form(...),
destination: str = Form(...),
vehicle_type: str = Form(...),
company_name: Optional[str] = Form(None),
trip_type: str = Form("one_way"),
price_per_person: Optional[float] = Form(None),
price_private_trip: Optional[float] = Form(None),
estimated_duration: str = Form(...),
contact_whatsapp: str = Form(...),
phone_number: Optional[str] = Form(None),
english_speaking: bool = Form(False),
description: Optional[str] = Form(None),
departure_times: Optional[str] = Form(None),
is_active: bool = Form(True),
image: Optional[UploadFile] = File(None),
session: Session = Depends(get_session),
_: bool = Depends(get_current_admin)
):
"""Update a shuttle trip (Admin only)."""
db_shuttle = session.get(Shuttle, shuttle_id)
if not db_shuttle:
raise HTTPException(status_code=404, detail="Shuttle not found")
db_shuttle.route_name = route_name
db_shuttle.origin = origin
db_shuttle.destination = destination
db_shuttle.vehicle_type = vehicle_type
db_shuttle.company_name = company_name
db_shuttle.trip_type = trip_type
db_shuttle.price_per_person = price_per_person
db_shuttle.price_private_trip = price_private_trip
db_shuttle.estimated_duration = estimated_duration
db_shuttle.contact_whatsapp = contact_whatsapp
db_shuttle.phone_number = phone_number
db_shuttle.english_speaking = english_speaking
db_shuttle.description = description
db_shuttle.departure_times = departure_times
db_shuttle.is_active = is_active
if image:
# Delete old image if exists
if db_shuttle.image_url:
delete_image(db_shuttle.image_url)
db_shuttle.image_url = save_image(image, "vehicles")
session.add(db_shuttle)
session.commit()
session.refresh(db_shuttle)
return db_shuttle
@router.delete("/{shuttle_id}")
async def delete_shuttle(
shuttle_id: UUID,
session: Session = Depends(get_session),
_: bool = Depends(get_current_admin)
):
"""Delete a shuttle trip (Admin only)."""
db_shuttle = session.get(Shuttle, shuttle_id)
if not db_shuttle:
raise HTTPException(status_code=404, detail="Shuttle not found")
# Delete image from storage
if db_shuttle.image_url:
delete_image(db_shuttle.image_url)
session.delete(db_shuttle)
session.commit()
return {"ok": True}
@router.patch("/{shuttle_id}/status")
async def update_shuttle_status(
shuttle_id: UUID,
is_active: bool = Query(...),
session: Session = Depends(get_session),
_: bool = Depends(get_current_admin)
):
"""Update shuttle active status (Admin only)."""
db_shuttle = session.get(Shuttle, shuttle_id)
if not db_shuttle:
raise HTTPException(status_code=404, detail="Shuttle not found")
db_shuttle.is_active = is_active
session.add(db_shuttle)
session.commit()
session.refresh(db_shuttle)
return db_shuttle