Files
replypier/backend/alembic/versions/add_ticket_csat.py
T
WangShen007 977783c126 build: 打通 FastAPI 与 Vue 最小工程、依赖与数据库连接
后端入口、配置、Redis 与 Alembic 迁移就位;前端 Vite 工程可安装可构建。
2026-09-22 20:15:00 +08:00

44 lines
1.6 KiB
Python

"""CSAT score linkage on tickets
Revision ID: add_tkt_csat_001
Revises: add_tkt_row_scope_001
Create Date: 2026-07-22
The CSAT ask already goes out on close; nothing carried the answer back. These
columns close the loop: when the customer rates the conversation linked to a
ticket, the score lands on the ticket itself, so AI-resolved vs human-resolved
CSAT is a plain query instead of a join through ratings/sessions.
"""
from alembic import op
import sqlalchemy as sa
revision = "add_tkt_csat_001"
down_revision = "add_tkt_row_scope_001"
branch_labels = None
depends_on = None
def upgrade() -> None:
op.add_column("tickets", sa.Column("csat_requested_at", sa.DateTime(timezone=True), nullable=True))
op.add_column("tickets", sa.Column("csat_score", sa.Integer(), nullable=True))
op.add_column("tickets", sa.Column("csat_rating_id", sa.UUID(), nullable=True))
op.add_column("tickets", sa.Column("csat_responded_at", sa.DateTime(timezone=True), nullable=True))
op.create_foreign_key(
"fk_tickets_csat_rating_id",
"tickets",
"ratings",
["csat_rating_id"],
["id"],
ondelete="SET NULL",
)
op.create_index("ix_tickets_org_csat", "tickets", ["organization_id", "csat_responded_at"])
def downgrade() -> None:
op.drop_index("ix_tickets_org_csat", table_name="tickets")
op.drop_constraint("fk_tickets_csat_rating_id", "tickets", type_="foreignkey")
op.drop_column("tickets", "csat_responded_at")
op.drop_column("tickets", "csat_rating_id")
op.drop_column("tickets", "csat_score")
op.drop_column("tickets", "csat_requested_at")