43 lines
1.6 KiB
Python
43 lines
1.6 KiB
Python
"""Device model"""
|
|
from sqlalchemy import Column, String, Integer, ForeignKey, Boolean, Index, Enum
|
|
from sqlalchemy.orm import relationship
|
|
from app.models.base import BaseModel
|
|
import enum
|
|
|
|
|
|
class DeviceOSType(str, enum.Enum):
|
|
"""Supported Cisco OS versions"""
|
|
IOS = "ios"
|
|
IOS_XE = "ios_xe"
|
|
IOS_XR = "ios_xr"
|
|
|
|
|
|
class Device(BaseModel):
|
|
"""Network device (Cisco switch/router)"""
|
|
__tablename__ = "devices"
|
|
__table_args__ = (
|
|
Index("ix_devices_project_id", "project_id"),
|
|
Index("ix_devices_hostname", "hostname"),
|
|
)
|
|
|
|
project_id = Column(Integer, ForeignKey("projects.id"), nullable=False)
|
|
hostname = Column(String(255), nullable=False)
|
|
ip_address = Column(String(15), nullable=False) # IPv4 or FQDN
|
|
os_type = Column(Enum(DeviceOSType), default=DeviceOSType.IOS, nullable=False)
|
|
model = Column(String(255), nullable=True) # e.g., "Catalyst 2960"
|
|
|
|
# SSH connectivity (optional, used only for push)
|
|
# WARNING: Never store plain passwords in database
|
|
ssh_username = Column(String(255), nullable=True)
|
|
ssh_port = Column(Integer, default=22, nullable=False)
|
|
|
|
is_active = Column(Boolean, default=True, nullable=False)
|
|
|
|
# Relationships
|
|
project = relationship("Project", back_populates="devices")
|
|
configurations = relationship("Configuration", back_populates="device", cascade="all, delete-orphan")
|
|
push_logs = relationship("PushLog", back_populates="device", cascade="all, delete-orphan")
|
|
|
|
def __repr__(self):
|
|
return f"<Device {self.hostname} ({self.ip_address})>"
|