"""Cumplimiento PDF agente de carga: decisiones/costos en ops, envío/revisión en fin, continuidad comercial en crm (opportunity_id, contacto). Revision ID: d5e6f7a8b9c0 Revises: c4d5e6f7a8b9 Create Date: 2026-07-15 00:00:00.000000 """ from typing import Sequence, Union import sqlalchemy as sa from alembic import op revision: str = "d5e6f7a8b9c0" down_revision: Union[str, None] = "c4d5e6f7a8b9" branch_labels: Union[str, Sequence[str], None] = None depends_on: Union[str, Sequence[str], None] = None def upgrade() -> None: # ---------- ops.shipments: transporte terrestre, reprogramación y cierre operativo ---------- op.add_column("shipments", sa.Column("ground_carrier_supplier_id", sa.Integer(), nullable=True), schema="ops") op.add_column("shipments", sa.Column("pickup_at", sa.DateTime(), nullable=True), schema="ops") op.add_column("shipments", sa.Column("previous_etd", sa.Date(), nullable=True), schema="ops") op.add_column("shipments", sa.Column("actual_cost_total", sa.Numeric(precision=14, scale=2), nullable=True), schema="ops") op.add_column("shipments", sa.Column("cost_currency", sa.String(length=3), nullable=True), schema="ops") op.add_column("shipments", sa.Column("closed_at", sa.DateTime(), nullable=True), schema="ops") op.add_column("shipments", sa.Column("closed_by", sa.String(length=64), nullable=True), schema="ops") op.create_foreign_key( "fk_ops_shipments_ground_carrier_supplier_id", "shipments", "suppliers", ["ground_carrier_supplier_id"], ["id"], source_schema="ops", referent_schema="crm", ) # ---------- ops.shipment_events: puntos de decisión y ciclo de corrección ---------- op.add_column("shipment_events", sa.Column("kind", sa.String(length=20), nullable=False, server_default=sa.text("'hito'")), schema="ops") op.add_column("shipment_events", sa.Column("outcome", sa.String(length=20), nullable=True), schema="ops") op.add_column("shipment_events", sa.Column("parent_event_id", sa.Integer(), nullable=True), schema="ops") op.add_column("shipment_events", sa.Column("attempt", sa.Integer(), nullable=False, server_default=sa.text("1")), schema="ops") op.create_foreign_key( "fk_ops_shipment_events_parent_event_id", "shipment_events", "shipment_events", ["parent_event_id"], ["id"], source_schema="ops", referent_schema="ops", ) # ---------- fin.invoices: costos de operación, PDF y revisión del cliente ---------- op.add_column("invoices", sa.Column("ops_cost_total", sa.Numeric(precision=14, scale=2), nullable=True), schema="fin") op.add_column("invoices", sa.Column("pdf_file_key", sa.String(length=512), nullable=True), schema="fin") op.add_column("invoices", sa.Column("client_reviewed_at", sa.DateTime(), nullable=True), schema="fin") op.add_column("invoices", sa.Column("client_approved", sa.Boolean(), nullable=True), schema="fin") op.add_column("invoices", sa.Column("review_notes", sa.Text(), nullable=True), schema="fin") # ---------- crm.service_requests: continuidad comercial y contacto ---------- op.add_column("service_requests", sa.Column("opportunity_id", sa.Integer(), nullable=True), schema="crm") op.add_column("service_requests", sa.Column("first_contact_at", sa.DateTime(), nullable=True), schema="crm") op.add_column("service_requests", sa.Column("first_contact_notes", sa.Text(), nullable=True), schema="crm") op.create_index("ix_crm_service_requests_opportunity_id", "service_requests", ["opportunity_id"], schema="crm") op.create_foreign_key( "fk_crm_service_requests_opportunity_id", "service_requests", "opportunities", ["opportunity_id"], ["id"], source_schema="crm", referent_schema="crm", ) def downgrade() -> None: # crm.service_requests op.drop_constraint("fk_crm_service_requests_opportunity_id", "service_requests", schema="crm", type_="foreignkey") op.drop_index("ix_crm_service_requests_opportunity_id", table_name="service_requests", schema="crm") op.drop_column("service_requests", "first_contact_notes", schema="crm") op.drop_column("service_requests", "first_contact_at", schema="crm") op.drop_column("service_requests", "opportunity_id", schema="crm") # fin.invoices op.drop_column("invoices", "review_notes", schema="fin") op.drop_column("invoices", "client_approved", schema="fin") op.drop_column("invoices", "client_reviewed_at", schema="fin") op.drop_column("invoices", "pdf_file_key", schema="fin") op.drop_column("invoices", "ops_cost_total", schema="fin") # ops.shipment_events op.drop_constraint("fk_ops_shipment_events_parent_event_id", "shipment_events", schema="ops", type_="foreignkey") op.drop_column("shipment_events", "attempt", schema="ops") op.drop_column("shipment_events", "parent_event_id", schema="ops") op.drop_column("shipment_events", "outcome", schema="ops") op.drop_column("shipment_events", "kind", schema="ops") # ops.shipments op.drop_constraint("fk_ops_shipments_ground_carrier_supplier_id", "shipments", schema="ops", type_="foreignkey") op.drop_column("shipments", "closed_by", schema="ops") op.drop_column("shipments", "closed_at", schema="ops") op.drop_column("shipments", "cost_currency", schema="ops") op.drop_column("shipments", "actual_cost_total", schema="ops") op.drop_column("shipments", "previous_etd", schema="ops") op.drop_column("shipments", "pickup_at", schema="ops") op.drop_column("shipments", "ground_carrier_supplier_id", schema="ops")