Files
sac4cps-backend/microservices/battery-service/models.py
rafaeldpsilva a7a18e6295 first commit
2025-09-09 13:46:42 +01:00

157 lines
5.6 KiB
Python

"""
Pydantic models for Battery Management Service
"""
from pydantic import BaseModel, Field
from typing import List, Optional, Dict, Any, Literal
from datetime import datetime
from enum import Enum
class BatteryState(str, Enum):
IDLE = "idle"
CHARGING = "charging"
DISCHARGING = "discharging"
MAINTENANCE = "maintenance"
ERROR = "error"
class BatteryType(str, Enum):
LITHIUM_ION = "lithium_ion"
LEAD_ACID = "lead_acid"
NICKEL_METAL_HYDRIDE = "nickel_metal_hydride"
FLOW_BATTERY = "flow_battery"
class BatteryStatus(BaseModel):
"""Battery status model"""
battery_id: str = Field(..., description="Unique battery identifier")
name: str = Field(..., description="Human-readable battery name")
type: BatteryType = Field(..., description="Battery technology type")
state: BatteryState = Field(..., description="Current operational state")
# Energy metrics
capacity_kwh: float = Field(..., description="Total battery capacity in kWh")
stored_energy_kwh: float = Field(..., description="Currently stored energy in kWh")
state_of_charge: float = Field(..., description="State of charge (0-100%)")
# Power metrics
max_charge_power_kw: float = Field(..., description="Maximum charging power in kW")
max_discharge_power_kw: float = Field(..., description="Maximum discharging power in kW")
current_power_kw: float = Field(0, description="Current power flow in kW (positive = charging)")
# Technical specifications
efficiency: float = Field(0.95, description="Round-trip efficiency (0-1)")
cycles_completed: int = Field(0, description="Number of charge/discharge cycles")
max_cycles: int = Field(5000, description="Maximum rated cycles")
# Health and maintenance
health_percentage: float = Field(100, description="Battery health (0-100%)")
temperature_celsius: Optional[float] = Field(None, description="Battery temperature")
last_maintenance: Optional[datetime] = Field(None, description="Last maintenance date")
next_maintenance: Optional[datetime] = Field(None, description="Next maintenance date")
# Location and installation
location: Optional[str] = Field(None, description="Physical location")
building: Optional[str] = Field(None, description="Building identifier")
room: Optional[str] = Field(None, description="Room identifier")
# Operational data
installed_date: Optional[datetime] = Field(None, description="Installation date")
last_updated: datetime = Field(default_factory=datetime.utcnow, description="Last status update")
class Config:
json_encoders = {
datetime: lambda v: v.isoformat() if v else None
}
class BatteryCommand(BaseModel):
"""Battery control command"""
battery_id: str = Field(..., description="Target battery ID")
command: Literal["charge", "discharge", "stop"] = Field(..., description="Command type")
power_kw: Optional[float] = Field(None, description="Power level in kW")
duration_minutes: Optional[int] = Field(None, description="Command duration in minutes")
target_soc: Optional[float] = Field(None, description="Target state of charge (0-100%)")
class ChargingRequest(BaseModel):
"""Battery charging/discharging request"""
power_kw: float = Field(..., description="Power level in kW", gt=0)
duration_minutes: Optional[int] = Field(None, description="Duration in minutes", gt=0)
target_soc: Optional[float] = Field(None, description="Target SOC (0-100%)", ge=0, le=100)
class BatteryResponse(BaseModel):
"""Battery operation response"""
battery_id: str
status: Dict[str, Any]
message: Optional[str] = None
class BatteryListResponse(BaseModel):
"""Response for battery list endpoint"""
batteries: List[Dict[str, Any]]
count: int
total_capacity: float = Field(description="Total system capacity in kWh")
total_stored_energy: float = Field(description="Total stored energy in kWh")
class HistoricalDataRequest(BaseModel):
"""Request for historical battery data"""
battery_id: str
start_time: Optional[datetime] = None
end_time: Optional[datetime] = None
hours: int = Field(default=24, description="Hours of data to retrieve")
class BatteryHistoricalData(BaseModel):
"""Historical battery data point"""
timestamp: datetime
state_of_charge: float
power_kw: float
temperature_celsius: Optional[float] = None
efficiency: float
class Config:
json_encoders = {
datetime: lambda v: v.isoformat()
}
class BatteryAnalytics(BaseModel):
"""Battery system analytics"""
total_batteries: int
active_batteries: int
total_capacity_kwh: float
total_stored_energy_kwh: float
average_soc: float
# Energy flows
total_energy_charged_kwh: float
total_energy_discharged_kwh: float
net_energy_flow_kwh: float
# Efficiency metrics
round_trip_efficiency: float
capacity_utilization: float
# Health metrics
average_health: float
batteries_needing_maintenance: int
class MaintenanceAlert(BaseModel):
"""Battery maintenance alert"""
battery_id: str
alert_type: Literal["scheduled", "health", "temperature", "cycles"]
severity: Literal["info", "warning", "critical"]
message: str
recommended_action: str
timestamp: datetime
class Config:
json_encoders = {
datetime: lambda v: v.isoformat()
}
class HealthResponse(BaseModel):
"""Health check response"""
service: str
status: str
timestamp: datetime
version: str
class Config:
json_encoders = {
datetime: lambda v: v.isoformat()
}