""" Authentication-related persistence models """ from datetime import datetime from typing import Optional from sqlalchemy import Column, Integer, String, DateTime, Boolean, ForeignKey, UniqueConstraint from sqlalchemy.orm import relationship from app.models.base import BaseModel class RefreshToken(BaseModel): """Persisted refresh tokens for revocation and auditing.""" __tablename__ = "refresh_tokens" id = Column(Integer, primary_key=True, autoincrement=True, index=True) user_id = Column(Integer, ForeignKey("users.id"), nullable=False, index=True) jti = Column(String(64), nullable=False, unique=True, index=True) user_agent = Column(String(255), nullable=True) ip_address = Column(String(45), nullable=True) issued_at = Column(DateTime, default=datetime.utcnow, nullable=False) expires_at = Column(DateTime, nullable=False, index=True) revoked = Column(Boolean, default=False, nullable=False) revoked_at = Column(DateTime, nullable=True) # relationships user = relationship("User") __table_args__ = ( UniqueConstraint("jti", name="uq_refresh_tokens_jti"), )