-- ============================================================================
-- INVENTORY EXTENSIONS - FASE 8 ERP-Core
-- ERP Clínicas (Base Genérica)
-- ============================================================================
-- Fecha: 2026-01-04
-- Versión: 1.0
-- ============================================================================

-- Schema
CREATE SCHEMA IF NOT EXISTS inventory;

-- ============================================================================
-- TABLAS
-- ============================================================================

-- Tipos de paquete
CREATE TABLE IF NOT EXISTS inventory.package_types (
    id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
    tenant_id UUID NOT NULL,
    name VARCHAR(100) NOT NULL,
    height NUMERIC(10,2),
    width NUMERIC(10,2),
    length NUMERIC(10,2),
    base_weight NUMERIC(10,2),
    max_weight NUMERIC(10,2),
    sequence INTEGER DEFAULT 10,
    created_at TIMESTAMPTZ DEFAULT NOW()
);

COMMENT ON TABLE inventory.package_types IS 'Tipos de paquete - FASE 8';

-- Paquetes
CREATE TABLE IF NOT EXISTS inventory.packages (
    id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
    tenant_id UUID NOT NULL,
    package_type_id UUID REFERENCES inventory.package_types(id),
    name VARCHAR(100),
    product_id UUID,
    -- Extensiones clínica (medicamentos)
    lote VARCHAR(50),
    fecha_fabricacion DATE,
    fecha_caducidad DATE,
    laboratorio VARCHAR(100),
    registro_sanitario VARCHAR(50),
    -- Control
    created_at TIMESTAMPTZ DEFAULT NOW(),
    updated_at TIMESTAMPTZ DEFAULT NOW()
);

COMMENT ON TABLE inventory.packages IS 'Paquetes/lotes de productos - FASE 8';
COMMENT ON COLUMN inventory.packages.lote IS 'Número de lote del fabricante';
COMMENT ON COLUMN inventory.packages.registro_sanitario IS 'Registro sanitario COFEPRIS';

-- Categorías de almacenamiento
CREATE TABLE IF NOT EXISTS inventory.storage_categories (
    id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
    tenant_id UUID NOT NULL,
    name VARCHAR(100) NOT NULL,
    max_weight NUMERIC(10,2),
    allow_new_product VARCHAR(20) DEFAULT 'mixed',
    -- Extensiones clínica
    requiere_refrigeracion BOOLEAN DEFAULT false,
    temperatura_min NUMERIC(5,2),
    temperatura_max NUMERIC(5,2),
    es_controlado BOOLEAN DEFAULT false,
    requiere_receta BOOLEAN DEFAULT false,
    -- Control
    created_at TIMESTAMPTZ DEFAULT NOW()
);

COMMENT ON TABLE inventory.storage_categories IS 'Categorías de almacenamiento - FASE 8';
COMMENT ON COLUMN inventory.storage_categories.es_controlado IS 'Medicamento controlado (requiere receta especial)';
COMMENT ON COLUMN inventory.storage_categories.requiere_refrigeracion IS 'Requiere cadena de frío';

-- Reglas de ubicación
CREATE TABLE IF NOT EXISTS inventory.putaway_rules (
    id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
    tenant_id UUID NOT NULL,
    name VARCHAR(100),
    product_id UUID,
    category_id UUID REFERENCES inventory.storage_categories(id),
    warehouse_id UUID,
    location_in_id UUID,
    location_out_id UUID,
    sequence INTEGER DEFAULT 10,
    active BOOLEAN DEFAULT true,
    created_at TIMESTAMPTZ DEFAULT NOW()
);

COMMENT ON TABLE inventory.putaway_rules IS 'Reglas de ubicación automática - FASE 8';

-- Estrategias de remoción
CREATE TABLE IF NOT EXISTS inventory.removal_strategies (
    id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
    code VARCHAR(20) NOT NULL UNIQUE,
    name VARCHAR(100) NOT NULL,
    description TEXT,
    created_at TIMESTAMPTZ DEFAULT NOW()
);

COMMENT ON TABLE inventory.removal_strategies IS 'Estrategias de remoción (FIFO, FEFO, etc.) - FASE 8';

-- ============================================================================
-- CAMPOS ADICIONALES A PRODUCTS (si existe)
-- ============================================================================

DO $$
BEGIN
    IF EXISTS (SELECT 1 FROM information_schema.tables
               WHERE table_schema = 'inventory' AND table_name = 'products') THEN

        -- tracking
        IF NOT EXISTS (SELECT 1 FROM information_schema.columns
                       WHERE table_schema = 'inventory' AND table_name = 'products'
                       AND column_name = 'tracking') THEN
            ALTER TABLE inventory.products ADD COLUMN tracking VARCHAR(20) DEFAULT 'none';
        END IF;

        -- removal_strategy_id
        IF NOT EXISTS (SELECT 1 FROM information_schema.columns
                       WHERE table_schema = 'inventory' AND table_name = 'products'
                       AND column_name = 'removal_strategy_id') THEN
            ALTER TABLE inventory.products ADD COLUMN removal_strategy_id UUID
                REFERENCES inventory.removal_strategies(id);
        END IF;

        -- sale_ok
        IF NOT EXISTS (SELECT 1 FROM information_schema.columns
                       WHERE table_schema = 'inventory' AND table_name = 'products'
                       AND column_name = 'sale_ok') THEN
            ALTER TABLE inventory.products ADD COLUMN sale_ok BOOLEAN DEFAULT true;
        END IF;

        -- purchase_ok
        IF NOT EXISTS (SELECT 1 FROM information_schema.columns
                       WHERE table_schema = 'inventory' AND table_name = 'products'
                       AND column_name = 'purchase_ok') THEN
            ALTER TABLE inventory.products ADD COLUMN purchase_ok BOOLEAN DEFAULT true;
        END IF;

    END IF;
END $$;

-- ============================================================================
-- ÍNDICES
-- ============================================================================

CREATE INDEX IF NOT EXISTS idx_package_types_tenant ON inventory.package_types(tenant_id);

CREATE INDEX IF NOT EXISTS idx_packages_tenant ON inventory.packages(tenant_id);
CREATE INDEX IF NOT EXISTS idx_packages_type ON inventory.packages(package_type_id);
CREATE INDEX IF NOT EXISTS idx_packages_lote ON inventory.packages(tenant_id, lote);
CREATE INDEX IF NOT EXISTS idx_packages_caducidad ON inventory.packages(tenant_id, fecha_caducidad);

CREATE INDEX IF NOT EXISTS idx_storage_categories_tenant ON inventory.storage_categories(tenant_id);
CREATE INDEX IF NOT EXISTS idx_storage_categories_controlado
    ON inventory.storage_categories(tenant_id, es_controlado) WHERE es_controlado = true;

CREATE INDEX IF NOT EXISTS idx_putaway_rules_tenant ON inventory.putaway_rules(tenant_id);
CREATE INDEX IF NOT EXISTS idx_putaway_rules_category ON inventory.putaway_rules(category_id);

-- ============================================================================
-- RLS
-- ============================================================================

ALTER TABLE inventory.package_types ENABLE ROW LEVEL SECURITY;
ALTER TABLE inventory.packages ENABLE ROW LEVEL SECURITY;
ALTER TABLE inventory.storage_categories ENABLE ROW LEVEL SECURITY;
ALTER TABLE inventory.putaway_rules ENABLE ROW LEVEL SECURITY;

DROP POLICY IF EXISTS tenant_isolation_package_types ON inventory.package_types;
CREATE POLICY tenant_isolation_package_types ON inventory.package_types
    USING (tenant_id = current_setting('app.current_tenant_id', true)::UUID);

DROP POLICY IF EXISTS tenant_isolation_packages ON inventory.packages;
CREATE POLICY tenant_isolation_packages ON inventory.packages
    USING (tenant_id = current_setting('app.current_tenant_id', true)::UUID);

DROP POLICY IF EXISTS tenant_isolation_storage_categories ON inventory.storage_categories;
CREATE POLICY tenant_isolation_storage_categories ON inventory.storage_categories
    USING (tenant_id = current_setting('app.current_tenant_id', true)::UUID);

DROP POLICY IF EXISTS tenant_isolation_putaway_rules ON inventory.putaway_rules;
CREATE POLICY tenant_isolation_putaway_rules ON inventory.putaway_rules
    USING (tenant_id = current_setting('app.current_tenant_id', true)::UUID);

-- ============================================================================
-- FIN INVENTORY EXTENSIONS
-- ============================================================================
