-- DDL Script para inicialização do banco de dados PostgreSQL
-- Para para.AI - Sistema de análise jurídica com IA

-- Criar extensões necessárias
CREATE EXTENSION IF NOT EXISTS "uuid-ossp";
CREATE EXTENSION IF NOT EXISTS "pg_trgm";

-- Tabela: Tribunais
CREATE TABLE IF NOT EXISTS tribunais (
    id VARCHAR(36) PRIMARY KEY,
    nome VARCHAR(255) NOT NULL UNIQUE,
    sigla VARCHAR(10) NOT NULL UNIQUE,
    uf VARCHAR(2) NOT NULL,
    tipo VARCHAR(50) NOT NULL,
    url_base VARCHAR(500),
    created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
    updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
    CONSTRAINT ck_tribunal_sigla_len CHECK (LENGTH(sigla) > 0),
    CONSTRAINT ck_tribunal_uf_len CHECK (LENGTH(uf) = 2)
);

CREATE INDEX IF NOT EXISTS idx_tribunal_sigla_uf ON tribunais(sigla, uf);

-- Tabela: Acórdãos
CREATE TABLE IF NOT EXISTS acordaos (
    id VARCHAR(36) PRIMARY KEY,
    tribunal_id VARCHAR(36) NOT NULL REFERENCES tribunais(id) ON DELETE CASCADE,
    numero VARCHAR(50) NOT NULL,
    ano INTEGER NOT NULL,
    data_julgamento TIMESTAMP NOT NULL,
    ementa TEXT NOT NULL,
    relator VARCHAR(255),
    orgao_julgador VARCHAR(255),
    url_original VARCHAR(500) UNIQUE,
    hash_conteudo VARCHAR(64) NOT NULL UNIQUE,
    status_processamento VARCHAR(20) DEFAULT 'pendente',
    created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
    updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
    CONSTRAINT uq_acordao_tribunal_numero_ano UNIQUE(tribunal_id, numero, ano)
);

CREATE INDEX IF NOT EXISTS idx_acordao_tribunal_id ON acordaos(tribunal_id);
CREATE INDEX IF NOT EXISTS idx_acordao_ano ON acordaos(ano);
CREATE INDEX IF NOT EXISTS idx_acordao_data_julgamento ON acordaos(data_julgamento);
CREATE INDEX IF NOT EXISTS idx_acordao_hash_conteudo ON acordaos(hash_conteudo);
CREATE INDEX IF NOT EXISTS idx_acordao_status_processamento ON acordaos(status_processamento);
CREATE INDEX IF NOT EXISTS idx_acordao_data_tribunal ON acordaos(data_julgamento, tribunal_id);
CREATE INDEX IF NOT EXISTS idx_acordao_ementa_trgm ON acordaos USING gin(ementa gin_trgm_ops);

-- Tabela: Decisões
CREATE TABLE IF NOT EXISTS decisoes (
    id VARCHAR(36) PRIMARY KEY,
    acordao_id VARCHAR(36) NOT NULL REFERENCES acordaos(id) ON DELETE CASCADE,
    tipo VARCHAR(50) NOT NULL,
    texto TEXT NOT NULL,
    confianca FLOAT DEFAULT 0.0,
    created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
);

CREATE INDEX IF NOT EXISTS idx_decisao_acordao_id ON decisoes(acordao_id);
CREATE INDEX IF NOT EXISTS idx_decisao_tipo ON decisoes(tipo);
CREATE INDEX IF NOT EXISTS idx_decisao_acordo_tipo ON decisoes(acordao_id, tipo);

-- Tabela: Palavras-chave
CREATE TABLE IF NOT EXISTS palavras_chave (
    id VARCHAR(36) PRIMARY KEY,
    termo VARCHAR(255) NOT NULL UNIQUE,
    categoria VARCHAR(100) NOT NULL,
    frequencia INTEGER DEFAULT 0,
    ativo BOOLEAN DEFAULT TRUE,
    created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
);

CREATE INDEX IF NOT EXISTS idx_palavra_chave_termo ON palavras_chave(termo);
CREATE INDEX IF NOT EXISTS idx_palavra_chave_categoria ON palavras_chave(categoria);

-- Tabela: Associação Acórdão-PalavraChave
CREATE TABLE IF NOT EXISTS acordao_palavras_chave (
    id VARCHAR(36) PRIMARY KEY,
    acordao_id VARCHAR(36) NOT NULL REFERENCES acordaos(id) ON DELETE CASCADE,
    palavra_chave_id VARCHAR(36) NOT NULL REFERENCES palavras_chave(id) ON DELETE CASCADE,
    relevancia FLOAT DEFAULT 0.0,
    created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
    CONSTRAINT uq_acordao_palavra UNIQUE(acordao_id, palavra_chave_id)
);

CREATE INDEX IF NOT EXISTS idx_acordao_palavras_chave_acordao ON acordao_palavras_chave(acordao_id);
CREATE INDEX IF NOT EXISTS idx_acordao_palavras_chave_palavra ON acordao_palavras_chave(palavra_chave_id);

-- Tabela: Embeddings
CREATE TABLE IF NOT EXISTS embeddings (
    id VARCHAR(36) PRIMARY KEY,
    acordao_id VARCHAR(36) NOT NULL REFERENCES acordaos(id) ON DELETE CASCADE,
    modelo VARCHAR(100) NOT NULL,
    tipo VARCHAR(50) NOT NULL,
    vetor TEXT NOT NULL,
    dimensoes INTEGER,
    created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
);

CREATE INDEX IF NOT EXISTS idx_embedding_acordao_id ON embeddings(acordao_id);
CREATE INDEX IF NOT EXISTS idx_embedding_modelo ON embeddings(modelo);
CREATE INDEX IF NOT EXISTS idx_embedding_acordo_modelo ON embeddings(acordao_id, modelo);

-- Tabela: Usuários
CREATE TABLE IF NOT EXISTS usuarios (
    id VARCHAR(36) PRIMARY KEY,
    email VARCHAR(255) NOT NULL UNIQUE,
    nome VARCHAR(255) NOT NULL,
    senha_hash VARCHAR(255) NOT NULL,
    ativo BOOLEAN DEFAULT TRUE,
    role VARCHAR(50) DEFAULT 'user',
    created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
    updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
);

CREATE INDEX IF NOT EXISTS idx_usuario_email ON usuarios(email);

-- Tabela: Buscas
CREATE TABLE IF NOT EXISTS buscas (
    id VARCHAR(36) PRIMARY KEY,
    usuario_id VARCHAR(36) NOT NULL REFERENCES usuarios(id) ON DELETE CASCADE,
    termo VARCHAR(500) NOT NULL,
    filtros TEXT,
    resultado_count INTEGER DEFAULT 0,
    tempo_execucao FLOAT,
    created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
);

CREATE INDEX IF NOT EXISTS idx_busca_usuario_id ON buscas(usuario_id);
CREATE INDEX IF NOT EXISTS idx_busca_usuario_data ON buscas(usuario_id, created_at);
CREATE INDEX IF NOT EXISTS idx_busca_created_at ON buscas(created_at);

-- Tabela: Processos Judiciais
CREATE TABLE IF NOT EXISTS processos_judiciais (
    id VARCHAR(36) PRIMARY KEY,
    numero_processo VARCHAR(50) NOT NULL UNIQUE,
    tribunal_id VARCHAR(36) NOT NULL REFERENCES tribunais(id) ON DELETE CASCADE,
    data_distribuicao TIMESTAMP NOT NULL,
    status VARCHAR(50) DEFAULT 'ativo',
    parte_ativa VARCHAR(255),
    parte_passiva VARCHAR(255),
    created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
    updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
);

CREATE INDEX IF NOT EXISTS idx_processo_numero ON processos_judiciais(numero_processo);
CREATE INDEX IF NOT EXISTS idx_processo_tribunal_id ON processos_judiciais(tribunal_id);
CREATE INDEX IF NOT EXISTS idx_processo_status ON processos_judiciais(status);

-- Tabela: Auditoria de Acessos
CREATE TABLE IF NOT EXISTS auditoria_acessos (
    id VARCHAR(36) PRIMARY KEY,
    usuario_id VARCHAR(36) REFERENCES usuarios(id) ON DELETE SET NULL,
    acao VARCHAR(100) NOT NULL,
    recurso VARCHAR(255),
    ip_address VARCHAR(45),
    status VARCHAR(20),
    created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
);

CREATE INDEX IF NOT EXISTS idx_auditoria_usuario_id ON auditoria_acessos(usuario_id);
CREATE INDEX IF NOT EXISTS idx_auditoria_created_at ON auditoria_acessos(created_at);
CREATE INDEX IF NOT EXISTS idx_auditoria_usuario_data ON auditoria_acessos(usuario_id, created_at);

-- Views úteis
CREATE OR REPLACE VIEW v_acordaos_por_tribunal AS
SELECT 
    t.sigla,
    t.nome,
    COUNT(a.id) as total_acordaos,
    COUNT(CASE WHEN a.status_processamento = 'processado' THEN 1 END) as processados,
    COUNT(CASE WHEN a.status_processamento = 'pendente' THEN 1 END) as pendentes
FROM tribunais t
LEFT JOIN acordaos a ON t.id = a.tribunal_id
GROUP BY t.id, t.sigla, t.nome;

CREATE OR REPLACE VIEW v_estatisticas_buscas AS
SELECT 
    DATE_TRUNC('day', b.created_at) as data,
    COUNT(*) as total_buscas,
    COUNT(DISTINCT b.usuario_id) as usuarios_unicos,
    AVG(b.tempo_execucao) as tempo_medio_ms
FROM buscas b
GROUP BY DATE_TRUNC('day', b.created_at);

-- Função para atualizar updated_at automaticamente
CREATE OR REPLACE FUNCTION update_updated_at_column()
RETURNS TRIGGER AS $$
BEGIN
    NEW.updated_at = CURRENT_TIMESTAMP;
    RETURN NEW;
END;
$$ LANGUAGE plpgsql;

-- Triggers para updated_at
CREATE TRIGGER tg_tribunais_updated_at BEFORE UPDATE ON tribunais
    FOR EACH ROW EXECUTE FUNCTION update_updated_at_column();

CREATE TRIGGER tg_acordaos_updated_at BEFORE UPDATE ON acordaos
    FOR EACH ROW EXECUTE FUNCTION update_updated_at_column();

CREATE TRIGGER tg_usuarios_updated_at BEFORE UPDATE ON usuarios
    FOR EACH ROW EXECUTE FUNCTION update_updated_at_column();

CREATE TRIGGER tg_processos_judiciais_updated_at BEFORE UPDATE ON processos_judiciais
    FOR EACH ROW EXECUTE FUNCTION update_updated_at_column();
