phase 3.2 & 4.1

This commit is contained in:
Danilo Reyes
2025-11-02 00:36:32 -06:00
parent cac1db0ed7
commit d40139822d
21 changed files with 2230 additions and 123 deletions

View File

@@ -1,31 +1,47 @@
"""Group model for image grouping."""
"""Group database model."""
import uuid
from datetime import datetime
from typing import TYPE_CHECKING
from uuid import UUID, uuid4
from sqlalchemy import Column, DateTime, ForeignKey, String, Text
from sqlalchemy.dialects.postgresql import UUID
from sqlalchemy.orm import relationship
from sqlalchemy import DateTime, ForeignKey, String, Text
from sqlalchemy.dialects.postgresql import UUID as PGUUID
from sqlalchemy.orm import Mapped, mapped_column, relationship
from app.database.base import Base
if TYPE_CHECKING:
from app.database.models.board import Board
from app.database.models.board_image import BoardImage
class Group(Base):
"""Group model for organizing images with annotations."""
"""
Group model for organizing images with labels and annotations.
Groups contain multiple images that can be moved together and have
shared visual indicators (color, annotation text).
"""
__tablename__ = "groups"
id = Column(UUID(as_uuid=True), primary_key=True, default=uuid.uuid4)
board_id = Column(UUID(as_uuid=True), ForeignKey("boards.id", ondelete="CASCADE"), nullable=False, index=True)
name = Column(String(255), nullable=False)
color = Column(String(7), nullable=False) # Hex color #RRGGBB
annotation = Column(Text, nullable=True)
created_at = Column(DateTime, nullable=False, default=datetime.utcnow)
updated_at = Column(DateTime, nullable=False, default=datetime.utcnow, onupdate=datetime.utcnow)
id: Mapped[UUID] = mapped_column(PGUUID(as_uuid=True), primary_key=True, default=uuid4)
board_id: Mapped[UUID] = mapped_column(
PGUUID(as_uuid=True), ForeignKey("boards.id", ondelete="CASCADE"), nullable=False
)
name: Mapped[str] = mapped_column(String(255), nullable=False)
color: Mapped[str] = mapped_column(String(7), nullable=False) # Hex color #RRGGBB
annotation: Mapped[str | None] = mapped_column(Text, nullable=True)
created_at: Mapped[datetime] = mapped_column(DateTime, nullable=False, default=datetime.utcnow)
updated_at: Mapped[datetime] = mapped_column(
DateTime, nullable=False, default=datetime.utcnow, onupdate=datetime.utcnow
)
# Relationships
board = relationship("Board", back_populates="groups")
board_images = relationship("BoardImage", back_populates="group")
board: Mapped["Board"] = relationship("Board", back_populates="groups")
board_images: Mapped[list["BoardImage"]] = relationship("BoardImage", back_populates="group")
def __repr__(self) -> str:
return f"<Group(id={self.id}, name={self.name})>"
"""String representation of Group."""
return f"<Group(id={self.id}, name='{self.name}', board_id={self.board_id})>"