"""retrieval_tuning_events — why a floor is where it is Revision ID: 0103 Revises: 0102 Create Date: 2026-09-17 Similarity thresholds are not values somebody has to defend: the model that reads the surface's own telemetry adjusts them, and the operator can still touch them. The number itself already has a home — the generic settings table. What has no home is the ARGUMENT, and once the values move on their own the argument is the part an operator needs: what changed, from what to what, who moved it, and on what evidence. This table is that trail, and it is what makes the delegation reviewable rather than merely automatic. Nothing is backfilled. A surface with no rows here is sitting on its shipped starting point, which is a true and useful thing for the history to say. """ import sqlalchemy as sa from alembic import op revision = "0103" down_revision = "0102" branch_labels = None depends_on = None def upgrade() -> None: op.create_table( "retrieval_tuning_events", sa.Column("id", sa.Integer(), primary_key=True), sa.Column( "created_at", sa.DateTime(timezone=True), server_default=sa.text("now()"), nullable=False, ), # FK-free, like retrieval_logs and app_logs: the record of why a number # is where it is must outlive the account that moved it. sa.Column("user_id", sa.Integer(), nullable=True), # Also the surface's `retrieval_logs.source`, so a change can be read # next to what the change did. sa.Column("surface", sa.Text(), nullable=False), sa.Column("dial", sa.Text(), nullable=False), # Nullable: the first change to a surface has no stored predecessor. It # moved off the shipped starting point, which is a different event from # moving off a value somebody chose. sa.Column("old_value", sa.Float(), nullable=True), sa.Column("new_value", sa.Float(), nullable=False), sa.Column( "actor", sa.Text(), nullable=False, server_default=sa.text("'model'") ), # Non-null here; non-BLANK is enforced at the service boundary, because # a column that merely forbids NULL is satisfied by "" and a required # field that accepts "" is a formality. sa.Column("reason", sa.Text(), nullable=False), ) # The only read this table has: one surface's history, newest first. op.create_index( "ix_retrieval_tuning_surface_created", "retrieval_tuning_events", ["surface", sa.text("created_at DESC")], ) def downgrade() -> None: op.drop_index( "ix_retrieval_tuning_surface_created", table_name="retrieval_tuning_events" ) op.drop_table("retrieval_tuning_events")