""" SQLAlchemy model for energy scores. This module defines the database model for storing energy score calculations from multiple sources (Twitter, Reddit, RSS). """ from datetime import datetime from sqlalchemy import Column, Integer, String, Float, DateTime, Index, ForeignKey, JSON from sqlalchemy.orm import relationship from app.database import Base class EnergyScore(Base): """ Model for storing energy score calculations. Attributes: id: Primary key match_id: Foreign key to the match team_id: Foreign key to the team score: Final energy score (0-100) confidence: Confidence level (0-1) sources_used: List of sources used in calculation (JSON) twitter_score: Energy score from Twitter component reddit_score: Energy score from Reddit component rss_score: Energy score from RSS component temporal_factor: Temporal weighting factor applied twitter_weight: Adjusted weight for Twitter (in degraded mode) reddit_weight: Adjusted weight for Reddit (in degraded mode) rss_weight: Adjusted weight for RSS (in degraded mode) created_at: Timestamp when the energy score was calculated updated_at: Timestamp when the energy score was last updated """ __tablename__ = "energy_scores" id = Column(Integer, primary_key=True, index=True) match_id = Column(Integer, nullable=False, index=True, comment="ID of the match") team_id = Column(Integer, nullable=False, index=True, comment="ID of the team") score = Column(Float, nullable=False, index=True, comment="Final energy score (0-100)") confidence = Column(Float, nullable=False, default=0.0, comment="Confidence level (0-1)") # Sources used (stored as JSON array) sources_used = Column(JSON, nullable=False, default=list, comment="List of sources used") # Component scores twitter_score = Column(Float, nullable=True, comment="Energy score from Twitter component") reddit_score = Column(Float, nullable=True, comment="Energy score from Reddit component") rss_score = Column(Float, nullable=True, comment="Energy score from RSS component") # Temporal weighting temporal_factor = Column(Float, nullable=True, comment="Temporal weighting factor applied") # Adjusted weights (for degraded mode tracking) twitter_weight = Column(Float, nullable=True, comment="Adjusted weight for Twitter") reddit_weight = Column(Float, nullable=True, comment="Adjusted weight for Reddit") rss_weight = Column(Float, nullable=True, comment="Adjusted weight for RSS") # Timestamps created_at = Column(DateTime, nullable=False, index=True, default=datetime.utcnow, comment="Creation timestamp") updated_at = Column(DateTime, nullable=False, index=True, default=datetime.utcnow, onupdate=datetime.utcnow, comment="Last update timestamp") # Indexes for performance __table_args__ = ( Index('idx_energy_scores_match_team', 'match_id', 'team_id'), Index('idx_energy_scores_score', 'score'), Index('idx_energy_scores_confidence', 'confidence'), Index('idx_energy_scores_created_at', 'created_at'), Index('idx_energy_scores_updated_at', 'updated_at'), ) def __repr__(self) -> str: return (f"") def to_dict(self) -> dict: """ Convert energy score model to dictionary. Returns: Dictionary representation of the energy score """ return { 'id': self.id, 'match_id': self.match_id, 'team_id': self.team_id, 'score': self.score, 'confidence': self.confidence, 'sources_used': self.sources_used, 'twitter_score': self.twitter_score, 'reddit_score': self.reddit_score, 'rss_score': self.rss_score, 'temporal_factor': self.temporal_factor, 'twitter_weight': self.twitter_weight, 'reddit_weight': self.reddit_weight, 'rss_weight': self.rss_weight, 'created_at': self.created_at.isoformat() if self.created_at else None, 'updated_at': self.updated_at.isoformat() if self.updated_at else None }