From dfaa0de7c46d5fda0858d4de38003d3eba230ac3 Mon Sep 17 00:00:00 2001 From: coder-bot Date: Tue, 18 Aug 2026 18:18:10 +0000 Subject: [PATCH] WIP checkpoint: Trust & Safety: Moderation data model + Alembic migration --- backend/app/models/user.py | 37 +++++++++++++++++++++++++++++++++++-- 1 file changed, 35 insertions(+), 2 deletions(-) diff --git a/backend/app/models/user.py b/backend/app/models/user.py index 8ce7f88..f3c0a7c 100644 --- a/backend/app/models/user.py +++ b/backend/app/models/user.py @@ -1,7 +1,7 @@ -from datetime import date +from datetime import date, datetime from typing import Optional -from sqlalchemy import Column, Integer, String, Boolean, DateTime, Date +from sqlalchemy import Column, Integer, String, Boolean, DateTime, Date, Enum from sqlalchemy.orm import relationship from sqlalchemy.sql import func @@ -17,12 +17,45 @@ class User(Base): hashed_password = Column(String(255), nullable=False) date_of_birth = Column(Date, nullable=True) is_active = Column(Boolean, default=True) + role = Column( + Enum("user", "moderator", "admin", name="user_role", create_type=False), + default="user", + nullable=False, + ) + banned_until = Column(DateTime(timezone=True), nullable=True) + suspended_until = Column(DateTime(timezone=True), nullable=True) created_at = Column(DateTime(timezone=True), server_default=func.now()) updated_at = Column(DateTime(timezone=True), onupdate=func.now()) sessions = relationship("Session", back_populates="user", cascade="all, delete-orphan") worlds = relationship("World", back_populates="owner") assets = relationship("Asset", back_populates="owner") + reported_by = relationship( + "Report", + foreign_keys="Report.reporter_id", + back_populates="reporter", + ) + resolved_reports = relationship( + "Report", + foreign_keys="Report.resolved_by", + back_populates="resolver", + ) + moderation_actions = relationship( + "ModerationAction", + foreign_keys="ModerationAction.moderator_id", + back_populates="moderator", + ) + target_moderation_actions = relationship( + "ModerationAction", + foreign_keys="ModerationAction.target_user_id", + back_populates="target_user", + ) + appeals = relationship("Appeal", back_populates="user") + reviewed_appeals = relationship( + "Appeal", + foreign_keys="Appeal.reviewed_by", + back_populates="reviewer", + ) @property def is_adult(self) -> bool: