CREATE OR REPLACE PROCEDURE FCT_APURAR_FATURAMENTO_LISTA (
    P_NRORG IN NUMBER,
    P_CDOPERINCLUSAO IN FCT_APURACAO.CDOPERINCLUSAO%TYPE,
    P_NRFATURACONT IN CLOB, 
    P_NRITFATURACONT IN VARCHAR2 DEFAULT NULL,
    P_NRRATEIOITEMVENC IN VARCHAR2 DEFAULT NULL)
AS
   V_NRAPURACAO         VARCHAR2(20);
   V_VRVENCIMENTO       FLOAT;
   V_EMPRESA            VARCHAR2(02);
   V_GRFATUR            NUMBER;
   V_TPOPERFAT          VARCHAR2(02);
   V_TPSERIENF          VARCHAR2(05);
   V_PRODFAT            VARCHAR2(30);
   V_NMITEMCONTRATO     VARCHAR2(60);
   V_NMPRODFAT          VARCHAR2(50);
   V_NRLANCTONF         VARCHAR2(10);
   V_CDCLIENTE          VARCHAR2(21);
   V_PRXLANCESTQ        VARCHAR2(10);
   V_TPORCA             NUMBER;
   VD_SERIE             VARCHAR2(05);
   V_RETORN             VARCHAR2(05);
   V_TESTAPUR           VARCHAR2(30);
   V_TESTAPUR2          VARCHAR2(30);
   V_APURA              FLOAT;
   V_DTEMISS            DATE;
   V_TPEMISSNF          VARCHAR2(01);
   V_DIAEMISSNF         VARCHAR2(02);
   V_DADOADIC           VARCHAR2(03);
   V_VENCIMENTO         DATE;
   V_DTINIREFFAT        DATE;
   V_DTFINREFFAT        DATE;
   V_NFCRIADA           VARCHAR2(3600);
   V_MEDPREVISTA        INTEGER;
   V_QTPRODNOTA         INTEGER;
   V_TESTAITEM          INTEGER;
   V_NRSEQIRPROD        VARCHAR2(4);
   V_FILIAL             VARCHAR2(4);
   V_VRCONTITEM         FLOAT;
   V_VRBRUTITEM         FLOAT;
   V_VRPERCRATEIO       FLOAT;
   V_VRRATEIO           FLOAT;
   V_COUNTRATEIO        INTEGER;
   V_VRNOTAFISC         FLOAT;
   V_VRFALTAFATURAR     FLOAT;
   V_IDSITUACAO         CHAR(1);
   V_DSSERVORCANF       VARCHAR2(4000);
   V_PARCELAS           VARCHAR2(30);
   V_NRLANCTONF_EXISTE  NOTAFISCAL.NRLANCTONF%TYPE;
   V_IDFATCONTJUNT      FCT_RELACAGRUPAMENTOCONT.IDFATCONTJUNT%TYPE;
   V_NRAPURACAOFATURA   FCT_RELACAPURACAOFATURA.NRAPURACAOFATURA%TYPE;
   V_APURACAOCONLUIDA   VARCHAR2(1);
   V_CDINSCESTA         VARCHAR2(16);
   V_CDINSCMUNI         VARCHAR2(16);
   V_EXISTE_SERIE       NUMBER;
   V_DSSERVORCABOL      VARCHAR2(4000);
   V_MEDVARIAVEIS       VARCHAR2(4000);
   V_IDGERARATEIO       VARCHAR2(1);
   V_VRVENCIMENTORATEIO FLOAT(126);
   V_DSTIPOAPURACAO     VARCHAR2(5);
   V_NRCONTRATOS        VARCHAR2(4000);
   V_TPCALCULODTSAIDA   NUMBER;
   V_NRCALCULODTSAIDA   NUMBER;
   V_DTREFEDTSAIDA      DATE;

   V_NRFATURACONT VARCHAR2(4000);
   V_POS_UNDER NUMBER;
   V_POSINI NUMBER;
   V_NOVOCODIGO VARCHAR2(20);
   V_LISTANF VARCHAR2(10);
   V_GEROUNOTA BOOLEAN;
   
   V_NR_ERRO FCT_CONTRATO.NRCONTRATOFCT%TYPE;
   V_MSGERRO VARCHAR2(4000);
   V_DATAATUAL DATE;
   V_DEUERRO BOOLEAN;
BEGIN
    /*
    ERROS
    -20001 - SEM_CLIENTE = Cliente para faturamento nao encontrado
    -20002 - FK_SERIENF = Serie de NF nao esta relacionada com a inscricao estadual e municipal da filial informada
    -20003 - PARC_MAIS_DE_UM_CLIENTE = Parceiro de negoicio relacionado a mais de 1 cliente
    */    
    V_NFCRIADA         := NULL;
    V_IDFATCONTJUNT    := NULL;
    V_APURACAOCONLUIDA := NULL;
    V_GEROUNOTA        := FALSE;
    V_DATAATUAL        := SYSDATE;
    V_DEUERRO          := FALSE;

    DELETE FROM FCT_ERROSAPURACAOFATURA
     WHERE CDOPERADOR = P_CDOPERINCLUSAO
       AND NRORG      = P_NRORG;

    NOVO_CODIGO_SC('LISTA', V_NOVOCODIGO, 1, P_NRORG);
    V_LISTANF := SUBSTR(V_NOVOCODIGO, -10);

    V_POSINI := 1;
    WHILE (V_POSINI < LENGTH(P_NRFATURACONT)) LOOP

        V_POS_UNDER := INSTR(P_NRFATURACONT, '_', V_POSINI + 3950);
        IF (V_POS_UNDER = 0) THEN
            V_POS_UNDER := LENGTH(P_NRFATURACONT);
        END IF;

        V_NRFATURACONT := SUBSTR(P_NRFATURACONT, V_POSINI, V_POS_UNDER-V_POSINI+1);

        /* Realiza a busca dos dados do Faturamento */
        FOR C_APUR IN (SELECT DISTINCT FCT_FATURACONT.NRFATURACONT, IDFATCONTJUNT, DECODE(IDPARCAGRUP, 'N', FCT_CONTRATO.NRCONTRATOFCT, 'AGRUPAMENTO DE CONTRATOS') AS NRCONTRATOFCT,
                             FCT_FATURACONT.NRGRUPOFATURA, FCT_FATURACONT.CDFILIALFATURA, FCT_FATURACONT.NRPARCFATURA, FCT_FATURACONT.IDTPFATURA,
                             FCT_FATURACONT.IDSITUACAO, FCT_FATURACONT.DTINICOMPET, FCT_FATURACONT.DTFINCOMPET, FCT_FATURACONT.DTLIMITEAPU,
                             FCT_FATURACONT.DTVENCIMENTO, FCT_FATURACONT.NRDIASVENCIMENTO, FCT_FATURACONT.QTDIASFATUVENC,
                             FCT_FATURACONT.CDTIPOOPERFATURA, FCT_FATURACONT.CDSERIENF,
                             NVL((SELECT SUM(VRVENCIMENTO) FROM FCT_ITFATURACONT WHERE NRSEQCONTRATO IN(SELECT NRSEQCONTRATO
                                  FROM FCT_RELACAGRUPAMENTOCONT WHERE NRAGRUPAMENTO = AGRUPCONT.NRAGRUPAMENTO
                                    AND IDFATCONTJUNT = AGRUPCONT.IDFATCONTJUNT)), FCT_FATURACONT.VRVENCIMENTO) AS VRVENCIMENTO, FCT_FATURACONT.VRFATURADO, FCT_FATURACONT.VRFALTAFATURAR, FCT_FATURACONT.IDFORMAFATURA, TO_CHAR(FCT_FATURACONT.DSJUSTIFICATIVA) AS DSJUSTIFICATIVA,
                             FCT_FATURACONT.NRAPURACAO, FCT_FATURACONT.NRMEDICAOFATURA, FCT_FATURACONT.IDATIVO, FCT_FATURACONT.NRORG, FCT_FATURACONT.VRNEGCONTR, FCT_FATURACONT.NRPARCELASNEGCONTR
                        FROM FCT_FATURACONT
                        INNER JOIN FCT_RELACAGRUPCONTFAT AGRUPFAT
                          ON AGRUPFAT.NRFATURACONT = FCT_FATURACONT.NRFATURACONT
                          AND AGRUPFAT.NRORG       = FCT_FATURACONT.NRORG
                        LEFT JOIN FCT_RELACAGRUPAMENTOCONT AGRUPCONT
                          ON AGRUPFAT.NRSEQCONTRATO = AGRUPCONT.NRSEQCONTRATO
                          AND AGRUPFAT.NRORG       = AGRUPCONT.NRORG
                        JOIN FCT_CONTRATO
                          ON FCT_CONTRATO.NRSEQCONTRATO = AGRUPFAT.NRSEQCONTRATO
                         AND FCT_CONTRATO.NRORG         = AGRUPFAT.NRORG
                       WHERE (FCT_FATURACONT.NRORG = P_NRORG)
                         AND ((INSTR(V_NRFATURACONT, '_' || TO_CHAR(FCT_FATURACONT.NRFATURACONT) || '_') > 0) OR (V_NRFATURACONT IS NULL))
        ) LOOP

            BEGIN --tratamento de erro

                V_GEROUNOTA := FALSE;
                V_APURACAOCONLUIDA := NULL;
                V_NR_ERRO := C_APUR.NRCONTRATOFCT;
                V_MSGERRO := NULL;

                IF (C_APUR.IDSITUACAO NOT IN ('1', '6')) THEN
                    V_DEUERRO := TRUE;
                    V_MSGERRO := 'So e permitido apurar parcelas com situacao "Pendente".';
                    
                    INSERT INTO FCT_ERROSAPURACAOFATURA (
                        NRFATURACONT,           DSERRO,          CDOPERADOR,
                        DTINCLUSAO,             NRORG
                    )
                    VALUES (
                        C_APUR.NRFATURACONT,    V_MSGERRO,       P_CDOPERINCLUSAO,
                        V_DATAATUAL,            P_NRORG
                    );

                    CONTINUE;
                END IF;
            
                IF (NVL(C_APUR.VRNEGCONTR, C_APUR.VRVENCIMENTO) = 0) THEN 
                    
                    UPDATE FCT_FATURACONT
                    SET IDSITUACAO = '3',
                        CDOPERULTATU   = P_CDOPERINCLUSAO,
                        DTULTATU       = SYSDATE,
                        NRORGULTATU    = P_NRORG
                    WHERE NRFATURACONT = C_APUR.NRFATURACONT
                        AND NRORG      = C_APUR.NRORG;

                    UPDATE FCT_ITFATURACONT
                    SET IDSITUACAO = '3',
                        CDOPERULTATU   = P_CDOPERINCLUSAO,
                        DTULTATU       = SYSDATE,
                        NRORGULTATU    = P_NRORG
                    WHERE NRFATURACONT = C_APUR.NRFATURACONT
                        AND NRORG      = C_APUR.NRORG;

                    UPDATE FCT_RATEIOITFATURACONT
                    SET IDSITUVENCRATEIO = '3',
                        CDOPERULTATU   = P_CDOPERINCLUSAO,
                        DTULTATU       = SYSDATE,
                        NRORGULTATU    = P_NRORG
                    WHERE NRFATURACONT = C_APUR.NRFATURACONT
                        AND NRORG      = C_APUR.NRORG;

                ELSE 
                    /*Preenche Filial*/
                    V_FILIAL    := C_APUR.CDFILIALFATURA;
                    V_TPOPERFAT := C_APUR.CDTIPOOPERFATURA;
                    V_TPSERIENF := C_APUR.CDSERIENF;

                    /* Recebe empresa para faturamento */
                    SELECT CDEMPRESA
                      INTO V_EMPRESA
                      FROM FILIAL
                     WHERE CDFILIAL = V_FILIAL
                       AND NRORG = P_NRORG;

                    /* Recebe codigo do cliente */
                    BEGIN
                        SELECT CL.CDCLIENTE
                          INTO V_CDCLIENTE
                          FROM PARCNEGOCIO PN, CLIENTE CL
                         WHERE PN.NRPARCNEGOCIO = C_APUR.NRPARCFATURA
                           AND PN.NRORG = P_NRORG
                           AND CL.NRPARCNEGOCIO = PN.NRPARCNEGOCIO
                           AND CL.NRORG = PN.NRORG
                           AND CL.IDCLIEATIV = 'S';
                    EXCEPTION 
                       WHEN NO_DATA_FOUND THEN
                          RAISE_APPLICATION_ERROR('-20001', 'SEM_CLIENTE##'||V_NR_ERRO||'##');
                       WHEN TOO_MANY_ROWS THEN
                          RAISE_APPLICATION_ERROR('-20003', 'PARC_MAIS_DE_UM_CLIENTE##'||V_NR_ERRO||'##');
                    END;

                    /* ----- Recebe a data de saida da NF ----- */
                    V_TPCALCULODTSAIDA := 1;
                    V_NRCALCULODTSAIDA := 0;
                    FOR C_PARAMDTSAIDA IN (
                        SELECT COUNT(*) AS QTESCOPOSDIF,
                               IDTPCALCDTSAIDANF,
                               NRCALCULODTSAIDANF
                          FROM (
                               SELECT DISTINCT NVL(IDTPCALCDTSAIDANF, 1) AS IDTPCALCDTSAIDANF, 
                                      NVL(NRCALCULODTSAIDANF, 0) AS NRCALCULODTSAIDANF
                                 FROM FCT_CAPAPARAMFATESC ESCOPO
                                INNER JOIN (
                                  SELECT DISTINCT CONT.NRORG, 
                                      NVL(CONT.NRTIPOORCAMENTO, REFE.NRTIPOORCAMENTO) AS NRTIPOORCAMENTO
                                    FROM FCT_CONTRATO CONT
                                    LEFT JOIN FCT_REFEORCACONT REFE
                                      ON CONT.NRSEQCONTRATO = REFE.NRSEQCONTRATO
                                     AND CONT.NRORG         = REFE.NRORG
                                    JOIN FCT_RELACAGRUPCONTFAT CONTFAT
                                      ON CONT.NRSEQCONTRATO = CONTFAT.NRSEQCONTRATO
                                     AND CONT.NRORG         = CONTFAT.NRORG
                                  WHERE CONTFAT.NRFATURACONT = C_APUR.NRFATURACONT
                                      AND CONT.NRORG         = P_NRORG
                                ) ESCOPOCONT
                                  ON ESCOPO.NRTIPOORCAMENTO = ESCOPOCONT.NRTIPOORCAMENTO
                                  AND ESCOPO.NRORG          = ESCOPOCONT.NRORG
                          )
                          GROUP BY IDTPCALCDTSAIDANF,
                                   NRCALCULODTSAIDANF
                    ) LOOP

                        IF(C_PARAMDTSAIDA.QTESCOPOSDIF > 1) THEN
                            V_TPCALCULODTSAIDA := 1;
                            V_NRCALCULODTSAIDA := 0;
                        ELSE
                            V_TPCALCULODTSAIDA := C_PARAMDTSAIDA.IDTPCALCDTSAIDANF;
                            V_NRCALCULODTSAIDA := C_PARAMDTSAIDA.NRCALCULODTSAIDANF;
                        END IF;

                    END LOOP; -- C_PARAMDTSAIDA

                    IF (V_TPCALCULODTSAIDA = 1) THEN 
                        V_DTEMISS := TRUNC(SYSDATE);
                    ELSE 
                        IF (V_TPCALCULODTSAIDA = 2 OR V_TPCALCULODTSAIDA = 3) THEN
                            IF V_TPCALCULODTSAIDA = 2 THEN
                                V_DTREFEDTSAIDA := C_APUR.DTFINCOMPET;
                            ELSE 
                                V_DTREFEDTSAIDA := SYSDATE;
                            END IF;

                            V_DTEMISS := TO_DATE(LPAD(V_NRCALCULODTSAIDA, 2, '0') || '/' || TO_CHAR(V_DTREFEDTSAIDA, 'MM/YYYY'), 'DD/MM/YYYY');

                            IF V_NRCALCULODTSAIDA < TO_CHAR(V_DTREFEDTSAIDA, 'DD') THEN
                                V_DTEMISS := ADD_MONTHS(V_DTEMISS, 1);
                            END IF;

                            V_DTEMISS := TRUNC(V_DTEMISS);
                        ELSE 
                            IF V_TPCALCULODTSAIDA = 4 THEN
                                V_DTEMISS := TRUNC(C_APUR.DTFINCOMPET + V_NRCALCULODTSAIDA);
                            ELSE 
                                V_DTEMISS := TRUNC(SYSDATE + V_NRCALCULODTSAIDA);
                            END IF;
                        END IF;
                    END IF;

                    /* INICIO: verificacao da serie da nota de acordo com a empresa e filial */
                    SELECT MAX(F.CDINSCESTA), MAX(F.CDINSCMUNI)
                      INTO V_CDINSCESTA, V_CDINSCMUNI
                      FROM FILIAL F, INSCRESTAD I
                     WHERE (F.CDFILIAL   = C_APUR.CDFILIALFATURA)
                       AND (F.CDEMPRESA  = V_EMPRESA)
                       AND (I.CDINSCESTA = F.CDINSCESTA)
                       AND (I.CDEMPRESA  = F.CDEMPRESA)
                       AND (NVL(V_DTEMISS, TRUNC(SYSDATE)) >= NVL(NVL(I.DTINIVIGIEST, V_DTEMISS), TRUNC(SYSDATE)))
                       AND (NVL(V_DTEMISS, TRUNC(SYSDATE)) <= NVL(NVL(I.DTFIMVIGIEST, V_DTEMISS), TRUNC(SYSDATE)));

                    IF (V_CDINSCESTA IS NULL) OR (V_CDINSCMUNI IS NULL) THEN
                       SELECT MAX(E.CDINSCESTA), MAX(E.CDINSCMUNI)
                         INTO V_CDINSCESTA, V_CDINSCMUNI
                         FROM EMPRCNTRFIL E, INSCRESTAD I
                        WHERE (E.CDFILIAL  = C_APUR.CDFILIALFATURA)
                          AND (E.CDEMPRESA = V_EMPRESA)
                          AND (E.CDINSCESTA = I.CDINSCESTA)
                          AND (E.CDEMPRESA  = I.CDEMPRESA)
                          AND (NVL(V_DTEMISS, TRUNC(SYSDATE)) >= NVL(NVL(I.DTINIVIGIEST, V_DTEMISS), TRUNC(SYSDATE)))
                          AND (NVL(V_DTEMISS, TRUNC(SYSDATE)) <= NVL(NVL(I.DTFIMVIGIEST, V_DTEMISS), TRUNC(SYSDATE)));
                    END IF;

                    IF (V_CDINSCESTA IS NULL) OR (V_CDINSCMUNI IS NULL) THEN
                       SELECT MAX(CDINSCESTA), MAX(CDINSCMUNI)
                         INTO V_CDINSCESTA, V_CDINSCMUNI
                         FROM FILIAL
                        WHERE (CDFILIAL  = C_APUR.CDFILIALFATURA)
                          AND (CDEMPRESA = V_EMPRESA);
                    END IF;

                    IF (V_CDINSCESTA IS NULL) OR (V_CDINSCMUNI IS NULL) THEN
                        RAISE_APPLICATION_ERROR('-20002', 'FK_SERIENF##'||V_NR_ERRO||'##');
                    ELSE
                        SELECT COUNT(*)
                          INTO V_EXISTE_SERIE
                          FROM SERIENF
                         WHERE CDEMPRESA  = V_EMPRESA
                           AND CDINSCESTA = V_CDINSCESTA
                           AND CDINSCMUNI = V_CDINSCMUNI
                           AND CDSERIE    = V_TPSERIENF;
                        IF (V_EXISTE_SERIE = 0) THEN
                            RAISE_APPLICATION_ERROR('-20002', 'FK_SERIENF##'||V_NR_ERRO||'##');
                        END IF;
                    END IF;
                    /* FIM: verificacao da serie da nota de acordo com a empresa e filial */
                    
                    /* Busca as NFs em digitacao relacionadas a essa parcela para excluir. Essas NFs so devem existir
                    se a rotina rodou anteriormente e deu algum erro no meio, nao chamando a procedure de cancelar
                    a apuracao para desfazer o processo. */
                    FOR C_NF_DIGIT IN (
                        SELECT NF.NRLANCTONF, NF.CDFILIAL
                          FROM FCT_RELACAPURACAOFATURA RA
                          JOIN FCT_APURACAO AP
                            ON RA.NRAPURACAO = AP.NRAPURACAO
                           AND RA.NRORG      = AP.NRORG
                          JOIN NOTAFISCAL NF
                            ON AP.NRLANCTONF = NF.NRLANCTONF
                           AND AP.CDFILIAL   = NF.CDFILIAL
                         WHERE NF.IDSTATUS     = 'D'
                           AND RA.NRFATURACONT = C_APUR.NRFATURACONT
                           AND RA.NRORG        = P_NRORG
                    ) LOOP
                        DELETA_NF(C_NF_DIGIT.CDFILIAL, C_NF_DIGIT.NRLANCTONF);
                    END LOOP;
                    
                    /* Geracao do CORPO da nota fiscal da apuracao*/
                    GERA_NOTAFISCAL_CORPO(C_APUR.CDFILIALFATURA, C_APUR.CDFILIALFATURA, V_EMPRESA, V_TPOPERFAT, V_TPSERIENF, V_CDCLIENTE, V_DTEMISS,'DFS', V_NRLANCTONF, V_PRXLANCESTQ);
                    IF (V_NRLANCTONF IS NOT NULL) THEN
                        --ALTERAR
                        FCT_PREENCHE_DADOS_NOTAFISC(P_NRORG, C_APUR.CDFILIALFATURA, V_NRLANCTONF, C_APUR.NRFATURACONT, P_CDOPERINCLUSAO);
                        --V_NFCRIADA := V_NFCRIADA||'_'||V_NRLANCTONF||'_';
                        V_GEROUNOTA := TRUE;

                        UPDATE NOTAFISCAL
                           SET IDSTATUS = 'D'
                         WHERE NRLANCTONF = V_NRLANCTONF
                           AND CDFILIAL = C_APUR.CDFILIALFATURA;

                        BEGIN
                           INSERT INTO LISTA (
                               NRLISTA,
                               CDLISTA,
                               NRORG,
                               DTINCLUSAO,
                               NRORGINCLUSAO,
                               CDOPERINCLUSAO,
                               IDATIVO
                           )
                           VALUES (
                               V_LISTANF,
                               V_NRLANCTONF || '_' || C_APUR.CDFILIALFATURA,
                               P_NRORG,
                               SYSDATE,
                               P_NRORG,
                               P_CDOPERINCLUSAO,
                               'S'
                           );
                        EXCEPTION
                           WHEN OTHERS THEN NULL;
                        END;

                    END IF;
                    /* Insercao dos itens na nota fical */
                    FOR C_ITENS IN (SELECT IT.NRITFATURACONT,
                                     IT.NRFATURACONT,
                                     IT.NRSEQCONTRATO,
                                     IT.NRITEMOCONTRATO,
                                     IT.CDPRODFATURA,
                                     PRODUTO.NMPRODUTO,
                                     IT.IDSITUACAO,
                                     1 AS QUANTIDADE,
                                     NVL(IT.VRNEGCONTR, IT.VRVENCIMENTO) AS VRVENCIMENTO,
                                     IT.VRNEGCONTR,
                                     IT.VRFATURADO,
                                     IT.VRFALTAFATURAR,
                                     IT.IDFORMAFATURA,
                                     IT.DSJUSTIFICATIVA,
                                     IT.NRAPURACAO,
                                     IT.IDATIVO,
                                     IT.NRORG
                                FROM FCT_ITFATURACONT IT
                                LEFT JOIN FCT_RELACAGRUPAMENTOCONT AGRUP
                                  ON IT.NRSEQCONTRATO = AGRUP.NRSEQCONTRATO
                                  AND IT.NRORG        = AGRUP.NRORG
                                JOIN PRODUTO
                                  ON IT.CDPRODFATURA = PRODUTO.CDPRODUTO
                                 AND IT.NRORG        = PRODUTO.NRORG
                               WHERE (AGRUP.IDFATCONTJUNT          = C_APUR.IDFATCONTJUNT
                                      OR C_APUR.IDFATCONTJUNT      IS NULL)
                                 AND IT.NRFATURACONT = C_APUR.NRFATURACONT
                                 AND IT.NRORG        = P_NRORG
                                 AND ((P_NRITFATURACONT IS NULL AND P_NRRATEIOITEMVENC IS NULL)
                                      OR (P_NRRATEIOITEMVENC IS NULL AND (INSTR(P_NRITFATURACONT, '_' || TO_CHAR(NRITFATURACONT) || '_') > 0))
                                      OR (P_NRITFATURACONT IS NULL AND IT.NRITFATURACONT IN (SELECT NRITFATURACONT
                                                                                                           FROM FCT_RATEIOITFATURACONT
                                                                                                           WHERE ((INSTR(P_NRRATEIOITEMVENC, '_' || TO_CHAR(NRRATEIOITEMFAT) || '_') > 0)))))
                    ) LOOP
                        SELECT COUNT(*)
                          INTO V_QTPRODNOTA
                          FROM ITEMPRODUTO
                         WHERE NRLANCTONF = V_NRLANCTONF
                           AND CDFILIAL   = C_APUR.CDFILIALFATURA
                           AND CDPRODUTO  = C_ITENS.CDPRODFATURA;

                        V_VRVENCIMENTORATEIO := ROUND(C_ITENS.VRVENCIMENTO, 2);

                        IF (P_NRRATEIOITEMVENC IS NOT NULL) THEN
                            BEGIN 
                                SELECT ROUND(SUM(VRRATEADO), 2)
                                INTO V_VRVENCIMENTORATEIO
                                FROM FCT_RATEIOITFATURACONT
                                WHERE NRITFATURACONT = C_ITENS.NRITFATURACONT
                                  AND (INSTR(P_NRRATEIOITEMVENC, '_' || TO_CHAR(NRRATEIOITEMFAT) || '_') > 0);
                            EXCEPTION WHEN NO_DATA_FOUND THEN 
                                V_VRVENCIMENTORATEIO := ROUND(C_ITENS.VRVENCIMENTO, 2);
                            END;
                        END IF;

                        IF (V_QTPRODNOTA = 0) THEN
                           GERA_NOTAFISCAL_PRODUTO(C_APUR.CDFILIALFATURA, V_NRLANCTONF, C_ITENS.CDPRODFATURA, C_ITENS.CDPRODFATURA, C_ITENS.NMPRODUTO, C_ITENS.QUANTIDADE, V_VRVENCIMENTORATEIO);
                        ELSE
                            UPDATE ITEMPRODUTO
                               SET VRUNITITEM = ROUND(VRUNITITEM + V_VRVENCIMENTORATEIO, 2), 
                                   VRTOTAITEM = ROUND(VRTOTAITEM + V_VRVENCIMENTORATEIO, 2)
                             WHERE NRLANCTONF = V_NRLANCTONF
                               AND CDFILIAL   = C_APUR.CDFILIALFATURA
                               AND CDPRODUTO  = C_ITENS.CDPRODFATURA;
                        END IF;

                        /* Caso o item tenha rateio, serao criados os rateios na Nota Fiscal */
                        FOR C_RATEIO IN (
                            SELECT NRITFATURACONT, NRFATURACONT, NRSEQCONTRATO,
                                   NRESTRUTURAM, CDCENTCUST, VRRATEADO
                              FROM FCT_RATEIOITFATURACONT RAT
                             WHERE RAT.NRFATURACONT       = C_APUR.NRFATURACONT
                               AND RAT.NRSEQCONTRATO    = C_ITENS.NRSEQCONTRATO
                               AND RAT.NRITFATURACONT   = C_ITENS.NRITFATURACONT
                               AND RAT.IDSITUVENCRATEIO IN('1', '6')
                               AND (P_NRRATEIOITEMVENC IS NULL OR INSTR(P_NRRATEIOITEMVENC, '_' || TO_CHAR(NRRATEIOITEMFAT) || '_') > 0)
                        ) LOOP
                            -- Busca o numero do item na Nota Fiscal
                            SELECT NRSEQITPROD
                              INTO V_NRSEQIRPROD
                              FROM ITEMPRODUTO
                             WHERE NRLANCTONF = V_NRLANCTONF
                               AND CDFILIAL   = C_APUR.CDFILIALFATURA
                               AND CDPRODUTO  = C_ITENS.CDPRODFATURA;

                            SELECT COUNT(*)
                              INTO V_COUNTRATEIO
                              FROM RATEIONF
                             WHERE NRLANCTONF  = V_NRLANCTONF
                               AND CDFILIAL    = C_APUR.CDFILIALFATURA
                               AND NRSEQITPROD = V_NRSEQIRPROD
                               AND CDFILICCUST = C_APUR.CDFILIALFATURA
                               AND CDCENTCUSNF = C_RATEIO.CDCENTCUST
                               AND NRORG       = P_NRORG;

                            IF V_COUNTRATEIO = 0 THEN
                                INSERT INTO RATEIONF(
                                    CDFILIAL, NRLANCTONF, NRSEQITPROD, CDFILICCUST, CDCENTCUSNF,
                                    VRRATENF, NRORG,      DTINCLUSAO,  IDATIVO
                                ) VALUES(
                                    C_APUR.CDFILIALFATURA, V_NRLANCTONF, V_NRSEQIRPROD, C_APUR.CDFILIALFATURA, C_RATEIO.CDCENTCUST,
                                    ROUND(C_RATEIO.VRRATEADO, 2),    P_NRORG,      SYSDATE,       'S'
                                );
                            ELSE
                               UPDATE RATEIONF
                                  SET VRRATENF = ROUND(VRRATENF + C_RATEIO.VRRATEADO, 2)
                                WHERE NRLANCTONF  = V_NRLANCTONF
                                  AND NRSEQITPROD = V_NRSEQIRPROD
                                  AND CDFILIAL    = C_APUR.CDFILIALFATURA
                                  AND CDFILICCUST = C_APUR.CDFILIALFATURA
                                  AND CDCENTCUSNF = C_RATEIO.CDCENTCUST
                                  AND NRORG       = P_NRORG;
                            END IF;

                            IF ROUND(C_ITENS.VRFATURADO + C_RATEIO.VRRATEADO, 2) = ROUND(C_ITENS.VRVENCIMENTO, 2) THEN
                                V_IDSITUACAO := '2';
                            ELSE 
                                V_IDSITUACAO := '6';
                            END IF;

                            UPDATE FCT_ITFATURACONT
                               SET IDSITUACAO     = V_IDSITUACAO,
                                   VRFATURADO     = ROUND(VRFATURADO     + C_RATEIO.VRRATEADO, 2),
                                   VRFALTAFATURAR = ROUND(VRFALTAFATURAR - C_RATEIO.VRRATEADO, 2) 
                             WHERE NRORG          = P_NRORG
                               AND NRFATURACONT   = C_APUR.NRFATURACONT
                               AND NRITFATURACONT = C_RATEIO.NRITFATURACONT 
                               AND (IDSITUACAO = '1' OR IDSITUACAO = '6');

                            FOR C_RATITENS IN (
                                SELECT NRESTRUTURAM, 
                                       ROUND(SUM(VRRATEADO), 2) AS VRRATEADO
                                  FROM FCT_RATEIOITFATURACONT
                                 WHERE NRFATURACONT  = C_APUR.NRFATURACONT
                                   AND NRSEQCONTRATO = C_ITENS.NRSEQCONTRATO
                                   AND NRESTRUTURAM  = C_RATEIO.NRESTRUTURAM
                                 GROUP BY NRESTRUTURAM
                            ) LOOP 
                                IF ROUND(C_RATITENS.VRRATEADO, 2) = ROUND(C_RATEIO.VRRATEADO, 2) THEN
                                    V_IDSITUACAO := '2';
                                ELSE 
                                    V_IDSITUACAO := '6';
                                END IF;
                                UPDATE FCT_RATEIOITFATURACONT
                                   SET IDSITUVENCRATEIO = V_IDSITUACAO
                                 WHERE NRORG        = P_NRORG
                                   AND NRFATURACONT = C_APUR.NRFATURACONT
                                   AND NRESTRUTURAM = C_RATITENS.NRESTRUTURAM;
                            END LOOP; -- C_RATITENS
                        END LOOP; --C_RATEIO

                    END LOOP;  -- C_ITENS

                    /* ====== Abaixo ele testa se a nota fiscal possui algum item, se ela nao possuir ele deleta a nota fiscal e ignora o resto da rotina.
                             Se ela possuir, ele continua a rotina normalmente. */
                    SELECT COUNT(*)
                      INTO V_TESTAITEM
                      FROM ITEMPRODUTO
                     WHERE NRLANCTONF = V_NRLANCTONF
                       AND CDFILIAL   = C_APUR.CDFILIALFATURA
                       AND NRORG      = P_NRORG;

                    IF V_TESTAITEM = 0 THEN
                        DELETE FROM NOTAFISCAL
                         WHERE NRLANCTONF = V_NRLANCTONF
                           AND CDFILIAL = C_APUR.CDFILIALFATURA
                           AND NRORG    = P_NRORG;
                    ELSE
                      /* UPDATA DATAS DE COMPETENCIA DE FATURAMENTO NA NF */
                      UPDATE NOTAFISCAL
                         SET DTINIREFEFAT = C_APUR.DTINICOMPET,
                             DTFINREFEFAT = C_APUR.DTFINCOMPET
                       WHERE NRLANCTONF   = V_NRLANCTONF
                         AND CDFILIAL     = C_APUR.CDFILIALFATURA;

                      IF(V_IDFATCONTJUNT IS NULL OR V_IDFATCONTJUNT <> C_APUR.IDFATCONTJUNT) THEN
                        V_NRAPURACAO    := NULL;
                        V_IDFATCONTJUNT := C_APUR.IDFATCONTJUNT;
                      END IF;

                     /* Gera apuracao do contrato */
                     IF (V_NRAPURACAO IS NULL) THEN
                        IF(P_NRRATEIOITEMVENC IS NOT NULL) THEN 
                            V_DSTIPOAPURACAO := 'RAT';
                        ELSIF (P_NRITFATURACONT IS NOT NULL) THEN
                            V_DSTIPOAPURACAO := 'ITEM';
                        ELSE
                            V_DSTIPOAPURACAO := 'APU';
                        END IF;

                        NOVO_CODIGO('FCT_APURACAO', V_NRAPURACAO, 1, P_NRORG);
                        V_NRAPURACAO := SUBSTR(V_NRAPURACAO, 11, 10);
                        INSERT INTO FCT_APURACAO
                                (NRAPURACAO, NRSEQCONTRATO, NRTIPOORCAMENTO,
                                 NRPARCNEGOCIO, CDMODPGTO, NRGRUPOFATURA,
                                 CDEMPRESA, CDFILIAL, NRLANCTONF,
                                 IDSITUACAOAPURACAO, VRAPURACAO, VRAPURACAOORIGINAL,
                                 DSALTERACAO, CDAGRUPANF, NRORG,
                                 DTINCLUSAO, NRORGINCLUSAO, CDOPERINCLUSAO, DSTIPOAPURACAO)
                        VALUES
                                (V_NRAPURACAO, NULL, V_TPORCA,
                                 C_APUR.NRPARCFATURA, NULL, NULL,
                                 V_EMPRESA, C_APUR.CDFILIALFATURA, V_NRLANCTONF,
                                 'FATURADA', ROUND(C_APUR.VRVENCIMENTO, 2), ROUND(C_APUR.VRVENCIMENTO, 2),
                                 NULL, NULL, P_NRORG,
                                 SYSDATE, P_NRORG, P_CDOPERINCLUSAO, V_DSTIPOAPURACAO);

                        /* cria uma ligacao entre as apuracaos e a parcela */
                        NOVO_CODIGO('FCT_RELACAPURACAOFATURA', V_NRAPURACAOFATURA, 1, P_NRORG);
                        INSERT INTO FCT_RELACAPURACAOFATURA (
                            NRAPURACAOFATURA, NRAPURACAO,    NRFATURACONT,
                            NRORG,            IDATIVO,       DTINCLUSAO,
                            DTULTATU,         NRORGINCLUSAO, CDOPERINCLUSAO,
                            NRORGULTATU,      CDOPERULTATU
                        ) VALUES (
                            V_NRAPURACAOFATURA, V_NRAPURACAO,    C_APUR.NRFATURACONT,
                            P_NRORG,            'S',       SYSDATE,
                            NULL,               P_NRORG, P_CDOPERINCLUSAO,
                            NULL,               NULL
                        );

                        V_APURACAOCONLUIDA := 'S';
                    END IF;

                    /** Atualiza a tabela de itens **/
                    IF (P_NRITFATURACONT IS NOT NULL) THEN
                        
                        UPDATE FCT_ITFATURACONT
                           SET IDSITUACAO     = '2',
                               VRFATURADO     = ROUND(NVL(VRNEGCONTR, VRVENCIMENTO), 2),
                               NRAPURACAO     = V_NRAPURACAO,
                               VRFALTAFATURAR = 0 
                         WHERE NRORG         = P_NRORG
                           AND NRFATURACONT  = C_APUR.NRFATURACONT
                           AND ((INSTR(P_NRITFATURACONT, '_' || TO_CHAR(NRITFATURACONT) || '_') > 0) OR P_NRITFATURACONT IS NULL);

                    ELSIF (P_NRRATEIOITEMVENC IS NULL) THEN
                        
                        UPDATE FCT_ITFATURACONT
                           SET IDSITUACAO     = '2',
                               VRFATURADO     = ROUND(NVL(VRNEGCONTR, VRVENCIMENTO), 2),
                               NRAPURACAO     = V_NRAPURACAO,
                               VRFALTAFATURAR = 0 
                         WHERE NRORG         = P_NRORG
                           AND NRFATURACONT  = C_APUR.NRFATURACONT
                           AND (IDSITUACAO = '1' OR IDSITUACAO = '6');

                    END IF;

                    /* Atualiza a tabela de rateios */
                    IF (P_NRRATEIOITEMVENC IS NOT NULL) THEN

                        UPDATE FCT_RATEIOITFATURACONT
                           SET NRAPURACAO       = V_NRAPURACAO,
                               IDSITUVENCRATEIO = '2'
                         WHERE NRORG         = P_NRORG
                           AND NRFATURACONT  = C_APUR.NRFATURACONT
                           AND NRAPURACAO    IS NULL
                           AND (INSTR(P_NRRATEIOITEMVENC, '_' || TO_CHAR(NRRATEIOITEMFAT) || '_') > 0);

                    ELSIF (P_NRITFATURACONT IS NOT NULL) THEN

                        UPDATE FCT_RATEIOITFATURACONT
                           SET NRAPURACAO       = V_NRAPURACAO
                         WHERE NRORG            = P_NRORG
                           AND NRFATURACONT     = C_APUR.NRFATURACONT
                           AND NRAPURACAO       IS NULL
                           AND ((INSTR(P_NRITFATURACONT, '_' || TO_CHAR(NRITFATURACONT) || '_') > 0));

                    ELSE 

                        UPDATE FCT_RATEIOITFATURACONT
                           SET NRAPURACAO       = V_NRAPURACAO,
                               IDSITUVENCRATEIO = '2'
                         WHERE NRORG            = P_NRORG
                           AND NRFATURACONT     = C_APUR.NRFATURACONT
                           AND NRAPURACAO       IS NULL
                           AND (IDSITUVENCRATEIO = '1' OR IDSITUVENCRATEIO = '6');

                    END IF;

                    /*Contrato*/
                    IF C_APUR.NRCONTRATOFCT IS NOT NULL THEN

                        SELECT LISTAGG(CONT.NRCONTRATOFCT, ', ') WITHIN GROUP (ORDER BY NRCONTRATOFCT)
                        INTO V_NRCONTRATOS
                        FROM FCT_RELACAGRUPCONTFAT RELACFAT
                        INNER JOIN FCT_CONTRATO CONT
                            ON RELACFAT.NRSEQCONTRATO = CONT.NRSEQCONTRATO
                            AND RELACFAT.NRORG        = CONT.NRORG
                        WHERE RELACFAT.NRFATURACONT   = C_APUR.NRFATURACONT
                          AND RELACFAT.NRORG          = C_APUR.NRORG;

                        SELECT MAX(NRDADOADIC)
                          INTO V_DADOADIC
                          FROM DADOSADIC
                         WHERE CDFILIAL   = C_APUR.CDFILIALFATURA
                           AND NRLANCTONF = V_NRLANCTONF;

                        IF V_DADOADIC IS NULL THEN
                            V_DADOADIC := '001';
                        ELSE
                            V_DADOADIC := V_DADOADIC+1;
                        END IF;

                        INSERT INTO DADOSADIC(
                            CDFILIAL,   NRLANCTONF,
                            NRDADOADIC, DSDADOADIC
                        ) VALUES (
                            C_APUR.CDFILIALFATURA,  V_NRLANCTONF, 
                            LPAD(V_DADOADIC,3,'0'), SUBSTR('Contrato(s): '|| V_NRCONTRATOS, 1, 255)
                        );

                    END IF;

                    /*Vencimento*/
                    IF C_APUR.DTVENCIMENTO IS NOT NULL THEN
                        SELECT MAX(NRDADOADIC)
                        INTO V_DADOADIC
                        FROM DADOSADIC
                        WHERE CDFILIAL     = C_APUR.CDFILIALFATURA
                            AND NRLANCTONF = V_NRLANCTONF;

                        IF V_DADOADIC IS NULL THEN
                            V_DADOADIC := '001';
                        ELSE
                            V_DADOADIC := V_DADOADIC + 1;
                        END IF;

                        BEGIN
                            SELECT DTATUAVENREC
                            INTO V_VENCIMENTO
                            FROM CONTARECEBER
                            WHERE NRLANCTONF = V_NRLANCTONF
                                AND CDFILIAL = C_APUR.CDFILIALFATURA;
                        EXCEPTION WHEN NO_DATA_FOUND THEN
                                V_VENCIMENTO := C_APUR.DTVENCIMENTO;
                        END;

                        INSERT INTO DADOSADIC(CDFILIAL, NRLANCTONF, NRDADOADIC, DSDADOADIC)
                        VALUES(C_APUR.CDFILIALFATURA, V_NRLANCTONF, LPAD(V_DADOADIC,3,'0'), SUBSTR('Vencimento: '||TO_CHAR(V_VENCIMENTO,'DD/MM/YYYY'), 1, 255));
                    END IF;

                    /*Periodo*/
                    IF C_APUR.DTINICOMPET IS NOT NULL THEN
                        SELECT MAX(NRDADOADIC)
                            INTO V_DADOADIC
                            FROM DADOSADIC
                        WHERE CDFILIAL     = C_APUR.CDFILIALFATURA 
                            AND NRLANCTONF = V_NRLANCTONF;

                        IF V_DADOADIC IS NULL THEN
                            V_DADOADIC := '001';
                        ELSE
                            V_DADOADIC := V_DADOADIC+1;
                        END IF;

                        INSERT INTO DADOSADIC(CDFILIAL, NRLANCTONF, NRDADOADIC, DSDADOADIC)
                            VALUES(C_APUR.CDFILIALFATURA, V_NRLANCTONF, LPAD(V_DADOADIC,3,'0'), SUBSTR('Periodo: '||TO_CHAR(C_APUR.DTINICOMPET,'DD/MM/YYYY')||' - '||TO_CHAR(C_APUR.DTFINCOMPET,'DD/MM/YYYY'), 1, 255));
                        END IF;

                        /*Observacoes*/
                        /*IF C_APUR.DSOBSERVACAOCONT IS NOT NULL THEN
                            SELECT MAX(NRDADOADIC)
                                INTO V_DADOADIC
                                FROM DADOSADIC
                                WHERE CDFILIAL   = C_APUR.CDFILIALFATURA
                                  AND NRLANCTONF = V_NRLANCTONF;
                            IF V_DADOADIC IS NULL THEN
                                V_DADOADIC := '001';
                            ELSE
                                V_DADOADIC := V_DADOADIC+1;
                            END IF;

                            INSERT INTO DADOSADIC(CDFILIAL, NRLANCTONF, NRDADOADIC, DSDADOADIC)
                                VALUES(C_APUR.CDFILIALFATURA, V_NRLANCTONF, LPAD(V_DADOADIC,3,'0'), SUBSTR(C_APUR.DSOBSERVACAOCONT, 1, 255));
                        END IF;*/ --C_APUR.DSOBSERVACAOCONT  IS NOT NULL
                    END IF; --C_APUR.DTINICOMPET IS NOT NULL
                END IF; -- C_APUR.VRVENCIMENTO = 0

            EXCEPTION WHEN OTHERS THEN
                BEGIN
                    V_DEUERRO := TRUE;

                    IF (SQLCODE = -20001) THEN
                        V_MSGERRO := 'O Parceiro de Negocio parametrizado na parcela nao e do tipo Cliente.';
                    ELSIF (SQLCODE = -20002) THEN
                        V_MSGERRO := 'A Serie de Nota Fiscal parametrizada na parcela nao esta relacionada com a Unidade para Faturamento.';
                    ELSIF (SQLCODE = -20003) THEN
                        V_MSGERRO := 'O Parceiro de Negocio parametrizado na parcela esta relacionado a mais de um Cliente.';
                    ELSE
                        V_MSGERRO := 'Erro inesperado: '|| SQLERRM;
                    END IF;

                    INSERT INTO FCT_ERROSAPURACAOFATURA (
                        NRFATURACONT,           DSERRO,          CDOPERADOR,
                        DTINCLUSAO,             NRORG
                    )
                    VALUES (
                        C_APUR.NRFATURACONT,    V_MSGERRO,       P_CDOPERINCLUSAO,
                        V_DATAATUAL,            P_NRORG
                    );

                    --Desfazer NFs e apuracoes
                    IF V_GEROUNOTA = TRUE THEN -- Verifica se tem NF criada --
                        IF V_APURACAOCONLUIDA IS NULL THEN -- Verifica se a NF criada nao foi vinculada a apuracao. No caso, se ja foi gravada a ITEMPRODUTO e a FCT_APURACAO --
                            
                            --  Caso exista rateio para nota, deleta o rateio --
                            DELETE FROM RATEIONF
                                  WHERE NRORG = P_NRORG
                                    AND NRLANCTONF = V_NRLANCTONF
                                    AND CDFILIAL = C_APUR.CDFILIALFATURA;
                            
                            -- Deleta a NF ---
                            DELETA_NF(C_APUR.CDFILIALFATURA, V_NRLANCTONF);

                            --  ALTERA O STATUS DO VENCIMEMNTO PARA PENDENTE --
                            FOR C_UPDVENC IN (SELECT NRAPURACAO, VRAPURACAO
                                           FROM FCT_APURACAO
                                          WHERE NRLANCTONF = V_NRLANCTONF
                                            AND CDFILIAL = C_APUR.CDFILIALFATURA
                                            AND NRORG = P_NRORG
                            ) LOOP

                                UPDATE FCT_FATURACONT
                                   SET IDSITUACAO = '1',
                                       IDFORMAFATURA = NULL,
                                       VRFALTAFATURAR = VRFALTAFATURAR + C_UPDVENC.VRAPURACAO,
                                       VRFATURADO = VRFATURADO - C_UPDVENC.VRAPURACAO
                                 WHERE NRORG = P_NRORG
                                   AND NRAPURACAO = C_UPDVENC.NRAPURACAO;

                                UPDATE FCT_RATEIOITFATURACONT
                                   SET IDSITUVENCRATEIO = '1'
                                 WHERE NRORG = P_NRORG
                                   AND NRAPURACAO = C_UPDVENC.NRAPURACAO;

                                UPDATE FCT_ITFATURACONT
                                   SET IDSITUACAO = '1',
                                       VRFALTAFATURAR = VRFALTAFATURAR + C_UPDVENC.VRAPURACAO,
                                       VRFATURADO = VRFATURADO - C_UPDVENC.VRAPURACAO
                                 WHERE NRORG = P_NRORG
                                   AND NRAPURACAO = C_UPDVENC.NRAPURACAO;

                            END LOOP; --C_UPDVENC
                            
                        ELSE
                            
                            BEGIN
                               FCT_CANC_APURCAO_FATURAMENTO (P_NRORG, NULL, P_CDOPERINCLUSAO, C_APUR.DTINICOMPET, C_APUR.DTFINCOMPET, '_'||TO_CHAR(C_APUR.NRFATURACONT)||'_', P_NRRATEIOITEMVENC, P_NRITFATURACONT);
                            EXCEPTION WHEN OTHERS THEN
                               BEGIN
                                
                                  --RAISE_APPLICATION_ERROR(-20000, 'ERRO_ORACLE_CANC'||'##'||V_NR_ERRO||'##'||SUBSTR(SQLERRM, INSTR(SQLERRM, '##')+2));
                                  V_MSGERRO := 'Erro inesperado ao cancelar a apuracao: '|| SQLERRM;

                                  INSERT INTO FCT_ERROSAPURACAOFATURA (
                                      NRFATURACONT,           DSERRO,          CDOPERADOR,
                                      DTINCLUSAO,             NRORG
                                  )
                                  VALUES (
                                      C_APUR.NRFATURACONT,    V_MSGERRO,       P_CDOPERINCLUSAO,
                                      V_DATAATUAL,            P_NRORG
                                  );

                               END;
                            END;
                        END IF; --V_APURACAOCONLUIDA IS NULL
                    END IF; --V_NFCRIADA IS NOT NULL

                    CONTINUE;
                END;
            END; --tratamento de erro

        END LOOP; -- C_APUR

        V_POSINI := V_POS_UNDER;

    END LOOP;

    FOR C_NFFECHAMENTO IN (
        SELECT LISTAGG(CONT.NRCONTRATOFCT, ', ') WITHIN GROUP (ORDER BY RELAC.NRSEQCONTRATO) AS NRCONTRATOFCT,
               LISTAGG(RELAC.NRSEQCONTRATO, '_') WITHIN GROUP (ORDER BY RELAC.NRSEQCONTRATO) AS NRSEQCONTRATO,
               DADOS.NRLANCTONF, DADOS.CDFILIAL, DADOS.NRFATURACONT, DADOS.DSREFERENCIANOTA
        FROM FCT_DADOSNF DADOS
        INNER JOIN FCT_RELACAGRUPCONTFAT RELAC
            ON DADOS.NRFATURACONT = RELAC.NRFATURACONT
            AND DADOS.NRORG       = RELAC.NRORG
        INNER JOIN FCT_CONTRATO CONT
           ON RELAC.NRSEQCONTRATO = CONT.NRSEQCONTRATO
          AND RELAC.NRORG         = CONT.NRORG
        INNER JOIN LISTA
           ON DADOS.NRLANCTONF = SUBSTR(LISTA.CDLISTA, 1, 10)
          AND DADOS.CDFILIAL = SUBSTR(LISTA.CDLISTA, 12)
        WHERE 1=1 --(INSTR('_'||P_NRFATURACONT||'_', '_'||TO_CHAR(DADOS.NRFATURACONT)||'_')>0)
            --AND (INSTR('_'||V_NFCRIADA||'_', '_'||DADOS.NRLANCTONF||'_') > 0)
            AND LISTA.NRLISTA = V_LISTANF
            AND DADOS.NRORG = P_NRORG
        GROUP BY DADOS.NRLANCTONF, DADOS.CDFILIAL, DADOS.NRFATURACONT, DADOS.DSREFERENCIANOTA
    ) LOOP
        
        BEGIN --tratamento de erro

            UPDATE NOTAFISCAL
               SET IDSTATUS = 'P'
             WHERE NRLANCTONF = C_NFFECHAMENTO.NRLANCTONF
               AND CDFILIAL   = C_NFFECHAMENTO.CDFILIAL;
            
            GERA_NOTAFISCAL_FECHAMENTO(C_NFFECHAMENTO.CDFILIAL, C_NFFECHAMENTO.NRLANCTONF);
            SELECT VRNOTAFISC
              INTO V_VRNOTAFISC
              FROM NOTAFISCAL
             WHERE NRLANCTONF = C_NFFECHAMENTO.NRLANCTONF
               AND CDFILIAL   = C_NFFECHAMENTO.CDFILIAL
               AND NRORG      = P_NRORG;
            BEGIN
                SELECT NVL(VRNEGCONTR, VRVENCIMENTO), VRFALTAFATURAR
                  INTO V_VRVENCIMENTO, V_VRFALTAFATURAR
                  FROM FCT_FATURACONT
                 WHERE NRFATURACONT = C_NFFECHAMENTO.NRFATURACONT
                   AND NRORG        = P_NRORG;
            EXCEPTION WHEN NO_DATA_FOUND THEN
                V_VRVENCIMENTO := NULL;
                V_VRFALTAFATURAR := NULL;
            END;
            IF(V_VRFALTAFATURAR IS NOT NULL AND V_VRFALTAFATURAR <> 0) THEN
                V_VRNOTAFISC     := ROUND(V_VRNOTAFISC, 2);
                V_VRVENCIMENTO   := ROUND(V_VRVENCIMENTO, 2);
                V_VRFALTAFATURAR := ROUND(V_VRFALTAFATURAR, 2);
                IF (V_VRNOTAFISC = V_VRVENCIMENTO) THEN
                    V_IDSITUACAO := '2';
                    UPDATE FCT_FATURACONT
                       SET IDSITUACAO     = V_IDSITUACAO,
                           VRFATURADO     = ROUND(V_VRNOTAFISC, 2),
                           VRFALTAFATURAR = 0,
                           IDFORMAFATURA  = 'A'
                     WHERE NRFATURACONT = C_NFFECHAMENTO.NRFATURACONT
                       AND NRORG          = P_NRORG;
                ELSE
                    IF (V_VRFALTAFATURAR - V_VRNOTAFISC) = 0 THEN
                        V_IDSITUACAO := '2';
                    ELSE 
                        V_IDSITUACAO := '6';
                    END IF;
                    UPDATE FCT_FATURACONT
                       SET IDSITUACAO     = V_IDSITUACAO,
                           VRFATURADO     = ROUND(VRFATURADO + V_VRNOTAFISC, 2),
                           VRFALTAFATURAR = ROUND(VRFALTAFATURAR - V_VRNOTAFISC, 2),
                           IDFORMAFATURA  = 'A'
                     WHERE NRFATURACONT   = C_NFFECHAMENTO.NRFATURACONT
                       AND NRORG          = P_NRORG;
                END IF;
                IF (V_IDSITUACAO = '2') THEN
                    UPDATE FCT_RATEIOITFATURACONT
                       SET IDSITUVENCRATEIO = '2'
                     WHERE NRFATURACONT = C_NFFECHAMENTO.NRFATURACONT
                       AND NRORG        = P_NRORG;
                    UPDATE FCT_ITFATURACONT
                       SET IDSITUACAO     = '2',
                           VRFALTAFATURAR = 0,
                           VRFATURADO     = ROUND(NVL(VRNEGCONTR, VRVENCIMENTO), 2)
                     WHERE NRFATURACONT = C_NFFECHAMENTO.NRFATURACONT
                       AND NRORG        = P_NRORG;
                END IF; --V_IDSITUACAO = '2'
            END IF; --V_VRFALTAFATURAR IS NOT NULL AND V_VRFALTAFATURAR <> 0
            UPDATE FCT_APURACAO
               SET VRAPURACAO         = ROUND(V_VRNOTAFISC, 2),
                   VRAPURACAOORIGINAL = ROUND(V_VRNOTAFISC, 2)
             WHERE NRAPURACAO = V_NRAPURACAO
               AND NRORG      = P_NRORG;
            -- UPDATA VALORES DO RATEIO PARA CONSIDER O VALOR CONTycaoyparam1BIL DO ITEM DA NF (ITEMPRODUTO.VRCONTITEM)
            FOR C_UPDRATEIO IN (
                SELECT NRSEQITPROD, VRRATENF, CDFILICCUST, CDCENTCUSNF
                FROM RATEIONF RAT
                WHERE RAT.NRLANCTONF =  C_NFFECHAMENTO.NRLANCTONF
                    AND RAT.CDFILIAL = C_NFFECHAMENTO.CDFILIAL
                    AND NRORG        = P_NRORG
            ) LOOP
                -- Busca valores do item
                SELECT VRCONTITEM, VRBRUTITEM
                  INTO V_VRCONTITEM, V_VRBRUTITEM
                  FROM ITEMPRODUTO
                 WHERE NRLANCTONF  = C_NFFECHAMENTO.NRLANCTONF
                   AND CDFILIAL    = C_NFFECHAMENTO.CDFILIAL
                   AND NRSEQITPROD = C_UPDRATEIO.NRSEQITPROD
                   AND NRORG       = P_NRORG;
                /*SELECT (C_UPDRATEIO.VRRATENF*100)/ V_VRBRUTITEM
                  INTO V_VRPERCRATEIO
                  FROM DUAL;*/
                V_VRPERCRATEIO := (C_UPDRATEIO.VRRATENF * 100) / V_VRBRUTITEM;
                IF V_VRPERCRATEIO = 100 THEN
                    V_VRRATEIO := V_VRCONTITEM;
                ELSE
                    V_VRRATEIO := (V_VRCONTITEM * V_VRPERCRATEIO)/100;
                END IF;
                UPDATE RATEIONF
                   SET VRRATENF = V_VRRATEIO
                 WHERE CDFILIAL    = C_NFFECHAMENTO.CDFILIAL
                   AND NRLANCTONF  = C_NFFECHAMENTO.NRLANCTONF
                   AND CDFILICCUST = C_UPDRATEIO.CDFILICCUST
                   AND CDCENTCUSNF = C_UPDRATEIO.CDCENTCUSNF
                   AND NRSEQITPROD = C_UPDRATEIO.NRSEQITPROD
                   AND NRORG       = P_NRORG;
            END LOOP; --C_UPDRATEIO
            /* atualiza a descricao do item da NF de acordo com a referencia da FCT_DADOSNF*/
            IF C_NFFECHAMENTO.DSREFERENCIANOTA IS NOT NULL THEN
                UPDATE ITEMPRODUTO
                   SET DSPRODEMIS = C_NFFECHAMENTO.DSREFERENCIANOTA
                 WHERE NRLANCTONF = C_NFFECHAMENTO.NRLANCTONF
                   AND CDFILIAL   = C_NFFECHAMENTO.CDFILIAL
                   AND NRORG      = P_NRORG;
            END IF;
            /* atualiza a descricao do item da NF de acordo com a parametrizacao do servico, SIM, ELA SUBSTITUI A DO FCT_DADOSNF */
            FOR C_ITENSVENC IN (
                SELECT ITCONT.CDSERVORCA,
                  LISTAGG(ITFAT.NRITFATURACONT, '_') WITHIN GROUP (ORDER BY ITFAT.NRITFATURACONT) AS NRITFATURACONT,
                  LISTAGG(ITFAT.NRITEMOCONTRATO, '_') WITHIN GROUP (ORDER BY ITFAT.NRITEMOCONTRATO) AS NRITEMOCONTRATO
                FROM FCT_ITFATURACONT ITFAT
                INNER JOIN FCT_ITEMCONTRATO ITCONT
                  ON ITFAT.NRITEMOCONTRATO = ITCONT.NRITEMOCONTRATO
                  AND ITFAT.NRORG          = ITCONT.NRORG
                WHERE ITFAT.NRFATURACONT = C_NFFECHAMENTO.NRFATURACONT
                    AND ITFAT.NRORG      = P_NRORG
                    AND (INSTR('_'|| C_NFFECHAMENTO.NRSEQCONTRATO ||'_', '_'|| ITFAT.NRSEQCONTRATO ||'_') > 0)
                GROUP BY ITCONT.CDSERVORCA
            ) LOOP
                V_DSSERVORCANF  := NULL;
                V_DSSERVORCABOL := NULL;
                
                FOR C_SERVICOS IN (
                    SELECT LISTAGG(PARCELA.NRORCAMENTO, ', ') WITHIN GROUP (ORDER BY PARCELA.NRORCAMENTO) AS NRORCAMENTO,
                           LISTAGG(PARCELA.NRCONTRATOFCT, ', ') WITHIN GROUP (ORDER BY PARCELA.NRCONTRATOFCT) AS NRCONTRATOFCT,
                           PARCELA.DTINICONT,
                           PARCELA.DTFINCONT,
                           PARCELA.NMPRINCIPALPARC,
                           MAX(PARCELA.QTPARCELASTOT) AS QTPARCELASTOT,
                           MAX(PARCELA.QTPARCELAS) AS QTPARCELAS,
                           PARCELA.DTINICOMPET,
                           PARCELA.DTFINCOMPET,
                           PARCELA.NMITEMCONTRATO, 
                           SUM(PARCELA.VRTOTITEMCONT) AS VRTOTITEMCONT,
                           SUM(PARCELA.VRFATURADO) AS VRFATURADO,
                           PARCELA.CDPRODFATSERV,
                           PARCELA.CDSERVORCA,
                           LISTAGG(PARCELA.NRMEDICAOFATURA, '_') WITHIN GROUP (ORDER BY PARCELA.NRMEDICAOFATURA) AS NRMEDICAOFATURA,
                           PARCELA.DSSERVORCANF,
                           PARCELA.DSSERVORCABOL,
                           PARCELA.MESCOMPET
                    FROM (
                          SELECT ORC.NRORCAMENTO,
                             CONT.NRCONTRATOFCT,
                             NVL (TO_CHAR(CONT.DTINIVIGENCONT, 'DD/MM/YYYY'), TO_CHAR(CONT.DTINICIOCONTRATO, 'DD/MM/YYYY')) AS DTINICONT,
                             NVL (TO_CHAR(CONT.DTFINVIGENCONT, 'DD/MM/YYYY'), TO_CHAR(CONT.DTFIMCONTRATO, 'DD/MM/YYYY')) AS DTFINCONT,
                             PARC.NMPRINCIPALPARC,
                             PARCELATOT.QTPARCELASTOT,
                             NVL(PARCELA.QTPARCELAS, 0) AS QTPARCELAS,
                             TO_CHAR(FAT.DTINICOMPET, 'MM/YYYY') AS MESCOMPET,
                             TO_CHAR(FAT.DTINICOMPET, 'DD/MM/YYYY') AS DTINICOMPET,
                             TO_CHAR(FAT.DTFINCOMPET, 'DD/MM/YYYY') AS DTFINCOMPET,
                             ITEMCONT.NMITEMCONTRATO,
                             NVL(ITEMCONT.VRTOTITEMCONT,0) AS VRTOTITEMCONT,
                             NVL(ITFATURA.VRFATURADO,0) AS VRFATURADO,
                             NVL(PFITESC.CDPRODFATURA, NVL(CAPAPARAM.CDPRODFATURA, SERVORCA.CDPRODFATSERV)) AS CDPRODFATSERV,
                             SERVORCA.CDSERVORCA,
                             AGCONTFAT.NRMEDICAOFATURA,
                             NVL(PFITESC.DSSERVORCANF,  NVL(CAPAPARAM.DSSERVORCANF, SERVORCA.DSSERVORCANF)) AS DSSERVORCANF,
                             NVL(PFITESC.DSSERVORCABOL, NVL(CAPAPARAM.DSSERVORCABOL,SERVORCA.DSSERVORCABOL)) AS DSSERVORCABOL
                        FROM FCT_CONTRATO CONT
                        INNER JOIN FCT_RELACAGRUPCONTFAT AGCONTFAT
                              ON AGCONTFAT.NRSEQCONTRATO = CONT.NRSEQCONTRATO
                             AND AGCONTFAT.NRORG         = CONT.NRORG
                        INNER JOIN FCT_FATURACONT FAT
                             ON FAT.NRFATURACONT = AGCONTFAT.NRFATURACONT
                            AND FAT.NRORG        = AGCONTFAT.NRORG
                        INNER JOIN PARCNEGOCIO PARC
                             ON PARC.NRPARCNEGOCIO = CONT.NRPARCNEGOCIO
                            AND PARC.NRORG         = CONT.NRORG
                        LEFT JOIN (
                            SELECT AGRUPCONT.NRSEQCONTRATO,
                                 AGRUPCONT.NRORG,
                                 COUNT(AGRUPCONT.NRFATURACONT) AS QTPARCELASTOT
                            FROM FCT_RELACAGRUPCONTFAT AGRUPCONT
                            JOIN FCT_ITFATURACONT
                              ON FCT_ITFATURACONT.NRFATURACONT    = AGRUPCONT.NRFATURACONT
                             AND FCT_ITFATURACONT.NRORG           = AGRUPCONT.NRORG
                             AND (INSTR('_'|| C_ITENSVENC.NRITEMOCONTRATO ||'_', '_'||FCT_ITFATURACONT.NRITEMOCONTRATO||'_') > 0)
                           WHERE (INSTR('_'|| C_NFFECHAMENTO.NRSEQCONTRATO ||'_', '_'||AGRUPCONT.NRSEQCONTRATO||'_') > 0)
                             AND AGRUPCONT.NRORG = P_NRORG
                          GROUP BY AGRUPCONT.NRSEQCONTRATO, AGRUPCONT.NRORG
                        ) PARCELATOT
                            ON PARCELATOT.NRSEQCONTRATO = CONT.NRSEQCONTRATO
                            AND PARCELATOT.NRORG = CONT.NRORG
                        LEFT JOIN (
                            SELECT AGRUPCONT.NRSEQCONTRATO,
                                 AGRUPCONT.NRORG,
                                 COUNT(AGRUPCONT.NRFATURACONT) AS QTPARCELAS
                            FROM FCT_RELACAGRUPCONTFAT AGRUPCONT
                            JOIN FCT_ITFATURACONT
                              ON FCT_ITFATURACONT.NRFATURACONT    = AGRUPCONT.NRFATURACONT
                             AND FCT_ITFATURACONT.NRORG           = AGRUPCONT.NRORG
                             AND (INSTR('_'|| C_ITENSVENC.NRITEMOCONTRATO ||'_', '_'||FCT_ITFATURACONT.NRITEMOCONTRATO||'_') > 0)
                           WHERE (INSTR('_'|| C_NFFECHAMENTO.NRSEQCONTRATO ||'_', '_'||AGRUPCONT.NRSEQCONTRATO||'_') > 0)
                             AND AGRUPCONT.NRORG = P_NRORG
                             AND FCT_ITFATURACONT.IDSITUACAO IN('2', '3', '6')
                          GROUP BY AGRUPCONT.NRSEQCONTRATO, AGRUPCONT.NRORG
                        ) PARCELA
                             ON PARCELA.NRSEQCONTRATO = CONT.NRSEQCONTRATO
                            AND PARCELA.NRORG = CONT.NRORG
                        LEFT JOIN FCT_REFEORCACONT RELACCONTPROP
                             ON RELACCONTPROP.NRSEQCONTRATO = CONT.NRSEQCONTRATO
                             AND RELACCONTPROP.NRORG = CONT.NRORG
                        LEFT JOIN FCT_ORCAMENTO ORC
                             ON RELACCONTPROP.NRSEQORCAMENTO = ORC.NRSEQORCAMENTO
                            AND RELACCONTPROP.NRORG = ORC.NRORG
                        INNER JOIN FCT_ITEMCONTRATO ITEMCONT
                             ON ITEMCONT.NRSEQCONTRATO = CONT.NRSEQCONTRATO
                            AND (INSTR('_'|| C_ITENSVENC.NRITEMOCONTRATO ||'_', '_'||ITEMCONT.NRITEMOCONTRATO||'_') > 0)
                            AND ITEMCONT.NRORG = CONT.NRORG
                        INNER JOIN FCT_ITFATURACONT ITFATURA
                             ON ITFATURA.NRFATURACONT = FAT.NRFATURACONT
                            AND ITFATURA.NRITEMOCONTRATO = ITEMCONT.NRITEMOCONTRATO
                            AND ITFATURA.NRORG = FAT.NRORG
                        INNER JOIN FCT_SERVICOORCA SERVORCA
                             ON SERVORCA.CDSERVORCA = ITEMCONT.CDSERVORCA
                            AND SERVORCA.NRORG = ITEMCONT.NRORG
                        LEFT JOIN FCT_ITESCOPOPROPOSTA ITESC
                          ON ITEMCONT.CDSERVORCA = ITESC.CDSERVORCA
                         AND NVL(CONT.NRTIPOORCAMENTO, RELACCONTPROP.NRTIPOORCAMENTO) = ITESC.NRTIPOORCAMENTO
                         AND ITEMCONT.NRORG = ITESC.NRORG
                        LEFT JOIN FCT_PARAMFATITESC PFITESC
                          ON ITESC.NRITESCOPOPROPOSTA = PFITESC.NRITESCOPOPROPOSTA
                         AND ITESC.NRORG = PFITESC.NRORG
                        LEFT JOIN FCT_CAPAPARAMFATESC CAPAPARAM
                              ON  NVL(CONT.NRTIPOORCAMENTO, RELACCONTPROP.NRTIPOORCAMENTO) = CAPAPARAM.NRTIPOORCAMENTO
                              AND CAPAPARAM.NRORG = ORC.NRORG
                        WHERE (INSTR('_'|| C_NFFECHAMENTO.NRSEQCONTRATO ||'_', '_'||CONT.NRSEQCONTRATO||'_') > 0)
                            AND CONT.NRORG             = P_NRORG
                            AND AGCONTFAT.NRFATURACONT = C_NFFECHAMENTO.NRFATURACONT
                            AND (PFITESC.DSSERVORCANF IS NOT NULL OR SERVORCA.DSSERVORCANF IS NOT NULL)
                    ) PARCELA
                    GROUP BY PARCELA.DTINICONT,
                           PARCELA.DTFINCONT,
                           PARCELA.NMPRINCIPALPARC,
                           PARCELA.DTINICOMPET,
                           PARCELA.DTFINCOMPET,
                           PARCELA.NMITEMCONTRATO, 
                           PARCELA.CDPRODFATSERV,
                           PARCELA.CDSERVORCA,
                           PARCELA.DSSERVORCANF,
                           PARCELA.DSSERVORCABOL,
                           PARCELA.MESCOMPET
                ) LOOP

                    V_DSSERVORCANF := C_SERVICOS.DSSERVORCANF;
                    IF V_DSSERVORCABOL IS NULL THEN
                        V_DSSERVORCABOL := C_SERVICOS.DSSERVORCABOL;
                    ELSE
                        V_DSSERVORCABOL := V_DSSERVORCABOL||CHR(10)||CHR(10)||C_SERVICOS.DSSERVORCABOL;
                    END IF;
                    V_MEDVARIAVEIS := NULL;
                    IF (C_SERVICOS.NRMEDICAOFATURA IS NOT NULL) THEN 
                        FOR MEDVAR IN (
                            SELECT SERV.NMSERVORCA, 
                              TPMEDIDA.DSTPMEDIDASERV, 
                              NVL(QTMEDIDAMEDICAO, QTMEDIDAVARIAVEL) AS QTMEDIDAVAR,
                              CONT.NRCONTRATOFCT
                            FROM FCT_MEDVARMEDICAOFATURA MEDVAR
                            JOIN FCT_TIPOMEDIDASERV TPMEDIDA
                               ON MEDVAR.CDTPMEDIDAVARIAVEL = TPMEDIDA.CDTPMEDIDASERV
                              AND MEDVAR.NRORG              = TPMEDIDA.NRORG
                            JOIN FCT_SERVICOORCA SERV
                               ON MEDVAR.IDELEMENTORAIZ = SERV.IDELEMENTO
                              AND MEDVAR.NRORG          = SERV.NRORG
                            INNER JOIN FCT_MEDICAOFATURA MEDICAO
                              ON MEDVAR.NRMEDICAOFATURA = MEDICAO.NRMEDICAOFATURA
                              AND MEDVAR.NRORG          = MEDICAO.NRORG
                            INNER JOIN FCT_CONTRATO CONT 
                              ON MEDICAO.NRSEQCONTRATO = CONT.NRSEQCONTRATO
                              AND MEDICAO.NRORG        = CONT.NRORG
                            WHERE (INSTR('_'|| C_SERVICOS.NRMEDICAOFATURA ||'_', '_'|| MEDVAR.NRMEDICAOFATURA ||'_') > 0)
                              AND MEDVAR.CDSERVORCA = C_SERVICOS.CDSERVORCA
                              AND MEDVAR.NRORG      = P_NRORG
                            ORDER BY NRCONTRATOFCT
                        ) LOOP
                            IF(V_MEDVARIAVEIS IS NULL OR INSTR(V_MEDVARIAVEIS, MEDVAR.NRCONTRATOFCT) = 0) THEN
                                IF(V_MEDVARIAVEIS IS NULL) THEN
                                    V_NRCONTRATOS := 'Contrato: ' || MEDVAR.NRCONTRATOFCT || ':' || CHR(13); 
                                ELSE 
                                    V_NRCONTRATOS := CHR(13) || 'Contrato: ' || MEDVAR.NRCONTRATOFCT || ':' || CHR(13); 
                                END IF;
                            ELSE 
                                V_NRCONTRATOS := CHR(13);
                            END IF;
                            IF (V_MEDVARIAVEIS IS NULL) THEN
                                V_MEDVARIAVEIS := V_NRCONTRATOS || MEDVAR.NMSERVORCA ||' - Medida: '|| MEDVAR.DSTPMEDIDASERV||' - Qtde:'||MEDVAR.QTMEDIDAVAR;
                            ELSE
                                V_MEDVARIAVEIS := V_MEDVARIAVEIS || V_NRCONTRATOS || MEDVAR.NMSERVORCA||' - Medida: '||MEDVAR.DSTPMEDIDASERV||' - Qtde:'||MEDVAR.QTMEDIDAVAR;
                            END IF;
                        END LOOP; --MEDVAR
                    END IF; --C_SERVICOS.NRMEDICAOFATURA IS NOT NULL

                    V_PARCELAS := C_SERVICOS.QTPARCELAS ||'/'|| C_SERVICOS.QTPARCELASTOT;
                    /*Mnemonicos: [CODPROP] - Codigo Proposta | [CODCONT] - Codigo Contrato [DTINICONT] - Data inicial do Contrato | [DTFINCONT] - Data final do contrato | [PARCEIRO] - Parceiro de Negocio |
                                  [PARCELA] - Parcelas | [MESCOMPET] - Mes de Competencia da Parcela | [DTINICOMPET] - Data de Inicio da Competencia | [DTFINCOMPET] - Data Final de Competencia |
                                  [NMSERVICO] - Nome do Servico | [VRSERVICO] - Valor Total do Servico no Contrato  | [VRSERVICOAPU] -  Valor Total Apurado para o Servico | 
                                  [MEDVARIAVES] - Elementos e tipos Medidas variaveis e suas quantidades (Somente para servicos que sejam de medicao) */
                    V_DSSERVORCANF  := REPLACE(V_DSSERVORCANF,'[CODPROP]', NVL(C_SERVICOS.NRORCAMENTO, ''));
                    V_DSSERVORCABOL := REPLACE(V_DSSERVORCABOL,'[CODPROP]', NVL(C_SERVICOS.NRORCAMENTO, ''));
                    V_DSSERVORCANF  := REPLACE(V_DSSERVORCANF,'[CODCONT]', NVL(C_SERVICOS.NRCONTRATOFCT, ''));
                    V_DSSERVORCABOL := REPLACE(V_DSSERVORCABOL,'[CODCONT]', NVL(C_SERVICOS.NRCONTRATOFCT, ''));
                    V_DSSERVORCANF  := REPLACE(V_DSSERVORCANF,'[DTINICONT]', NVL(C_SERVICOS.DTINICONT, ''));
                    V_DSSERVORCABOL := REPLACE(V_DSSERVORCABOL,'[DTINICONT]', NVL(C_SERVICOS.DTINICONT, ''));
                    V_DSSERVORCANF  := REPLACE(V_DSSERVORCANF,'[DTFINCONT]', NVL(C_SERVICOS.DTFINCONT, ''));
                    V_DSSERVORCABOL := REPLACE(V_DSSERVORCABOL,'[DTFINCONT]', NVL(C_SERVICOS.DTFINCONT, ''));
                    V_DSSERVORCANF  := REPLACE(V_DSSERVORCANF,'[PARCEIRO]', NVL(C_SERVICOS.NMPRINCIPALPARC, ''));
                    V_DSSERVORCABOL := REPLACE(V_DSSERVORCABOL,'[PARCEIRO]', NVL(C_SERVICOS.NMPRINCIPALPARC, ''));
                    V_DSSERVORCANF  := REPLACE(V_DSSERVORCANF,'[PARCELA]', NVL(V_PARCELAS, ''));
                    V_DSSERVORCABOL := REPLACE(V_DSSERVORCABOL,'[PARCELA]', NVL(V_PARCELAS, ''));
                    V_DSSERVORCANF  := REPLACE(V_DSSERVORCANF,'[MESCOMPET]', NVL(C_SERVICOS.MESCOMPET, ''));
                    V_DSSERVORCABOL := REPLACE(V_DSSERVORCABOL,'[MESCOMPET]', NVL(C_SERVICOS.MESCOMPET, ''));
                    V_DSSERVORCANF  := REPLACE(V_DSSERVORCANF,'[DTINICOMPET]', NVL(C_SERVICOS.DTINICOMPET, ''));
                    V_DSSERVORCABOL := REPLACE(V_DSSERVORCABOL,'[DTINICOMPET]', NVL(C_SERVICOS.DTINICOMPET, ''));
                    V_DSSERVORCANF  := REPLACE(V_DSSERVORCANF,'[DTFINCOMPET]', NVL(C_SERVICOS.DTFINCOMPET, ''));
                    V_DSSERVORCABOL := REPLACE(V_DSSERVORCABOL,'[DTFINCOMPET]', NVL(C_SERVICOS.DTFINCOMPET, ''));
                    V_DSSERVORCANF  := REPLACE(V_DSSERVORCANF,'[NMSERVICO]', NVL(C_SERVICOS.NMITEMCONTRATO, ''));
                    V_DSSERVORCABOL := REPLACE(V_DSSERVORCABOL,'[NMSERVICO]', NVL(C_SERVICOS.NMITEMCONTRATO, ''));
                    V_DSSERVORCANF  := REPLACE(V_DSSERVORCANF,'[VRSERVICO]', NVL(TRIM(TO_CHAR(C_SERVICOS.VRTOTITEMCONT,'999G999G999G990D99', 'NLS_NUMERIC_CHARACTERS = '',.''')), ''));
                    V_DSSERVORCABOL := REPLACE(V_DSSERVORCABOL,'[VRSERVICO]', NVL(TRIM(TO_CHAR(C_SERVICOS.VRTOTITEMCONT,'999G999G999G990D99', 'NLS_NUMERIC_CHARACTERS = '',.''')), ''));
                    V_DSSERVORCANF  := REPLACE(V_DSSERVORCANF,'[VRSERVICOAPU]', NVL(TRIM(TO_CHAR(C_SERVICOS.VRFATURADO,'999G999G999G990D99', 'NLS_NUMERIC_CHARACTERS = '',.''')), ''));
                    V_DSSERVORCABOL := REPLACE(V_DSSERVORCABOL,'[VRSERVICOAPU]', NVL(TRIM(TO_CHAR(C_SERVICOS.VRFATURADO, '999G999G999G999D99', 'NLS_NUMERIC_CHARACTERS = '',.'' ')), ''));
                    V_DSSERVORCANF  := REPLACE(V_DSSERVORCANF,'[MEDVARIAVEIS]', NVL(V_MEDVARIAVEIS, ''));
                    V_DSSERVORCABOL := REPLACE(V_DSSERVORCABOL,'[MEDVARIAVEIS]', NVL(V_MEDVARIAVEIS, ''));

                    /* Corta a descricao da NF para caber em 3000 characteres */
                    IF (LENGTH(V_DSSERVORCANF) > 3000) THEN
                        V_DSSERVORCANF := SUBSTR(V_DSSERVORCANF, 0, 3000);
                    END IF;

                    /*Atualiza a descricao do produto da NF*/
                    UPDATE ITEMPRODUTO
                       SET DSPRODEMIS = V_DSSERVORCANF
                     WHERE NRLANCTONF = C_NFFECHAMENTO.NRLANCTONF
                       AND CDFILIAL   = C_NFFECHAMENTO.CDFILIAL
                       AND CDPRODUTO  = C_SERVICOS.CDPRODFATSERV
                       AND NRORG      = P_NRORG;
                END LOOP; --C_SERVICOS

                /* Corta a descricao do boleto para caber em 400 characteres */
                IF (LENGTH(V_DSSERVORCABOL) > 400) THEN
                    V_DSSERVORCABOL := SUBSTR(V_DSSERVORCABOL, 0, 400);
                END IF;
                
                /* Atualiza o Boleto da NF */
                UPDATE CONTARECEBER
                   SET DSCONTAREC = V_DSSERVORCABOL
                 WHERE NRLANCTONF = C_NFFECHAMENTO.NRLANCTONF
                   AND CDFILIAL = C_NFFECHAMENTO.CDFILIAL
                   AND NRORG = P_NRORG;

            END LOOP; --C_ITENSVENC

        EXCEPTION WHEN OTHERS THEN
            BEGIN
                V_DEUERRO := TRUE;

                V_MSGERRO := 'Erro inesperado ao realizar fechamento de NF para os contratos '|| C_NFFECHAMENTO.NRCONTRATOFCT ||': '|| SQLERRM;

                INSERT INTO FCT_ERROSAPURACAOFATURA (
                    NRFATURACONT,           DSERRO,          CDOPERADOR,
                    DTINCLUSAO,             NRORG
                )
                VALUES (
                    C_NFFECHAMENTO.NRFATURACONT,    V_MSGERRO,       P_CDOPERINCLUSAO,
                    V_DATAATUAL,                    P_NRORG
                );
                CONTINUE;
            END;
        END; --tratamento de erro

    END LOOP; --C_NFFECHAMENTO

    DELETE FROM LISTA
     WHERE NRLISTA = V_LISTANF;

    IF (V_DEUERRO = TRUE) THEN
        COMMIT;
        RAISE_APPLICATION_ERROR(-20000, 'Ocorreram erros na realizacao do processo.');
    END IF;

    COMMIT;
END;
/