"""time entries and work schedules Revision ID: 0002_time_entries Revises: 0001_initial Create Date: 2026-03-27 """ from alembic import op import sqlalchemy as sa from sqlalchemy.dialects import postgresql revision = "0002_time_entries" down_revision = "0001_initial" branch_labels = None depends_on = None # Enum-Typen explizit definieren (create_type=False → sa.Enum erstellt sie selbst via op.create_table) entrystatus = sa.Enum("pending", "approved", "rejected", name="entrystatus") entrysource = sa.Enum("web", "kiosk", "api", "manual", name="entrysource") def upgrade() -> None: # ── work_schedules ───────────────────────────────────────────────────────── op.create_table( "work_schedules", sa.Column("id", postgresql.UUID(as_uuid=True), primary_key=True), sa.Column("company_id", postgresql.UUID(as_uuid=True), sa.ForeignKey("companies.id", ondelete="CASCADE"), nullable=False), sa.Column("name", sa.String(255), nullable=False), sa.Column("mon_h", sa.Numeric(4, 2), server_default="8.00"), sa.Column("tue_h", sa.Numeric(4, 2), server_default="8.00"), sa.Column("wed_h", sa.Numeric(4, 2), server_default="8.00"), sa.Column("thu_h", sa.Numeric(4, 2), server_default="8.00"), sa.Column("fri_h", sa.Numeric(4, 2), server_default="8.00"), sa.Column("sat_h", sa.Numeric(4, 2), server_default="0.00"), sa.Column("sun_h", sa.Numeric(4, 2), server_default="0.00"), sa.Column("valid_from", sa.Date, nullable=False), ) op.create_index("ix_work_schedules_company_id", "work_schedules", ["company_id"]) # ── time_entries ─────────────────────────────────────────────────────────── op.create_table( "time_entries", sa.Column("id", postgresql.UUID(as_uuid=True), primary_key=True), sa.Column("user_id", postgresql.UUID(as_uuid=True), sa.ForeignKey("users.id", ondelete="CASCADE"), nullable=False), sa.Column("date", sa.Date, nullable=False), sa.Column("start_time", sa.Time(timezone=False), nullable=False), sa.Column("end_time", sa.Time(timezone=False)), sa.Column("break_minutes", sa.Integer, server_default="0"), sa.Column("break_start", sa.Time(timezone=False)), sa.Column("project_id", postgresql.UUID(as_uuid=True)), sa.Column("note", sa.Text), sa.Column("status", entrystatus, nullable=False, server_default="pending"), sa.Column("source", entrysource, nullable=False, server_default="web"), sa.Column("approved_by", postgresql.UUID(as_uuid=True), sa.ForeignKey("users.id", ondelete="SET NULL")), sa.Column("correction_note", sa.Text), sa.Column("created_at", sa.DateTime(timezone=True), server_default=sa.func.now()), sa.Column("updated_at", sa.DateTime(timezone=True), server_default=sa.func.now()), ) op.create_index("ix_time_entries_user_id", "time_entries", ["user_id"]) op.create_index("ix_time_entries_date", "time_entries", ["date"]) op.create_index("ix_time_entries_user_date", "time_entries", ["user_id", "date"]) def downgrade() -> None: op.drop_table("time_entries") op.drop_table("work_schedules") entrystatus.drop(op.get_bind(), checkfirst=True) entrysource.drop(op.get_bind(), checkfirst=True)