"""exclui o cadastro antigo de impostos (Imposto, CenarioImposto e imposto_id)

Revision ID: f8b0d2e4a6c7
Revises: e7a9c1d3f5b6
Create Date: 2026-10-31 14:00:00.000000

O crédito passou a vir da classificação por item (`classificacao_credito`) e o débito da configuração de alíquotas (ICMS por destino, CBS e
IR/CSLL por vigência); o cadastro antigo (`imposto`, `cenario_imposto` e o `imposto_id` de gastos e insumo) saiu. A chave `imposto_id` também sai do
JSON do histórico. Só roda nos schemas de Planejamento (ver f1a9c3d7e284).
"""
import json
from typing import Sequence, Union

import sqlalchemy as sa
from alembic import op


# revision identifiers, used by Alembic.
revision: str = 'f8b0d2e4a6c7'
down_revision: Union[str, None] = 'e7a9c1d3f5b6'
branch_labels: Union[str, Sequence[str], None] = None
depends_on: Union[str, Sequence[str], None] = None

TABELAS_COM_IMPOSTO = ('ambiente_gasto', 'maquina_gasto', 'funcionario_gasto', 'insumo')


def _no_schema_comum() -> bool:
    contexto = op.get_context()
    return contexto.dialect.name == 'postgresql' and contexto.version_table_schema is None


def upgrade() -> None:
    if _no_schema_comum():
        return
    liga = op.get_bind()
    # a chave imposto_id sai dos valores guardados no histórico
    linhas = liga.execute(
        sa.text("select id, valores from historico_versao where entidade in :e").bindparams(sa.bindparam('e', expanding=True)),
        {'e': list(TABELAS_COM_IMPOSTO)},
    ).fetchall()
    for id_, valores in linhas:
        dados = valores if isinstance(valores, dict) else json.loads(valores)
        if 'imposto_id' in dados:
            dados.pop('imposto_id')
            liga.execute(sa.text('update historico_versao set valores = cast(:v as json) where id = :i'), {'v': json.dumps(dados), 'i': id_})
    op.drop_table('cenario_imposto')
    for tabela in TABELAS_COM_IMPOSTO:
        op.drop_column(tabela, 'imposto_id')
    op.drop_table('imposto')


def downgrade() -> None:
    if _no_schema_comum():
        return
    op.create_table(
        'imposto',
        sa.Column('id', sa.Integer(), primary_key=True),
        sa.Column('codigo', sa.String(20), nullable=False, unique=True),
        sa.Column('nome', sa.String(100), nullable=False),
        sa.Column('grupo', sa.String(20), nullable=False),
        sa.Column('aliquota_pct', sa.Numeric(6, 4), nullable=False),
        sa.CheckConstraint("grupo in ('federal_cbs', 'icms_ibs', 'ir_csll')", name='ck_imposto_grupo'),
    )
    for tabela in TABELAS_COM_IMPOSTO:
        op.add_column(tabela, sa.Column('imposto_id', sa.Integer(), nullable=True))
        op.create_foreign_key(f'{tabela}_imposto_id_fkey', tabela, 'imposto', ['imposto_id'], ['id'])
    op.create_table(
        'cenario_imposto',
        sa.Column('id', sa.Integer(), primary_key=True),
        sa.Column('cenario_id', sa.Integer(), sa.ForeignKey('cenario_precificacao.id'), nullable=False),
        sa.Column('imposto_id', sa.Integer(), sa.ForeignKey('imposto.id'), nullable=False),
        sa.Column('aliquota_pct', sa.Numeric(6, 4), nullable=False),
        sa.UniqueConstraint('cenario_id', 'imposto_id', name='uq_cenario_imposto'),
    )
