from sqlalchemy import Column, DateTime, Float, ForeignKey, Integer, String, Table, Text from sqlalchemy.dialects.sqlite import JSON from app.database import Base from app.models.base import BaseModel, utc_now brain_event_tags = Table( "brain_event_tags", Base.metadata, Column("event_id", String(36), ForeignKey("brain_events.id"), primary_key=True), Column("tag_id", String(36), ForeignKey("brain_tags.id"), primary_key=True), ) brain_memory_tags = Table( "brain_memory_tags", Base.metadata, Column("memory_id", String(36), ForeignKey("brain_memories.id"), primary_key=True), Column("tag_id", String(36), ForeignKey("brain_tags.id"), primary_key=True), ) brain_memory_sources = Table( "brain_memory_sources", Base.metadata, Column("memory_id", String(36), ForeignKey("brain_memories.id"), primary_key=True), Column("event_id", String(36), ForeignKey("brain_events.id"), primary_key=True), ) class BrainEvent(BaseModel): __tablename__ = "brain_events" user_id = Column(String(36), ForeignKey("users.id"), nullable=False, index=True) source_type = Column(String(50), nullable=False, index=True) source_id = Column(String(36), nullable=False, index=True) event_type = Column(String(50), nullable=False, index=True) title = Column(String(255), nullable=True) content_summary = Column(Text, nullable=True) raw_excerpt = Column(Text, nullable=True) metadata_ = Column(JSON, nullable=True) importance_signal = Column(Float, default=0.0, nullable=False) is_user_pinned = Column(Integer, default=0, nullable=False) occurred_at = Column(DateTime, default=utc_now, nullable=False, index=True) processed_at = Column(DateTime, nullable=True) status = Column(String(20), default="pending", nullable=False, index=True) class BrainCandidate(BaseModel): __tablename__ = "brain_candidates" user_id = Column(String(36), ForeignKey("users.id"), nullable=False, index=True) candidate_type = Column(String(50), nullable=False, index=True) title = Column(String(255), nullable=False) summary = Column(Text, nullable=False) importance_score = Column(Float, default=0.0, nullable=False) confidence_score = Column(Float, default=0.0, nullable=False) time_scope = Column(String(20), default="short_term", nullable=False) valid_from = Column(DateTime, nullable=True) valid_to = Column(DateTime, nullable=True) source_event_ids = Column(JSON, nullable=True) reasoning_trace = Column(Text, nullable=True) status = Column(String(20), default="new", nullable=False, index=True) reviewed_at = Column(DateTime, nullable=True) class BrainMemory(BaseModel): __tablename__ = "brain_memories" user_id = Column(String(36), ForeignKey("users.id"), nullable=False, index=True) memory_type = Column(String(50), nullable=False, index=True) title = Column(String(255), nullable=False) content = Column(Text, nullable=False) importance = Column(Integer, default=5, nullable=False) confidence = Column(Float, default=0.0, nullable=False) timeline_date = Column(DateTime, nullable=True) first_learned_at = Column(DateTime, default=utc_now, nullable=False) last_reinforced_at = Column(DateTime, nullable=True) reinforcement_count = Column(Integer, default=0, nullable=False) status = Column(String(20), default="active", nullable=False, index=True) origin_candidate_id = Column(String(36), ForeignKey("brain_candidates.id"), nullable=True) origin_source_types = Column(JSON, nullable=True) metadata_ = Column(JSON, nullable=True) class BrainTag(BaseModel): __tablename__ = "brain_tags" user_id = Column(String(36), ForeignKey("users.id"), nullable=False, index=True) name = Column(String(100), nullable=False, index=True) category = Column(String(50), nullable=False) priority = Column(String(20), default="secondary", nullable=False, index=True) score = Column(Float, default=0.0, nullable=False) last_seen_at = Column(DateTime, nullable=True)