from pydantic import BaseModel, Field, root_validator, validator, model_validator
from datetime import datetime
from typing import List, Optional, Dict, Any
from enum import Enum

class Status(str, Enum):
    ACTIVE = "active"
    INACTIVE = "inactive"
    MAINTENANCE = "maintenance"

class Coordinates(BaseModel):
    lat: float
    lng: float

class ScheduleBase(BaseModel):
    #account_id: str
    account_id: Optional[str] = None
    schedule_name: str
    description: Optional[str] = None
    # start_time: datetime
    # end_time: datetime
    start_time: Optional[datetime] = None
    end_time: Optional[datetime] = None
    # task_ids: List[str] = []
    # workforce_id: Optional[str] = None
    # metadata: Optional[Dict] = {}
    task_ids: Optional[List[str]] = None
    workforce_id: Optional[str] = None
    metadata: Optional[Dict] = None
    status: Status = Field(default=Status.ACTIVE)
    addons_name: Optional[str] = None

class ScheduleCreate(ScheduleBase):
    pass

class ScheduleUpdate(BaseModel):
    schedule_name: Optional[str] = None
    description: Optional[str] = None
    start_time: Optional[datetime] = None
    end_time: Optional[datetime] = None
    task_ids: Optional[List[str]] = None
    workforce_id: Optional[str] = None
    metadata: Optional[Dict] = None
    addons_name: Optional[str] = None

class Schedule(ScheduleBase):
    schedule_id: str
    sch_id: Optional[int] = None
    created_date: datetime
    customer_info: Optional[dict] = None
    workforce_info: Optional[dict] = None
    fleet_info: Optional[dict] = None
    travel_status: Optional[int] = None
    task_stops: Optional[List[Dict[str, Any]]] = None

class Schedules(BaseModel):
    total_count: int
    schedules: List[Schedule]

class ScheduleAssignmentRequest(BaseModel):
    schedule_id: str
    account_id: str
    workforce_id: str

class ScheduleSelectItem(BaseModel):
    schedule_id: str
    schedule_name: str

class ScheduleTravelStatusUpdateRequest(BaseModel):
    schedule_id: str
    travel_status: int

class TaskStop(BaseModel):
    location: str
    location_coords: Optional[Coordinates] = None 
    drop_location: Optional[str] = None             # <-- you had drop_location in payload
    drop_location_coords: Optional[Coordinates] = None
    type: str
    sequence: int
    timing: Optional[datetime] = None
    customer_id: Optional[str] = None  # <-- added
    skills: Optional[List[str]] = None

    @model_validator(mode="after")
    def validate_coordinates(self):
        if not self.location_coords or not self.drop_location_coords:
            raise ValueError("Both 'location_coords' and 'drop_location_coords' must be provided.")

        for field_name, coord in [
            ("location_coords", self.location_coords),
            ("drop_location_coords", self.drop_location_coords),
        ]:
            if coord.lat is None or coord.lng is None:
                raise ValueError(f"'{field_name}' must contain valid 'lat' and 'lng' values.")
            if not isinstance(coord.lat, (float, int)) or not isinstance(coord.lng, (float, int)):
                raise ValueError(f"'{field_name}' lat/lng must be numeric values.")

        return self


class ScheduleWithTasksCreate(BaseModel):
    account_id: str
    addons_name: Optional[str] = None
    start_time: Optional[datetime] = None
    end_time: Optional[datetime] = None
    description: Optional[str] = None
    task_stops: Optional[List[TaskStop]] = None  # <-- updated
    vehicle_model_id: Optional[str] = None   
    priority_type: Optional[str] = None

#Shift status started below
class ShiftStatusBase(BaseModel):
    account_id: str
    schedule_id: str
    workforce_id: str
    shift_status: str  # e.g. "active", "on_break"
    remarks: Optional[str] = None


class ShiftStatusCreate(ShiftStatusBase):
    pass


class ShiftStatusUpdate(BaseModel):
    shift_status: Optional[str] = None
    remarks: Optional[str] = None


class ShiftStatusResponse(ShiftStatusBase):
    id: str
    created_date: datetime
    updated_date: Optional[datetime] = None


class ShiftStatusList(BaseModel):
    total_count: int
    shift_statuses: List[ShiftStatusResponse]

