

-- ============================================================

-- SP_PrestacionesBonoImedManual

-- Retorna prestaciones con OrigenBono = 'Imed Manual' mas sus

-- registros de Copago asociados por IdCita.

-- Mismos parametros y columnas de salida que SP_PrestacionesBonoExterno.

--06-05-2026 se quitan los copagos

-- ============================================================

CREATE   PROCEDURE [Clinica].[SP_PrestacionesBonoImedManual]

    @FechaDesde         DATETIME,

    @FechaHasta         DATETIME,

    @IdProfesional      INT = NULL,

    @IdProfesionalOrden INT = NULL,

    @IdTipoPrestacion   VARCHAR(100) = NULL,

    @IdCaja             INT = NULL

AS

BEGIN

    SET NOCOUNT ON;



    -- CTE con metadata comun de cita (profesional, paciente, prestacion, etc.)

    -- Una fila por examen (cfee). nPrestaciones = total examenes de la cita (para dividir montos).

    ;WITH CitaBase AS (

        SELECT

            cita.IdCita,

            CASE WHEN profesional.IdTipoOrigenProfesional != 2 THEN profesional.IdProfesional

                 ELSE CASE WHEN cita.IdProfesionalExterno IS NOT NULL THEN cita.IdProfesionalExterno ELSE profesionalOrigen.IdProfesional END

            END AS IdProfesional,

            CASE WHEN profesional.IdTipoOrigenProfesional != 2 THEN profesional.Rut

                 ELSE CASE WHEN cita.IdProfesionalExterno IS NOT NULL THEN profesionalExterno.Rut ELSE profesionalOrigen.Rut END

            END AS RutProfesional,

            CASE WHEN profesional.IdTipoOrigenProfesional != 2 THEN profesional.Nombres+' '+profesional.Apellidos

                 ELSE CASE WHEN cita.IdProfesionalExterno IS NOT NULL THEN profesionalExterno.Nombres+' '+profesionalExterno.Apellidos ELSE profesionalOrigen.Nombres+' '+profesionalOrigen.Apellidos END

            END AS NombreProfesional,

            -- IdProfesionalOrden

            CASE WHEN (CASE WHEN prestacion.IdTipoPrestacion != 1 AND profesionalExterno.IdProfesional IS NULL THEN profesionalFichaEvolucion.IdProfesional WHEN profesionalExterno.IdProfesional IS NOT NULL THEN profesionalExterno.IdProfesional ELSE NULL END)

                    = (CASE WHEN profesional.IdTipoOrigenProfesional != 2 THEN profesional.IdProfesional ELSE CASE WHEN cita.IdProfesionalExterno IS NOT NULL THEN cita.IdProfesionalExterno ELSE profesionalOrigen.IdProfesional END END)

                 THEN NULL

                 ELSE CASE WHEN prestacion.IdTipoPrestacion != 1 AND profesionalExterno.IdProfesional IS NULL THEN profesionalFichaEvolucion.IdProfesional WHEN profesionalExterno.IdProfesional IS NOT NULL THEN profesionalExterno.IdProfesional ELSE NULL END

            END AS IdProfesionalOrden,

            -- RutProfesionalOrden

            CASE WHEN (CASE WHEN prestacion.IdTipoPrestacion != 1 AND profesionalExterno.IdProfesional IS NULL THEN profesionalFichaEvolucion.IdProfesional WHEN profesionalExterno.IdProfesional IS NOT NULL THEN profesionalExterno.IdProfesional ELSE NULL END)

                    = (CASE WHEN profesional.IdTipoOrigenProfesional != 2 THEN profesional.IdProfesional ELSE CASE WHEN cita.IdProfesionalExterno IS NOT NULL THEN cita.IdProfesionalExterno ELSE profesionalOrigen.IdProfesional END END)

                 THEN '-'

                 ELSE CASE WHEN prestacion.IdTipoPrestacion != 1 AND profesionalExterno.IdProfesional IS NULL THEN profesionalFichaEvolucion.Rut WHEN profesionalExterno.IdProfesional IS NOT NULL THEN profesionalExterno.Rut ELSE '-' END

            END AS RutProfesionalOrden,

            -- NombreProfesionalOrden

            CASE WHEN (CASE WHEN prestacion.IdTipoPrestacion != 1 AND profesionalExterno.IdProfesional IS NULL THEN profesionalFichaEvolucion.IdProfesional WHEN profesionalExterno.IdProfesional IS NOT NULL THEN profesionalExterno.IdProfesional ELSE NULL END)

                    = (CASE WHEN profesional.IdTipoOrigenProfesional != 2 THEN profesional.IdProfesional ELSE CASE WHEN cita.IdProfesionalExterno IS NOT NULL THEN cita.IdProfesionalExterno ELSE profesionalOrigen.IdProfesional END END)

                 THEN '-'

                 ELSE CASE WHEN prestacion.IdTipoPrestacion != 1 AND profesionalExterno.IdProfesional IS NULL THEN profesionalFichaEvolucion.Nombres+' '+profesionalFichaEvolucion.Apellidos WHEN profesionalExterno.IdProfesional IS NOT NULL THEN profesionalExterno.Nombres+' '+profesionalExterno.Apellidos ELSE '-' END

            END AS NombreProfesionalOrden,

            -- IdProfesionalOrden_Potencial

            CASE WHEN prestacion.IdTipoPrestacion != 1 AND profesionalExterno.IdProfesional IS NULL THEN profesionalFichaEvolucion.IdProfesional

                 WHEN profesionalExterno.IdProfesional IS NOT NULL THEN profesionalExterno.IdProfesional ELSE NULL

            END AS IdProfesionalOrden_Potencial,

            paciente.Rut AS RutPaciente,

            paciente.Nombres+' '+paciente.Apellidos AS NombrePaciente,

            CASE WHEN cfee.IdCitaFichaEvolucionExamen IS NOT NULL THEN prestacionExamen.CodigoInterno ELSE prestacion.CodigoInterno END AS CodigoPrestacion,

            CASE WHEN cfee.IdCitaFichaEvolucionExamen IS NOT NULL THEN prestacionExamen.Descripcion ELSE prestacion.Descripcion END AS NombrePrestacion,

            tp.IdTipoPrestacion,

            tp.Descripcion AS TipoPrestacion,

            CASE WHEN cfee.rn = 1 OR cfee.IdCitaFichaEvolucionExamen IS NULL THEN tmp.Descripcion ELSE 'Bono' END AS Modalidad,

            -- total de prestaciones para dividir montos del bono

            COUNT(*) OVER (PARTITION BY cita.IdCita) AS nPrestaciones

        FROM Clinica.Cita cita

        JOIN Clinica.Profesional profesional ON profesional.IdProfesional = cita.IdProfesional

        JOIN Clinica.Paciente paciente ON paciente.IdPaciente = cita.IdPaciente

        JOIN Clinica.Prestacion prestacion ON prestacion.IdPrestacion = cita.IdPrestacion

        JOIN Clinica.TipoPrestacion tp ON tp.IdTipoPrestacion = prestacion.IdTipoPrestacion

        JOIN Caja.TipoModalidadPago tmp ON tmp.IdTipoModalidadPago = 1  -- Bono

        LEFT JOIN (

            SELECT *, ROW_NUMBER() OVER (PARTITION BY IdCita ORDER BY IdCitaFichaEvolucionExamen) AS rn

            FROM Clinica.CitaFichaEvolucionExamen

        ) cfee ON cfee.IdCita = cita.IdCita

        LEFT JOIN Clinica.Prestacion prestacionExamen ON prestacionExamen.IdPrestacion = cfee.IdPrestacion

        LEFT JOIN Ficha.FichaEvolucion fe ON fe.IdFichaEvolucion = cfee.IdFichaEvolucion

        LEFT JOIN Clinica.Profesional profesionalOrigen ON profesionalOrigen.IdProfesional = fe.IdProfesional

        LEFT JOIN Clinica.Profesional profesionalFichaEvolucion ON fe.IdProfesional = profesionalFichaEvolucion.IdProfesional

        LEFT JOIN Clinica.Profesional profesionalExterno ON profesionalExterno.IdProfesional = cita.IdProfesionalExterno

        WHERE

            (@IdProfesional IS NULL OR

               CASE WHEN profesional.IdTipoOrigenProfesional != 2 THEN profesional.IdProfesional

                    ELSE CASE WHEN cita.IdProfesionalExterno IS NOT NULL THEN cita.IdProfesionalExterno ELSE profesionalOrigen.IdProfesional END

               END = @IdProfesional)

            AND (@IdTipoPrestacion IS NULL

               OR tp.IdTipoPrestacion IN (SELECT CAST(value AS INT) FROM STRING_SPLIT(@IdTipoPrestacion, ',')))

            AND (@IdProfesionalOrden IS NULL OR

               CASE WHEN (CASE WHEN prestacion.IdTipoPrestacion != 1 AND profesionalExterno.IdProfesional IS NULL THEN profesionalFichaEvolucion.IdProfesional WHEN profesionalExterno.IdProfesional IS NOT NULL THEN profesionalExterno.IdProfesional ELSE NULL END)

                       = (CASE WHEN profesional.IdTipoOrigenProfesional != 2 THEN profesional.IdProfesional ELSE CASE WHEN cita.IdProfesionalExterno IS NOT NULL THEN cita.IdProfesionalExterno ELSE profesionalOrigen.IdProfesional END END)

                    THEN NULL

                    ELSE CASE WHEN prestacion.IdTipoPrestacion != 1 AND profesionalExterno.IdProfesional IS NULL THEN profesionalFichaEvolucion.IdProfesional WHEN profesionalExterno.IdProfesional IS NOT NULL THEN profesionalExterno.IdProfesional ELSE NULL END

               END = @IdProfesionalOrden)

    )



    -- ==========================================================

    -- Bloque 1: Registro del bono Imed Manual (OrigenBono='Imed Manual', Monto=0)

    -- Muestra una fila por bono con el total de copago calculado

    -- a partir de los registros Copago vinculados por IdCita.

    -- ==========================================================

    SELECT

        mc.IdMovimientoCaja,

        CONVERT(VARCHAR, 'C-'+CONVERT(VARCHAR, mc.IdCita)) AS Identificador,

        cc.IdCaja,

        caja.Descripcion AS Caja,

        ec.IdTipoEstadoCaja,

        ec.Descripcion AS TipoEstadoCaja,

        '' AS RutCajero,

        usuario.LoginName AS NombreCajero,

        mc.FechaMovimiento,

        FORMAT(mc.FechaMovimiento, 'HH:mm') AS HoraMovimiento,

        cb.IdProfesional,

        mc.OrigenBono,

        cb.RutProfesional,

        cb.NombreProfesional,

        cb.IdProfesionalOrden_Potencial,

        cb.IdProfesionalOrden,

        cb.RutProfesionalOrden,

        cb.NombreProfesionalOrden,

        cb.RutPaciente,

        cb.NombrePaciente,

        cb.CodigoPrestacion,

        cb.NombrePrestacion,

        cb.IdTipoPrestacion,

        cb.TipoPrestacion,

        cb.Modalidad,

        sistemaSalud.Descripcion AS SistemaSalud,

        isapre.Descripcion AS Isapre,

        mc.NroBono,

        FORMAT(mc.FechaEmision,   'dd-MM-yyyy') AS FechaEmision,

        FORMAT(mc.FechaRecepcion, 'dd-MM-yyyy') AS FechaRecepcion,

        CAST(mc.TotalBono           / cb.nPrestaciones AS DECIMAL(18,2)) AS Valor,

        CAST(mc.MontoPagadoPrevision / cb.nPrestaciones AS DECIMAL(18,2)) AS MontoPagadoPrevision,

        -- MontoCopago dividido entre el numero de prestaciones del bono

        CAST(ISNULL((

            SELECT SUM(cp.Monto)

            FROM Caja.MovimientoCaja cp

            WHERE cp.IdCita = mc.IdCita

              AND cp.OrigenBono = 'Copago'

              AND cp.IdTipoEstadoMovimientoCaja IN (1, 3)

        ), mc.MontoCopago) / cb.nPrestaciones AS DECIMAL(18,2)) AS MontoCopago,

        CAST(mc.Seguros    / cb.nPrestaciones AS DECIMAL(18,2)) AS SeguroComplementario,

        CAST(mc.Excendentes / cb.nPrestaciones AS DECIMAL(18,2)) AS Excedentes,

        0                          AS TotalPagado,

        NULL                       AS IdTipoCopago,

        NULL                       AS TipoCopago

    FROM Caja.MovimientoCaja mc

    JOIN Caja.CicloCaja cc ON cc.IdCicloCaja = mc.IdCicloCaja

    JOIN Core.Usuario usuario ON usuario.IdUsuario = cc.IdUsuarioCajero

    JOIN Core.Contacto contacto ON contacto.IdContacto = usuario.IdContacto

    JOIN Caja.Caja caja ON caja.IdCaja = mc.IdCaja

    JOIN Caja.TipoEstadoCaja ec ON caja.IdTipoEstadoCaja = ec.IdTipoEstadoCaja

    JOIN CitaBase cb ON cb.IdCita = mc.IdCita

    LEFT JOIN Clinica.SistemaSalud sistemaSalud ON sistemaSalud.IdSistemaSalud = mc.SistemaSalud

    LEFT JOIN Clinica.Isapre isapre ON isapre.IdIsapre = mc.IdIsapre

    WHERE mc.OrigenBono = 'Imed Manual'

      AND mc.Monto = 0

      AND mc.IdPresupuesto IS NULL

      AND mc.IdTipoEstadoMovimientoCaja IN (1, 3)

      AND CAST(mc.FechaMovimiento AS DATE) BETWEEN CAST(@FechaDesde AS DATE) AND CAST(@FechaHasta AS DATE)

      AND (@IdCaja IS NULL OR mc.IdCaja = @IdCaja)





END


