from datetime import datetime, timezone from sqlalchemy import ( Column, DateTime, Integer, LargeBinary, String, Text, Boolean, Date, ForeignKey, UniqueConstraint, ) from sqlalchemy.orm import DeclarativeBase, relationship class Base(DeclarativeBase): pass class Show(Base): __tablename__ = "shows" id = Column(Integer, primary_key=True, autoincrement=True) title = Column(String(200), nullable=False) description = Column(Text, nullable=False) host = Column(String(100), nullable=False) genre = Column(String(80), nullable=False) show_art_url = Column(String(500), nullable=True) hero_image_url = Column(String(500), nullable=True) display_order = Column(Integer, nullable=False, default=0) active = Column(Boolean, default=True) schedules = relationship("ShowSchedule", back_populates="show", cascade="all, delete-orphan") class ShowSchedule(Base): __tablename__ = "show_schedules" id = Column(Integer, primary_key=True, autoincrement=True) show_id = Column(Integer, ForeignKey("shows.id", ondelete="CASCADE"), nullable=False) day_of_week = Column(Integer, nullable=False) time = Column(String(10), nullable=False) show = relationship("Show", back_populates="schedules") __table_args__ = ( UniqueConstraint("show_id", "day_of_week", "time", name="uq_show_sched"), ) class Event(Base): __tablename__ = "events" id = Column(Integer, primary_key=True, autoincrement=True) date = Column(Date, nullable=False) title = Column(String(200), nullable=False) description = Column(Text, nullable=False) location = Column(String(200), nullable=False) icon = Column(String(10), nullable=False) rsvp_url = Column(String(500), nullable=True) active = Column(Boolean, default=True) class StationConfig(Base): __tablename__ = "station_config" id = Column(Integer, primary_key=True, autoincrement=True) key = Column(String(20), unique=True, nullable=False, default="default") # Identity callsign = Column(String(10), nullable=False, default="KMTN") name_primary = Column(String(100), nullable=False, default="KMountain") name_secondary = Column(String(100), nullable=False, default="Flower Radio") tagline = Column(String(200), nullable=False, default="Community Radio — Est. 1987") frequency = Column(String(10), nullable=False, default="98.7 FM") founded_year = Column(Integer, nullable=False, default=1987) # Nonprofit nonprofit_type = Column(String(10), nullable=False, default="501(c)(3)") ein = Column(String(20), nullable=False, default="84-XXXXXXX") # Images (URL strings relative to app root) logo_url = Column(String(500), nullable=False, default="svg/small-flower.svg") hero_background_url = Column(String(500), nullable=False, default="svg/mountain-landscape.svg") hero_icon_url = Column(String(500), nullable=False, default="svg/orange-flower.svg") hero_divider_url = Column(String(500), nullable=False, default="svg/mountain-divider.svg") # Contact address = Column(Text, nullable=False, default="42 Pine Street\nMountain View, CO 80424") phone = Column(String(30), nullable=False, default="(970) 555-0198") email = Column(String(100), nullable=False, default="hello@kmountainflower.org") website = Column(String(200), nullable=False, default="kmountainflower.org") # Donation donation_url = Column(String(500), nullable=False, default="") class HistoryEntry(Base): __tablename__ = "history_entries" id = Column(Integer, primary_key=True, autoincrement=True) year = Column(Integer, nullable=False) title = Column(String(200), nullable=False) body = Column(Text, nullable=False) display_order = Column(Integer, nullable=False) active = Column(Boolean, default=True) class TeamMember(Base): __tablename__ = "team_members" id = Column(Integer, primary_key=True, autoincrement=True) name = Column(String(100), nullable=False) title = Column(String(150), nullable=False) bio = Column(Text, nullable=True) photo_url = Column(String(500), nullable=True) display_order = Column(Integer, nullable=False) active = Column(Boolean, default=True) class CommunityHighlight(Base): __tablename__ = "community_highlights" id = Column(Integer, primary_key=True, autoincrement=True) icon = Column(String(10), nullable=False) title = Column(String(200), nullable=False) description = Column(Text, nullable=False) display_order = Column(Integer, nullable=False) active = Column(Boolean, default=True) class StorageBlob(Base): __tablename__ = "storage_blobs" id = Column(Integer, primary_key=True, autoincrement=True) blob_id = Column(String(32), unique=True, nullable=False, index=True) content_type = Column(String(100), nullable=False) size = Column(Integer, nullable=False) data = Column(LargeBinary, nullable=False) created_at = Column(DateTime, nullable=False, default=lambda: datetime.now(timezone.utc))