"""rulebook tables: rulebooks, rulebook_topics, rules, project_rulebook_subscriptions

Revision ID: 0055
Revises: 0054
Create Date: 2026-05-27

Adds the Scribe Rulebook hierarchy as a fourth top-level entity, sibling
to Project. Rules carry a structural (statement, why, how_to_apply)
triple. Projects subscribe to Rulebooks (many-to-many). See the design
doc at docs/superpowers/specs/2026-05-27-scribe-rulebook-design.md.
"""
from alembic import op
import sqlalchemy as sa


revision = "0055"
down_revision = "0054"
branch_labels = None
depends_on = None


def upgrade() -> None:
    op.create_table(
        "rulebooks",
        sa.Column("id", sa.BigInteger, primary_key=True),
        sa.Column(
            "owner_user_id",
            sa.BigInteger,
            sa.ForeignKey("users.id", ondelete="CASCADE"),
            nullable=False,
        ),
        sa.Column("title", sa.Text, nullable=False),
        sa.Column("description", sa.Text),
        sa.Column(
            "created_at",
            sa.DateTime(timezone=True),
            nullable=False,
            server_default=sa.text("now()"),
        ),
        sa.Column(
            "updated_at",
            sa.DateTime(timezone=True),
            nullable=False,
            server_default=sa.text("now()"),
        ),
    )
    op.create_index("ix_rulebooks_owner", "rulebooks", ["owner_user_id"])

    op.create_table(
        "rulebook_topics",
        sa.Column("id", sa.BigInteger, primary_key=True),
        sa.Column(
            "rulebook_id",
            sa.BigInteger,
            sa.ForeignKey("rulebooks.id", ondelete="CASCADE"),
            nullable=False,
        ),
        sa.Column("title", sa.Text, nullable=False),
        sa.Column("description", sa.Text),
        sa.Column(
            "order_index", sa.Integer, nullable=False, server_default="0",
        ),
        sa.Column(
            "created_at",
            sa.DateTime(timezone=True),
            nullable=False,
            server_default=sa.text("now()"),
        ),
        sa.Column(
            "updated_at",
            sa.DateTime(timezone=True),
            nullable=False,
            server_default=sa.text("now()"),
        ),
        sa.UniqueConstraint("rulebook_id", "title", name="uq_topic_per_rulebook"),
    )
    op.create_index(
        "ix_rulebook_topics_rulebook", "rulebook_topics", ["rulebook_id"],
    )

    op.create_table(
        "rules",
        sa.Column("id", sa.BigInteger, primary_key=True),
        sa.Column(
            "topic_id",
            sa.BigInteger,
            sa.ForeignKey("rulebook_topics.id", ondelete="CASCADE"),
            nullable=False,
        ),
        sa.Column("title", sa.Text, nullable=False),
        sa.Column("statement", sa.Text, nullable=False),
        sa.Column("why", sa.Text),
        sa.Column("how_to_apply", sa.Text),
        sa.Column(
            "order_index", sa.Integer, nullable=False, server_default="0",
        ),
        sa.Column(
            "created_at",
            sa.DateTime(timezone=True),
            nullable=False,
            server_default=sa.text("now()"),
        ),
        sa.Column(
            "updated_at",
            sa.DateTime(timezone=True),
            nullable=False,
            server_default=sa.text("now()"),
        ),
        sa.UniqueConstraint("topic_id", "title", name="uq_rule_per_topic"),
    )
    op.create_index("ix_rules_topic", "rules", ["topic_id"])

    op.create_table(
        "project_rulebook_subscriptions",
        sa.Column(
            "project_id",
            sa.BigInteger,
            sa.ForeignKey("projects.id", ondelete="CASCADE"),
            nullable=False,
        ),
        sa.Column(
            "rulebook_id",
            sa.BigInteger,
            sa.ForeignKey("rulebooks.id", ondelete="CASCADE"),
            nullable=False,
        ),
        sa.Column(
            "created_at",
            sa.DateTime(timezone=True),
            nullable=False,
            server_default=sa.text("now()"),
        ),
        sa.PrimaryKeyConstraint("project_id", "rulebook_id"),
    )
    op.create_index(
        "ix_project_rulebook_subs_rulebook",
        "project_rulebook_subscriptions",
        ["rulebook_id"],
    )


def downgrade() -> None:
    op.drop_index(
        "ix_project_rulebook_subs_rulebook",
        table_name="project_rulebook_subscriptions",
    )
    op.drop_table("project_rulebook_subscriptions")
    op.drop_index("ix_rules_topic", table_name="rules")
    op.drop_table("rules")
    op.drop_index("ix_rulebook_topics_rulebook", table_name="rulebook_topics")
    op.drop_table("rulebook_topics")
    op.drop_index("ix_rulebooks_owner", table_name="rulebooks")
    op.drop_table("rulebooks")
