create or replace PACKAGE UTIL_OTIMIZADOR AS

   PROCEDURE EXPORTA_ITEM_FREQ_GR_PRAT(P_NRVIGENCIA IN NUMBER, -- NUMERO DA VIGENCIA DE ORIGEM
                                       P_CDFILIAL IN FILIAL.CDFILIAL%TYPE, -- CODIGO DA FILIAL DE ORIGEM
                                       P_CDSERVFILI IN SERVICO.CDSERVFILI%TYPE, -- CODIGO DO SERVICO DE ORIGEM
                                       P_IDTIPORESTRICAO IN VARCHAR2, -- TIPO DE RESTRICAO CONTRATUAL = PLANEJADO OU CONTRATO
                                       P_NRLISTA_DEST IN LISTA.NRLISTA%TYPE, -- NUMERO DE UMA LISTA CUJO CAMPO CDLISTA COMPOSTO DE CDFILIAL||CDSERVFILI||NRVIGENCIA
                                       P_NRLISTA IN LISTA.NRLISTA%TYPE, -- NUMERO DE UMA LISTA CUJO CAMPO CDLISTA CONTEM A PK DOS ITENS SELECIONADO
                                       P_IDOPCAO IN VARCHAR2, -- SOBREPOR OU ACRESCENTAR 
                                       P_CDOPERADOR IN OPERADOR.CDOPERADOR%TYPE,-- CODIGO DO OPERADOR LOGADO
                                       P_LISTA_ERROS OUT VARCHAR2); -- LISTA DE ERROS RETORNADOS

   PROCEDURE EXPORTA_ITEM_REST_PROD_GR(P_NRVIGENCIA IN NUMBER, -- NUMERO DA VIGENCIA DE ORIGEM
                                       P_CDFILIAL IN FILIAL.CDFILIAL%TYPE, -- CODIGO DA FILIAL DE ORIGEM
                                       P_CDSERVFILI IN SERVICO.CDSERVFILI%TYPE, -- CODIGO DO SERVICO DE ORIGEM
                                       P_IDTIPORESTRICAO IN VARCHAR2, -- TIPO DE RESTRICAO CONTRATUAL = PLANEJADO OU CONTRATO
                                       P_NRLISTA_DEST IN LISTA.NRLISTA%TYPE, -- NUMERO DE UMA LISTA CUJO CAMPO CDLISTA COMPOSTO DE CDFILIAL||CDSERVFILI||NRVIGENCIA
                                       P_NRLISTA IN LISTA.NRLISTA%TYPE, -- NUMERO DE UMA LISTA CUJO CAMPO CDLISTA CONTEM A PK DOS ITENS SELECIONADO
                                       P_IDOPCAO IN VARCHAR2, -- SOBREPOR OU ACRESCENTAR 
                                       P_CDOPERADOR IN OPERADOR.CDOPERADOR%TYPE,-- CODIGO DO OPERADOR LOGADO
                                       P_LISTA_ERROS OUT VARCHAR2); -- LISTA DE ERROS RETORNADOS
      
   PROCEDURE EXPORTA_ITEM_LIM_PERC_GR(P_NRVIGENCIA IN NUMBER, -- NUMERO DA VIGENCIA DE ORIGEM
                                      P_CDFILIAL IN FILIAL.CDFILIAL%TYPE, -- CODIGO DA FILIAL DE ORIGEM
                                      P_CDSERVFILI IN SERVICO.CDSERVFILI%TYPE, -- CODIGO DO SERVICO DE ORIGEM
                                      P_IDTIPORESTRICAO IN VARCHAR2, -- TIPO DE RESTRICAO CONTRATUAL = PLANEJADO OU CONTRATO
                                      P_NRLISTA_DEST IN LISTA.NRLISTA%TYPE, -- NUMERO DE UMA LISTA CUJO CAMPO CDLISTA COMPOSTO DE CDFILIAL||CDSERVFILI||NRVIGENCIA
                                      P_NRLISTA IN LISTA.NRLISTA%TYPE, -- NUMERO DE UMA LISTA CUJO CAMPO CDLISTA CONTEM A PK DOS ITENS SELECIONADO
                                      P_IDOPCAO IN VARCHAR2, -- SOBREPOR OU ACRESCENTAR 
                                      P_CDOPERADOR IN OPERADOR.CDOPERADOR%TYPE,-- CODIGO DO OPERADOR LOGADO
                                      P_LISTA_ERROS OUT VARCHAR2); -- LISTA DE ERROS RETORNADOS      


   PROCEDURE EXPORTA_ITEM_FREQ_GR_OPC_PRAT(P_NRVIGENCIA IN NUMBER, -- NUMERO DA VIGENCIA DE ORIGEM
                                           P_CDFILIAL IN FILIAL.CDFILIAL%TYPE, -- CODIGO DA FILIAL DE ORIGEM
                                           P_CDSERVFILI IN SERVICO.CDSERVFILI%TYPE, -- CODIGO DO SERVICO DE ORIGEM
                                           P_IDTIPORESTRICAO IN VARCHAR2, -- TIPO DE RESTRICAO CONTRATUAL = PLANEJADO OU CONTRATO
                                           P_NRLISTA_DEST IN LISTA.NRLISTA%TYPE, -- NUMERO DE UMA LISTA CUJO CAMPO CDLISTA COMPOSTO DE CDFILIAL||CDSERVFILI||NRVIGENCIA
                                           P_NRLISTA IN LISTA.NRLISTA%TYPE, -- NUMERO DE UMA LISTA CUJO CAMPO CDLISTA CONTEM A PK DOS ITENS SELECIONADO
                                           P_IDOPCAO IN VARCHAR2, -- SOBREPOR OU ACRESCENTAR 
                                           P_CDOPERADOR IN OPERADOR.CDOPERADOR%TYPE,-- CODIGO DO OPERADOR LOGADO
                                           P_LISTA_ERROS OUT VARCHAR2); -- LISTA DE ERROS RETORNADOS

   PROCEDURE EXPORTA_ITEM_FREQ_PROD_GR(P_NRVIGENCIA IN NUMBER, -- NUMERO DA VIGENCIA DE ORIGEM
                                       P_CDFILIAL IN FILIAL.CDFILIAL%TYPE, -- CODIGO DA FILIAL DE ORIGEM
                                       P_CDSERVFILI IN SERVICO.CDSERVFILI%TYPE, -- CODIGO DO SERVICO DE ORIGEM
                                       P_IDTIPORESTRICAO IN VARCHAR2, -- TIPO DE RESTRICAO CONTRATUAL = PLANEJADO OU CONTRATO
                                       P_NRLISTA_DEST IN LISTA.NRLISTA%TYPE, -- NUMERO DE UMA LISTA CUJO CAMPO CDLISTA COMPOSTO DE CDFILIAL||CDSERVFILI||NRVIGENCIA
                                       P_NRLISTA IN LISTA.NRLISTA%TYPE, -- NUMERO DE UMA LISTA CUJO CAMPO CDLISTA CONTEM A PK DOS ITENS SELECIONADO
                                       P_IDOPCAO IN VARCHAR2, -- SOBREPOR OU ACRESCENTAR 
                                       P_CDOPERADOR IN OPERADOR.CDOPERADOR%TYPE,-- CODIGO DO OPERADOR LOGADO
                                       P_LISTA_ERROS OUT VARCHAR2); -- LISTA DE ERROS RETORNADOS

   PROCEDURE EXPORTA_ITEM_UTIL_PRAT_SERV(P_NRVIGENCIA IN NUMBER, -- NUMERO DA VIGENCIA DE ORIGEM
                                         P_CDFILIAL IN FILIAL.CDFILIAL%TYPE, -- CODIGO DA FILIAL DE ORIGEM
                                         P_CDSERVFILI IN SERVICO.CDSERVFILI%TYPE, -- CODIGO DO SERVICO DE ORIGEM
                                         P_IDTIPORESTRICAO IN VARCHAR2, -- TIPO DE RESTRICAO CONTRATUAL = PLANEJADO OU CONTRATO
                                         P_NRLISTA_DEST IN LISTA.NRLISTA%TYPE, -- NUMERO DE UMA LISTA CUJO CAMPO CDLISTA COMPOSTO DE CDFILIAL||CDSERVFILI||NRVIGENCIA
                                         P_NRLISTA IN LISTA.NRLISTA%TYPE, -- NUMERO DE UMA LISTA CUJO CAMPO CDLISTA CONTEM A PK DOS ITENS SELECIONADO
                                         P_IDOPCAO IN VARCHAR2, -- SOBREPOR OU ACRESCENTAR 
                                         P_CDOPERADOR IN OPERADOR.CDOPERADOR%TYPE,-- CODIGO DO OPERADOR LOGADO
                                         P_LISTA_ERROS OUT VARCHAR2); -- LISTA DE ERROS RETORNADOS

   PROCEDURE EXPORTA_ITEM_FREQ_PRAT_MES(P_NRVIGENCIA IN NUMBER, -- NUMERO DA VIGENCIA DE ORIGEM
                                        P_CDFILIAL IN FILIAL.CDFILIAL%TYPE, -- CODIGO DA FILIAL DE ORIGEM
                                        P_CDSERVFILI IN SERVICO.CDSERVFILI%TYPE, -- CODIGO DO SERVICO DE ORIGEM
                                        P_IDTIPORESTRICAO IN VARCHAR2, -- TIPO DE RESTRICAO CONTRATUAL = PLANEJADO OU CONTRATO
                                        P_NRLISTA_DEST IN LISTA.NRLISTA%TYPE, -- NUMERO DE UMA LISTA CUJO CAMPO CDLISTA COMPOSTO DE CDFILIAL||CDSERVFILI||NRVIGENCIA
                                        P_NRLISTA IN LISTA.NRLISTA%TYPE, -- NUMERO DE UMA LISTA CUJO CAMPO CDLISTA CONTEM A PK DOS ITENS SELECIONADO
                                        P_IDOPCAO IN VARCHAR2, -- SOBREPOR OU ACRESCENTAR 
                                        P_CDOPERADOR IN OPERADOR.CDOPERADOR%TYPE,-- CODIGO DO OPERADOR LOGADO
                                        P_LISTA_ERROS OUT VARCHAR2); -- LISTA DE ERROS RETORNADOS

END UTIL_OTIMIZADOR;
/

create or replace PACKAGE BODY UTIL_OTIMIZADOR AS 

   /*PROCEDURE PARA EXPORTAR ITENS SELECIONADOS DE UMA VIGENCIA DE FREQUENCIA DE GRUPO DE PRATO NO MES*/
   PROCEDURE EXPORTA_ITEM_FREQ_GR_PRAT(
      P_NRVIGENCIA IN NUMBER, -- NUMERO DA VIGENCIA DE ORIGEM
      P_CDFILIAL IN FILIAL.CDFILIAL%TYPE, -- CODIGO DA FILIAL DE ORIGEM
      P_CDSERVFILI IN SERVICO.CDSERVFILI%TYPE, -- CODIGO DO SERVICO DE ORIGEM
      P_IDTIPORESTRICAO IN VARCHAR2, -- TIPO DE RESTRICAO CONTRATUAL = PLANEJADO OU CONTRATO
      P_NRLISTA_DEST IN LISTA.NRLISTA%TYPE, -- NUMERO DE UMA LISTA CUJO CAMPO CDLISTA COMPOSTO DE CDFILIAL||CDSERVFILI||NRVIGENCIA
      P_NRLISTA IN LISTA.NRLISTA%TYPE, -- NUMERO DE UMA LISTA CUJO CAMPO CDLISTA CONTEM A PK DOS ITENS SELECIONADO
      P_IDOPCAO IN VARCHAR2, -- SOBREPOR OU ACRESCENTAR 
      P_CDOPERADOR IN OPERADOR.CDOPERADOR%TYPE,-- CODIGO DO OPERADOR LOGADO
      P_LISTA_ERROS OUT VARCHAR2 -- LISTA DE ERROS RETORNADOS
      )
   AS
      V_FREQ_DEST VARCHAR2(20);
      V_LISTA_ERROS VARCHAR2(20);
      V_CDCHAVE VARCHAR2(500);
      V_MENSAGEM VARCHAR2(4000);      
   BEGIN
    
      /*CURSOR PARA FAZER UM LOOP NAS FILIAIS/SERVICOS DESTINOS E SUAS VIGENCIAS A EXPORTAR*/ 
      FOR C_DEST IN (SELECT V.NRVIGENCIA, V.DTVIGENCIA, V.DESCRICAO, V.CDFILIAL, SUBSTR(L.CDLISTA,5,5) AS CDSERVFILI, F.NRFREQGRPRATMES
                       FROM LISTA L INNER JOIN VIGFREQGRPRATMES V ON SUBSTR(L.CDLISTA,1,4) = V.CDFILIAL AND SUBSTR(L.CDLISTA,10) = V.NRVIGENCIA
                                    LEFT JOIN FREQGRPRATMES F ON F.CDFILIAL = SUBSTR(L.CDLISTA,1,4) AND F.CDSERVFILI = SUBSTR(L.CDLISTA,5,5) AND F.NRVIGENCIA = SUBSTR(L.CDLISTA,10)
                      WHERE L.NRLISTA = P_NRLISTA_DEST AND
                            V.IDTIPORESTRICAO = P_IDTIPORESTRICAO
                     ORDER BY V.NRVIGENCIA, SUBSTR(L.CDLISTA,5,5) 
      )LOOP
         /*PROCURA GRUPOS DE PRATOS NAO ASSOCIADOS AO SERVICO DESTINO PARA INSERIR NA LISTA DE ERROS*/
         FOR C_ERROS IN (SELECT G.CDGRUPOPRATO, G.NMGRUPOPRATO, G.NRORG
                           FROM ITFREQGRPRATMES I INNER JOIN LISTA L ON L.NRLISTA = P_NRLISTA AND L.CDLISTA = I.NRITFREQGRPRATMES
                                                  INNER JOIN GRUPOPRATOSERV GS ON GS.NRGRUPOPRATOSERV = I.NRGRUPOPRATOSERV
                                                  INNER JOIN GRUPOPRATO G ON G.NRGRUPOPRATO = GS.NRGRUPOPRATO
                           WHERE NOT EXISTS (SELECT GS2.NRGRUPOPRATO
                                              FROM GRUPOPRATOSERV GS2 
                                             WHERE GS2.NRGRUPOPRATO = GS.NRGRUPOPRATO AND
                                                   GS2.CDSERVFILI = C_DEST.CDSERVFILI)
         )LOOP
            /*INSERE NA TABELA DE ERROS*/
            V_CDCHAVE := (C_DEST.CDFILIAL||'|'||C_DEST.CDSERVFILI||'|'||C_ERROS.CDGRUPOPRATO);
            V_MENSAGEM := MSG('CONSISTE_GRUPOPRATO',C_DEST.CDFILIAL, C_DEST.CDSERVFILI, C_ERROS.CDGRUPOPRATO||' - '||C_ERROS.NMGRUPOPRATO);
            INSERE_LISTA_ERROS(C_DEST.CDFILIAL,V_MENSAGEM,P_CDOPERADOR, C_ERROS.NRORG, V_LISTA_ERROS, NULL, V_CDCHAVE);
         END LOOP;   

         /*SE NAO EXISTE A FREQUENCIA PARA O SERVICO DESTINO ENTAO INSERE A FREQUENCIA PARA O SERVICO PRIMEIRO*/
         IF C_DEST.NRFREQGRPRATMES IS NULL THEN
            NOVO_CODIGO('FREQGRPRATMES',V_FREQ_DEST);
            INSERT INTO FREQGRPRATMES (NRFREQGRPRATMES, CDFILIAL, CDSERVFILI, DTVIGENCIA, DSFREQGRPRATMES, DTINCLUSAO, CDOPERINCLUSAO, NRVIGENCIA) VALUES
                                      (V_FREQ_DEST, C_DEST.CDFILIAL, C_DEST.CDSERVFILI, C_DEST.DTVIGENCIA, C_DEST.DESCRICAO, SYSDATE, P_CDOPERADOR, C_DEST.NRVIGENCIA);            
         END IF;
         /*SE A OPCAO FOR SOBREPOR ENTAO VAI EXCLUIR OS ITENS NA VIGENCIA DESTINO SE EXISTIR*/
         IF P_IDOPCAO = 'SOBREPOR' AND C_DEST.NRFREQGRPRATMES IS NOT NULL THEN
            DELETE 
              FROM ITFREQGRPRATMES
             WHERE NRFREQGRPRATMES = C_DEST.NRFREQGRPRATMES;
         END IF;
         V_FREQ_DEST := NVL(C_DEST.NRFREQGRPRATMES, V_FREQ_DEST);   

         /*INSERE OS ITENS DA VIGENCIA NO SERVICO DESTINO ACRESCENTANDO OS QUE AINDA NAO EXISTEM*/
         INSERT INTO ITFREQGRPRATMES (NRITFREQGRPRATMES, NRFREQGRPRATMES, NRMINFREQGRPRATMES, NRMAXFREQGRPRATMES, NRMAXFREQGRPRATSEM, DTINCLUSAO, CDOPERINCLUSAO, NRGRUPOPRATOSERV)
         (SELECT RETORNA_NOVO_CODIGO('ITFREQGRPRATMES', 1), V_FREQ_DEST, NRMINFREQGRPRATMES, NRMAXFREQGRPRATMES, NRMAXFREQGRPRATSEM, SYSDATE, P_CDOPERADOR, NRGRUPOPRATOSERV
            FROM(SELECT NRMINFREQGRPRATMES, NRMAXFREQGRPRATMES, NRMAXFREQGRPRATSEM, GS2.NRGRUPOPRATOSERV
                   FROM ITFREQGRPRATMES I INNER JOIN LISTA L ON L.NRLISTA = P_NRLISTA AND L.CDLISTA = I.NRITFREQGRPRATMES
                                          INNER JOIN GRUPOPRATOSERV GS ON GS.NRGRUPOPRATOSERV = I.NRGRUPOPRATOSERV
                                          INNER JOIN GRUPOPRATOSERV GS2 ON GS2.NRGRUPOPRATO = GS.NRGRUPOPRATO AND GS2.CDSERVFILI = C_DEST.CDSERVFILI
                  WHERE NOT EXISTS (SELECT I2.NRGRUPOPRATOSERV
                                      FROM ITFREQGRPRATMES I2 
                                     WHERE I2.NRFREQGRPRATMES = V_FREQ_DEST AND
                                           I2.NRGRUPOPRATOSERV = GS2.NRGRUPOPRATOSERV))
         );
         COMMIT;
      END LOOP;
      P_LISTA_ERROS := V_LISTA_ERROS;
   END;


   /*PROCEDURE PARA EXPORTAR ITENS SELECIONADOS DE UMA VIGENCIA DE RESTRICAO DE PRODUTOS POR GRUPO DE PRATO*/
   PROCEDURE EXPORTA_ITEM_REST_PROD_GR(
      P_NRVIGENCIA IN NUMBER, -- NUMERO DA VIGENCIA DE ORIGEM
      P_CDFILIAL IN FILIAL.CDFILIAL%TYPE, -- CODIGO DA FILIAL DE ORIGEM
      P_CDSERVFILI IN SERVICO.CDSERVFILI%TYPE, -- CODIGO DO SERVICO DE ORIGEM
      P_IDTIPORESTRICAO IN VARCHAR2, -- TIPO DE RESTRICAO CONTRATUAL = PLANEJADO OU CONTRATO
      P_NRLISTA_DEST IN LISTA.NRLISTA%TYPE, -- NUMERO DE UMA LISTA CUJO CAMPO CDLISTA COMPOSTO DE CDFILIAL||CDSERVFILI||NRVIGENCIA
      P_NRLISTA IN LISTA.NRLISTA%TYPE, -- NUMERO DE UMA LISTA CUJO CAMPO CDLISTA CONTEM A PK DOS ITENS SELECIONADO
      P_IDOPCAO IN VARCHAR2, -- SOBREPOR OU ACRESCENTAR 
      P_CDOPERADOR IN OPERADOR.CDOPERADOR%TYPE,-- CODIGO DO OPERADOR LOGADO
      P_LISTA_ERROS OUT VARCHAR2 -- LISTA DE ERROS RETORNADOS
      )
   AS
      V_LISTA_ERROS VARCHAR2(20);
      V_CDCHAVE VARCHAR2(500);
      V_MENSAGEM VARCHAR2(4000);      
   BEGIN
      /*CURSOR PARA FAZER UM LOOP NAS FILIAIS/SERVICOS DESTINOS E SUAS VIGENCIAS A EXPORTAR*/ 
      FOR C_DEST IN (SELECT V.NRVIGENCIA, V.DTVIGENCIA, V.DESCRICAO, V.CDFILIAL, SUBSTR(L.CDLISTA,5,5) AS CDSERVFILI
                       FROM LISTA L INNER JOIN VIGRESTPRODGR V ON SUBSTR(L.CDLISTA,1,4) = V.CDFILIAL AND SUBSTR(L.CDLISTA,10) = V.NRVIGENCIA
                      WHERE L.NRLISTA = P_NRLISTA_DEST AND
                            V.IDTIPORESTRICAO = P_IDTIPORESTRICAO
                     ORDER BY V.NRVIGENCIA, SUBSTR(L.CDLISTA,5,5) 
      )LOOP

         /*PROCURA GRUPOS DE PRATOS NAO ASSOCIADOS AO SERVICO DESTINO PARA INSERIR NA LISTA DE ERROS*/
         FOR C_ERROS IN (SELECT DISTINCT G.CDGRUPOPRATO, G.NMGRUPOPRATO, G.NRORG
                           FROM RESTPRODGR R INNER JOIN LISTA L ON L.NRLISTA = P_NRLISTA AND L.CDLISTA = R.NRRESTPRODGR
                                                  INNER JOIN GRUPOPRATOSERV GS ON GS.NRGRUPOPRATOSERV = R.NRGRUPOPRATOSERV
                                                  INNER JOIN GRUPOPRATO G ON G.NRGRUPOPRATO = GS.NRGRUPOPRATO
                           WHERE NOT EXISTS (SELECT GS2.NRGRUPOPRATO
                                              FROM GRUPOPRATOSERV GS2 
                                             WHERE GS2.NRGRUPOPRATO = GS.NRGRUPOPRATO AND
                                                   GS2.CDSERVFILI = C_DEST.CDSERVFILI)
         )LOOP
            /*INSERE NA TABELA DE ERROS*/
            V_CDCHAVE := (C_DEST.CDFILIAL||'|'||C_DEST.CDSERVFILI||'|'||C_ERROS.CDGRUPOPRATO);
            V_MENSAGEM := MSG('CONSISTE_GRUPOPRATO',C_DEST.CDFILIAL, C_DEST.CDSERVFILI, C_ERROS.CDGRUPOPRATO||' - '||C_ERROS.NMGRUPOPRATO);
            INSERE_LISTA_ERROS(C_DEST.CDFILIAL,V_MENSAGEM,P_CDOPERADOR, C_ERROS.NRORG, V_LISTA_ERROS, NULL, V_CDCHAVE);
         END LOOP;   

         /*SE A OPCAO FOR SOBREPOR ENTAO VAI EXCLUIR OS ITENS NA VIGENCIA DESTINO SE EXISTIR*/
         IF P_IDOPCAO = 'SOBREPOR' THEN
            DELETE 
              FROM RESTPRODGR
             WHERE NRVIGENCIA = C_DEST.NRVIGENCIA AND
                   CDFILIAL = C_DEST.CDFILIAL AND
                   CDSERVFILI = C_DEST.CDSERVFILI;
         END IF;

         /*INSERE OS ITENS DA VIGENCIA NO SERVICO DESTINO ACRESCENTANDO OS QUE AINDA NAO EXISTEM*/
         INSERT INTO RESTPRODGR (NRRESTPRODGR, CDFILIAL, CDSERVFILI, CDPRODUTO, DTINCLUSAO, CDOPERINCLUSAO, NRGRUPOPRATOSERV, NRVIGENCIA)
         (SELECT RETORNA_NOVO_CODIGO('RESTPRODGR', 1), C_DEST.CDFILIAL, C_DEST.CDSERVFILI, CDPRODUTO, SYSDATE, P_CDOPERADOR, NRGRUPOPRATOSERV, C_DEST.NRVIGENCIA
            FROM(SELECT R.CDPRODUTO, GS2.NRGRUPOPRATOSERV
                   FROM RESTPRODGR R INNER JOIN LISTA L ON L.NRLISTA = P_NRLISTA AND L.CDLISTA = R.NRRESTPRODGR
                                          INNER JOIN GRUPOPRATOSERV GS ON GS.NRGRUPOPRATOSERV = R.NRGRUPOPRATOSERV
                                          INNER JOIN GRUPOPRATOSERV GS2 ON GS2.NRGRUPOPRATO = GS.NRGRUPOPRATO AND GS2.CDSERVFILI = C_DEST.CDSERVFILI
                  WHERE NOT EXISTS (SELECT R2.NRGRUPOPRATOSERV
                                      FROM RESTPRODGR R2 
                                     WHERE R2.NRVIGENCIA = C_DEST.NRVIGENCIA AND
                                           R2.CDFILIAL = C_DEST.CDFILIAL AND
                                           R2.CDSERVFILI = C_DEST.CDSERVFILI AND
                                           R2.NRGRUPOPRATOSERV = GS2.NRGRUPOPRATOSERV))
         );
         COMMIT;
      END LOOP;
      P_LISTA_ERROS := V_LISTA_ERROS;
   END;


   /*PROCEDURE PARA EXPORTAR ITENS SELECIONADOS DE UMA VIGENCIA DE LIMITE PERCAPITA DE PRODUTO POR GRUPO DE PRATO NO MES*/
   PROCEDURE EXPORTA_ITEM_LIM_PERC_GR(
      P_NRVIGENCIA IN NUMBER, -- NUMERO DA VIGENCIA DE ORIGEM
      P_CDFILIAL IN FILIAL.CDFILIAL%TYPE, -- CODIGO DA FILIAL DE ORIGEM
      P_CDSERVFILI IN SERVICO.CDSERVFILI%TYPE, -- CODIGO DO SERVICO DE ORIGEM
      P_IDTIPORESTRICAO IN VARCHAR2, -- TIPO DE RESTRICAO CONTRATUAL = PLANEJADO OU CONTRATO
      P_NRLISTA_DEST IN LISTA.NRLISTA%TYPE, -- NUMERO DE UMA LISTA CUJO CAMPO CDLISTA COMPOSTO DE CDFILIAL||CDSERVFILI||NRVIGENCIA
      P_NRLISTA IN LISTA.NRLISTA%TYPE, -- NUMERO DE UMA LISTA CUJO CAMPO CDLISTA CONTEM A PK DOS ITENS SELECIONADO
      P_IDOPCAO IN VARCHAR2, -- SOBREPOR OU ACRESCENTAR 
      P_CDOPERADOR IN OPERADOR.CDOPERADOR%TYPE,-- CODIGO DO OPERADOR LOGADO
      P_LISTA_ERROS OUT VARCHAR2 -- LISTA DE ERROS RETORNADOS
      )
   AS
      V_FREQ_DEST VARCHAR2(20);
      V_LISTA_ERROS VARCHAR2(20);
      V_CDCHAVE VARCHAR2(500);
      V_MENSAGEM VARCHAR2(4000);      
   BEGIN
    
      /*CURSOR PARA FAZER UM LOOP NAS FILIAIS/SERVICOS DESTINOS E SUAS VIGENCIAS A EXPORTAR*/ 
      FOR C_DEST IN (SELECT V.NRVIGENCIA, V.DTVIGENCIA, V.DESCRICAO, V.CDFILIAL, SUBSTR(L.CDLISTA,5,5) AS CDSERVFILI, F.NRLIMPESERGR
                       FROM LISTA L INNER JOIN VIGLIMPESERGR V ON SUBSTR(L.CDLISTA,1,4) = V.CDFILIAL AND SUBSTR(L.CDLISTA,10) = V.NRVIGENCIA
                                    LEFT JOIN LIMPESERGR F ON F.CDFILIAL = SUBSTR(L.CDLISTA,1,4) AND F.CDSERVFILI = SUBSTR(L.CDLISTA,5,5) AND F.NRVIGENCIA = SUBSTR(L.CDLISTA,10)
                      WHERE L.NRLISTA = P_NRLISTA_DEST AND
                            V.IDTIPORESTRICAO = P_IDTIPORESTRICAO
                     ORDER BY V.NRVIGENCIA, SUBSTR(L.CDLISTA,5,5) 
      )LOOP
         /*PROCURA GRUPOS DE PRATOS NAO ASSOCIADOS AO SERVICO DESTINO PARA INSERIR NA LISTA DE ERROS*/
         FOR C_ERROS IN (SELECT DISTINCT G.CDGRUPOPRATO, G.NMGRUPOPRATO, G.NRORG
                           FROM ITLIMPESERGR I INNER JOIN LISTA L ON L.NRLISTA = P_NRLISTA AND L.CDLISTA = I.NRITLIMPESERGR
                                                  INNER JOIN GRUPOPRATOSERV GS ON GS.NRGRUPOPRATOSERV = I.NRGRUPOPRATOSERV
                                                  INNER JOIN GRUPOPRATO G ON G.NRGRUPOPRATO = GS.NRGRUPOPRATO
                           WHERE NOT EXISTS (SELECT GS2.NRGRUPOPRATO
                                              FROM GRUPOPRATOSERV GS2 
                                             WHERE GS2.NRGRUPOPRATO = GS.NRGRUPOPRATO AND
                                                   GS2.CDSERVFILI = C_DEST.CDSERVFILI)
         )LOOP
            /*INSERE NA TABELA DE ERROS*/
            V_CDCHAVE := (C_DEST.CDFILIAL||'|'||C_DEST.CDSERVFILI||'|'||C_ERROS.CDGRUPOPRATO);
            V_MENSAGEM := MSG('CONSISTE_GRUPOPRATO',C_DEST.CDFILIAL, C_DEST.CDSERVFILI, C_ERROS.CDGRUPOPRATO||' - '||C_ERROS.NMGRUPOPRATO);
            INSERE_LISTA_ERROS(C_DEST.CDFILIAL,V_MENSAGEM,P_CDOPERADOR, C_ERROS.NRORG, V_LISTA_ERROS, NULL, V_CDCHAVE);
         END LOOP;   

         /*SE NAO EXISTE A FREQUENCIA PARA O SERVICO DESTINO ENTAO INSERE A FREQUENCIA PARA O SERVICO PRIMEIRO*/
         IF C_DEST.NRLIMPESERGR IS NULL THEN
            NOVO_CODIGO('LIMPESERGR',V_FREQ_DEST);
            INSERT INTO LIMPESERGR (NRLIMPESERGR, CDFILIAL, CDSERVFILI, DTVIGENCIA, DSLIMPESERGR, DTINCLUSAO, CDOPERINCLUSAO, NRVIGENCIA) VALUES
                                      (V_FREQ_DEST, C_DEST.CDFILIAL, C_DEST.CDSERVFILI, C_DEST.DTVIGENCIA, C_DEST.DESCRICAO, SYSDATE, P_CDOPERADOR, C_DEST.NRVIGENCIA);            
         END IF;
         /*SE A OPCAO FOR SOBREPOR ENTAO VAI EXCLUIR OS ITENS NA VIGENCIA DESTINO SE EXISTIR*/
         IF P_IDOPCAO = 'SOBREPOR' AND C_DEST.NRLIMPESERGR IS NOT NULL THEN
            DELETE 
              FROM ITLIMPESERGR
             WHERE NRLIMPESERGR = C_DEST.NRLIMPESERGR;
         END IF;
         V_FREQ_DEST := NVL(C_DEST.NRLIMPESERGR, V_FREQ_DEST);   

         /*INSERE OS ITENS DA VIGENCIA NO SERVICO DESTINO ACRESCENTANDO OS QUE AINDA NAO EXISTEM*/
         INSERT INTO ITLIMPESERGR (NRITLIMPESERGR, NRLIMPESERGR, CDPRODUTO, QTMINLIMPERSERGR, QTMAXLIMPERSERGR, DTINCLUSAO, CDOPERINCLUSAO, NRGRUPOPRATOSERV)
         (SELECT RETORNA_NOVO_CODIGO('ITLIMPESERGR', 1), V_FREQ_DEST, CDPRODUTO, QTMINLIMPERSERGR, QTMAXLIMPERSERGR, SYSDATE, P_CDOPERADOR, NRGRUPOPRATOSERV
            FROM(SELECT CDPRODUTO, QTMINLIMPERSERGR, QTMAXLIMPERSERGR, GS2.NRGRUPOPRATOSERV
                   FROM ITLIMPESERGR I INNER JOIN LISTA L ON L.NRLISTA = P_NRLISTA AND L.CDLISTA = I.NRITLIMPESERGR
                                       INNER JOIN GRUPOPRATOSERV GS ON GS.NRGRUPOPRATOSERV = I.NRGRUPOPRATOSERV
                                       INNER JOIN GRUPOPRATOSERV GS2 ON GS2.NRGRUPOPRATO = GS.NRGRUPOPRATO AND GS2.CDSERVFILI = C_DEST.CDSERVFILI
                  WHERE NOT EXISTS (SELECT I2.NRGRUPOPRATOSERV
                                      FROM ITLIMPESERGR I2 
                                     WHERE I2.NRLIMPESERGR = V_FREQ_DEST AND
                                           I2.NRGRUPOPRATOSERV = GS2.NRGRUPOPRATOSERV AND
                                           I2.CDPRODUTO = I.CDPRODUTO))
         );
         COMMIT;
      END LOOP;
      P_LISTA_ERROS := V_LISTA_ERROS;
   END;

   /*PROCEDURE PARA EXPORTAR ITENS SELECIONADOS DE UMA VIGENCIA DE FREQUENCIA DE OPCOES GRUPO DE PRATO NO MES*/
   PROCEDURE EXPORTA_ITEM_FREQ_GR_OPC_PRAT(
      P_NRVIGENCIA IN NUMBER, -- NUMERO DA VIGENCIA DE ORIGEM
      P_CDFILIAL IN FILIAL.CDFILIAL%TYPE, -- CODIGO DA FILIAL DE ORIGEM
      P_CDSERVFILI IN SERVICO.CDSERVFILI%TYPE, -- CODIGO DO SERVICO DE ORIGEM
      P_IDTIPORESTRICAO IN VARCHAR2, -- TIPO DE RESTRICAO CONTRATUAL = PLANEJADO OU CONTRATO
      P_NRLISTA_DEST IN LISTA.NRLISTA%TYPE, -- NUMERO DE UMA LISTA CUJO CAMPO CDLISTA COMPOSTO DE CDFILIAL||CDSERVFILI||NRVIGENCIA
      P_NRLISTA IN LISTA.NRLISTA%TYPE, -- NUMERO DE UMA LISTA CUJO CAMPO CDLISTA CONTEM A PK DOS ITENS SELECIONADO
      P_IDOPCAO IN VARCHAR2, -- SOBREPOR OU ACRESCENTAR 
      P_CDOPERADOR IN OPERADOR.CDOPERADOR%TYPE,-- CODIGO DO OPERADOR LOGADO
      P_LISTA_ERROS OUT VARCHAR2 -- LISTA DE ERROS RETORNADOS
      )
   AS
      V_FREQ_DEST VARCHAR2(20);
      V_LISTA_ERROS VARCHAR2(20);
      V_CDCHAVE VARCHAR2(500);
      V_MENSAGEM VARCHAR2(4000);      
   BEGIN
    
      /*CURSOR PARA FAZER UM LOOP NAS FILIAIS/SERVICOS DESTINOS E SUAS VIGENCIAS A EXPORTAR*/ 
      FOR C_DEST IN (SELECT V.NRVIGENCIA, V.DTVIGENCIA, V.DESCRICAO, V.CDFILIAL, SUBSTR(L.CDLISTA,5,5) AS CDSERVFILI, F.NRFREQOPCAGR
                       FROM LISTA L INNER JOIN VIGFREQOPCAGR V ON SUBSTR(L.CDLISTA,1,4) = V.CDFILIAL AND SUBSTR(L.CDLISTA,10) = V.NRVIGENCIA
                                    LEFT JOIN FREQOPCAGR F ON F.CDFILIAL = SUBSTR(L.CDLISTA,1,4) AND F.CDSERVFILI = SUBSTR(L.CDLISTA,5,5) AND F.NRVIGENCIA = SUBSTR(L.CDLISTA,10)
                      WHERE L.NRLISTA = P_NRLISTA_DEST AND
                            V.IDTIPORESTRICAO = P_IDTIPORESTRICAO
                     ORDER BY V.NRVIGENCIA, SUBSTR(L.CDLISTA,5,5) 
      )LOOP
         /*PROCURA GRUPOS DE PRATOS NAO ASSOCIADOS AO SERVICO DESTINO PARA INSERIR NA LISTA DE ERROS*/
         FOR C_ERROS IN (SELECT G.CDGRUPOPRATO, G.NMGRUPOPRATO, G.NRORG
                           FROM ITFREQOPCAGR I INNER JOIN LISTA L ON L.NRLISTA = P_NRLISTA AND L.CDLISTA = I.NRITFREQOPCAGR
                                                  INNER JOIN GRUPOPRATOSERV GS ON GS.NRGRUPOPRATOSERV = I.NRGRUPOPRATOSERV
                                                  INNER JOIN GRUPOPRATO G ON G.NRGRUPOPRATO = GS.NRGRUPOPRATO
                           WHERE NOT EXISTS (SELECT GS2.NRGRUPOPRATO
                                              FROM GRUPOPRATOSERV GS2 
                                             WHERE GS2.NRGRUPOPRATO = GS.NRGRUPOPRATO AND
                                                   GS2.CDSERVFILI = C_DEST.CDSERVFILI)
         )LOOP
            /*INSERE NA TABELA DE ERROS*/
            V_CDCHAVE := (C_DEST.CDFILIAL||'|'||C_DEST.CDSERVFILI||'|'||C_ERROS.CDGRUPOPRATO);
            V_MENSAGEM := MSG('CONSISTE_GRUPOPRATO',C_DEST.CDFILIAL, C_DEST.CDSERVFILI, C_ERROS.CDGRUPOPRATO||' - '||C_ERROS.NMGRUPOPRATO);
            INSERE_LISTA_ERROS(C_DEST.CDFILIAL,V_MENSAGEM,P_CDOPERADOR, C_ERROS.NRORG, V_LISTA_ERROS, NULL, V_CDCHAVE);
         END LOOP;   

         /*SE NAO EXISTE A FREQUENCIA PARA O SERVICO DESTINO ENTAO INSERE A FREQUENCIA PARA O SERVICO PRIMEIRO*/
         IF C_DEST.NRFREQOPCAGR IS NULL THEN
            NOVO_CODIGO('FREQOPCAGR',V_FREQ_DEST);
            INSERT INTO FREQOPCAGR (NRFREQOPCAGR, CDFILIAL, CDSERVFILI, DTVIGENCIA, DSFREQOPCAGR, DTINCLUSAO, CDOPERINCLUSAO, NRVIGENCIA) VALUES
                                      (V_FREQ_DEST, C_DEST.CDFILIAL, C_DEST.CDSERVFILI, C_DEST.DTVIGENCIA, C_DEST.DESCRICAO, SYSDATE, P_CDOPERADOR, C_DEST.NRVIGENCIA);            
         END IF;
         /*SE A OPCAO FOR SOBREPOR ENTAO VAI EXCLUIR OS ITENS NA VIGENCIA DESTINO SE EXISTIR*/
         IF P_IDOPCAO = 'SOBREPOR' AND C_DEST.NRFREQOPCAGR IS NOT NULL THEN
            DELETE 
              FROM ITFREQOPCAGR
             WHERE NRFREQOPCAGR = C_DEST.NRFREQOPCAGR;
         END IF;
         V_FREQ_DEST := NVL(C_DEST.NRFREQOPCAGR, V_FREQ_DEST);   

         /*INSERE OS ITENS DA VIGENCIA NO SERVICO DESTINO ACRESCENTANDO OS QUE AINDA NAO EXISTEM*/
         INSERT INTO ITFREQOPCAGR (NRITFREQOPCAGR, NRFREQOPCAGR, NRMINFREQOPCAGR, NRMAXFREQOPCAGR, NRMAXFREQOPCAGRSEM, DTINCLUSAO, CDOPERINCLUSAO, NRGRUPOPRATOSERV)
         (SELECT RETORNA_NOVO_CODIGO('ITFREQOPCAGRS', 1), V_FREQ_DEST, NRMINFREQOPCAGR, NRMAXFREQOPCAGR, NRMAXFREQOPCAGRSEM, SYSDATE, P_CDOPERADOR, NRGRUPOPRATOSERV
            FROM(SELECT NRMINFREQOPCAGR, NRMAXFREQOPCAGR, NRMAXFREQOPCAGRSEM, GS2.NRGRUPOPRATOSERV
                   FROM ITFREQOPCAGR I INNER JOIN LISTA L ON L.NRLISTA = P_NRLISTA AND L.CDLISTA = I.NRITFREQOPCAGR
                                          INNER JOIN GRUPOPRATOSERV GS ON GS.NRGRUPOPRATOSERV = I.NRGRUPOPRATOSERV
                                          INNER JOIN GRUPOPRATOSERV GS2 ON GS2.NRGRUPOPRATO = GS.NRGRUPOPRATO AND GS2.CDSERVFILI = C_DEST.CDSERVFILI
                  WHERE NOT EXISTS (SELECT I2.NRGRUPOPRATOSERV
                                      FROM ITFREQOPCAGR I2 
                                     WHERE I2.NRFREQOPCAGR = V_FREQ_DEST AND
                                           I2.NRGRUPOPRATOSERV = GS2.NRGRUPOPRATOSERV))
         );
         COMMIT;
      END LOOP;
      P_LISTA_ERROS := V_LISTA_ERROS;
   END;
   
   
   /*PROCEDURE PARA EXPORTAR ITENS SELECIONADOS DE UMA VIGENCIA DE FREQUENCIA DE PRODUTOS POR GRUPO DE PRATO NO MES*/
   PROCEDURE EXPORTA_ITEM_FREQ_PROD_GR(
      P_NRVIGENCIA IN NUMBER, -- NUMERO DA VIGENCIA DE ORIGEM
      P_CDFILIAL IN FILIAL.CDFILIAL%TYPE, -- CODIGO DA FILIAL DE ORIGEM
      P_CDSERVFILI IN SERVICO.CDSERVFILI%TYPE, -- CODIGO DO SERVICO DE ORIGEM
      P_IDTIPORESTRICAO IN VARCHAR2, -- TIPO DE RESTRICAO CONTRATUAL = PLANEJADO OU CONTRATO
      P_NRLISTA_DEST IN LISTA.NRLISTA%TYPE, -- NUMERO DE UMA LISTA CUJO CAMPO CDLISTA COMPOSTO DE CDFILIAL||CDSERVFILI||NRVIGENCIA
      P_NRLISTA IN LISTA.NRLISTA%TYPE, -- NUMERO DE UMA LISTA CUJO CAMPO CDLISTA CONTEM A PK DOS ITENS SELECIONADO
      P_IDOPCAO IN VARCHAR2, -- SOBREPOR OU ACRESCENTAR 
      P_CDOPERADOR IN OPERADOR.CDOPERADOR%TYPE,-- CODIGO DO OPERADOR LOGADO
      P_LISTA_ERROS OUT VARCHAR2 -- LISTA DE ERROS RETORNADOS
      )
   AS
      V_FREQ_DEST VARCHAR2(20);
      V_LISTA_ERROS VARCHAR2(20);
      V_CDCHAVE VARCHAR2(500);
      V_MENSAGEM VARCHAR2(4000);      
   BEGIN
    
      /*CURSOR PARA FAZER UM LOOP NAS FILIAIS/SERVICOS DESTINOS E SUAS VIGENCIAS A EXPORTAR*/ 
      FOR C_DEST IN (SELECT V.NRVIGENCIA, V.DTVIGENCIA, V.DESCRICAO, V.CDFILIAL, SUBSTR(L.CDLISTA,5,5) AS CDSERVFILI, F.NRFREQPRODGRPRAT
                       FROM LISTA L INNER JOIN VIGFREQPRODGRPRAT V ON SUBSTR(L.CDLISTA,1,4) = V.CDFILIAL AND SUBSTR(L.CDLISTA,10) = V.NRVIGENCIA
                                    LEFT JOIN FREQPRODGRPRAT F ON F.CDFILIAL = SUBSTR(L.CDLISTA,1,4) AND F.CDSERVFILI = SUBSTR(L.CDLISTA,5,5) AND F.NRVIGENCIA = SUBSTR(L.CDLISTA,10)
                      WHERE L.NRLISTA = P_NRLISTA_DEST AND
                            V.IDTIPORESTRICAO = P_IDTIPORESTRICAO
                     ORDER BY V.NRVIGENCIA, SUBSTR(L.CDLISTA,5,5) 
      )LOOP
         /*PROCURA GRUPOS DE PRATOS NAO ASSOCIADOS AO SERVICO DESTINO PARA INSERIR NA LISTA DE ERROS*/
         FOR C_ERROS IN (SELECT DISTINCT G.CDGRUPOPRATO, G.NMGRUPOPRATO, G.NRORG
                           FROM ITFREQPRODGRPRAT I INNER JOIN LISTA L ON L.NRLISTA = P_NRLISTA AND L.CDLISTA = I.NRITFREQPRODGRPRAT
                                                  INNER JOIN GRUPOPRATOSERV GS ON GS.NRGRUPOPRATOSERV = I.NRGRUPOPRATOSERV
                                                  INNER JOIN GRUPOPRATO G ON G.NRGRUPOPRATO = GS.NRGRUPOPRATO
                           WHERE NOT EXISTS (SELECT GS2.NRGRUPOPRATO
                                              FROM GRUPOPRATOSERV GS2 
                                             WHERE GS2.NRGRUPOPRATO = GS.NRGRUPOPRATO AND
                                                   GS2.CDSERVFILI = C_DEST.CDSERVFILI)
         )LOOP
            /*INSERE NA TABELA DE ERROS*/
            V_CDCHAVE := (C_DEST.CDFILIAL||'|'||C_DEST.CDSERVFILI||'|'||C_ERROS.CDGRUPOPRATO);
            V_MENSAGEM := MSG('CONSISTE_GRUPOPRATO',C_DEST.CDFILIAL, C_DEST.CDSERVFILI, C_ERROS.CDGRUPOPRATO||' - '||C_ERROS.NMGRUPOPRATO);
            INSERE_LISTA_ERROS(C_DEST.CDFILIAL,V_MENSAGEM,P_CDOPERADOR, C_ERROS.NRORG, V_LISTA_ERROS, NULL, V_CDCHAVE);
         END LOOP;   

         /*SE NAO EXISTE A FREQUENCIA PARA O SERVICO DESTINO ENTAO INSERE A FREQUENCIA PARA O SERVICO PRIMEIRO*/
         IF C_DEST.NRFREQPRODGRPRAT IS NULL THEN
            NOVO_CODIGO('FREQPRODGRPRAT',V_FREQ_DEST);
            INSERT INTO FREQPRODGRPRAT (NRFREQPRODGRPRAT, CDFILIAL, CDSERVFILI, DTVIGENCIA, DSFREQPRODGRPRAT, DTINCLUSAO, CDOPERINCLUSAO, NRVIGENCIA) VALUES
                                      (V_FREQ_DEST, C_DEST.CDFILIAL, C_DEST.CDSERVFILI, C_DEST.DTVIGENCIA, C_DEST.DESCRICAO, SYSDATE, P_CDOPERADOR, C_DEST.NRVIGENCIA);            
         END IF;
         /*SE A OPCAO FOR SOBREPOR ENTAO VAI EXCLUIR OS ITENS NA VIGENCIA DESTINO SE EXISTIR*/
         IF P_IDOPCAO = 'SOBREPOR' AND C_DEST.NRFREQPRODGRPRAT IS NOT NULL THEN
            DELETE 
              FROM ITFREQPRODGRPRAT
             WHERE NRFREQPRODGRPRAT = C_DEST.NRFREQPRODGRPRAT;
         END IF;
         V_FREQ_DEST := NVL(C_DEST.NRFREQPRODGRPRAT, V_FREQ_DEST);   

         /*INSERE OS ITENS DA VIGENCIA NO SERVICO DESTINO ACRESCENTANDO OS QUE AINDA NAO EXISTEM*/
         INSERT INTO ITFREQPRODGRPRAT (NRITFREQPRODGRPRAT, NRFREQPRODGRPRAT, CDPRODUTO, NRMINPRODGRPRAT, NRMAXPRODGRPRAT, NRMAXPRODGRPRATSEM, DTINCLUSAO, CDOPERINCLUSAO, NRGRUPOPRATOSERV)
         (SELECT RETORNA_NOVO_CODIGO('ITFREQPRODGRPRAT', 1), V_FREQ_DEST, CDPRODUTO, NRMINPRODGRPRAT, NRMAXPRODGRPRAT, NRMAXPRODGRPRATSEM, SYSDATE, P_CDOPERADOR, NRGRUPOPRATOSERV
            FROM(SELECT CDPRODUTO, NRMINPRODGRPRAT, NRMAXPRODGRPRAT, NRMAXPRODGRPRATSEM, GS2.NRGRUPOPRATOSERV
                   FROM ITFREQPRODGRPRAT I INNER JOIN LISTA L ON L.NRLISTA = P_NRLISTA AND L.CDLISTA = I.NRITFREQPRODGRPRAT
                                       INNER JOIN GRUPOPRATOSERV GS ON GS.NRGRUPOPRATOSERV = I.NRGRUPOPRATOSERV
                                       INNER JOIN GRUPOPRATOSERV GS2 ON GS2.NRGRUPOPRATO = GS.NRGRUPOPRATO AND GS2.CDSERVFILI = C_DEST.CDSERVFILI
                  WHERE NOT EXISTS (SELECT I2.NRGRUPOPRATOSERV
                                      FROM ITFREQPRODGRPRAT I2 
                                     WHERE I2.NRFREQPRODGRPRAT = V_FREQ_DEST AND
                                           I2.NRGRUPOPRATOSERV = GS2.NRGRUPOPRATOSERV AND
                                           I2.CDPRODUTO = I.CDPRODUTO))
         );
         COMMIT;
      END LOOP;
      P_LISTA_ERROS := V_LISTA_ERROS;
   END;   


   /*PROCEDURE PARA EXPORTAR ITENS SELECIONADOS DE UMA VIGENCIA DE UTILIZACAO DE GRUPO DE PRATO NA SEMANA*/
   PROCEDURE EXPORTA_ITEM_UTIL_PRAT_SERV(
      P_NRVIGENCIA IN NUMBER, -- NUMERO DA VIGENCIA DE ORIGEM
      P_CDFILIAL IN FILIAL.CDFILIAL%TYPE, -- CODIGO DA FILIAL DE ORIGEM
      P_CDSERVFILI IN SERVICO.CDSERVFILI%TYPE, -- CODIGO DO SERVICO DE ORIGEM
      P_IDTIPORESTRICAO IN VARCHAR2, -- TIPO DE RESTRICAO CONTRATUAL = PLANEJADO OU CONTRATO
      P_NRLISTA_DEST IN LISTA.NRLISTA%TYPE, -- NUMERO DE UMA LISTA CUJO CAMPO CDLISTA COMPOSTO DE CDFILIAL||CDSERVFILI||NRVIGENCIA
      P_NRLISTA IN LISTA.NRLISTA%TYPE, -- NUMERO DE UMA LISTA CUJO CAMPO CDLISTA CONTEM A PK DOS ITENS SELECIONADO
      P_IDOPCAO IN VARCHAR2, -- SOBREPOR OU ACRESCENTAR 
      P_CDOPERADOR IN OPERADOR.CDOPERADOR%TYPE,-- CODIGO DO OPERADOR LOGADO
      P_LISTA_ERROS OUT VARCHAR2 -- LISTA DE ERROS RETORNADOS
      )
   AS
      V_LISTA_ERROS VARCHAR2(20);
      V_CDCHAVE VARCHAR2(500);
      V_MENSAGEM VARCHAR2(4000);      
   BEGIN
      /*CURSOR PARA FAZER UM LOOP NAS FILIAIS/SERVICOS DESTINOS E SUAS VIGENCIAS A EXPORTAR*/ 
      FOR C_DEST IN (SELECT V.NRVIGENCIA, V.DTVIGENCIA, V.DESCRICAO, V.CDFILIAL, SUBSTR(L.CDLISTA,5,5) AS CDSERVFILI
                       FROM LISTA L INNER JOIN VIGUTILPRATOSERV V ON SUBSTR(L.CDLISTA,1,4) = V.CDFILIAL AND SUBSTR(L.CDLISTA,10) = V.NRVIGENCIA
                      WHERE L.NRLISTA = P_NRLISTA_DEST AND
                            V.IDTIPORESTRICAO = P_IDTIPORESTRICAO
                     ORDER BY V.NRVIGENCIA, SUBSTR(L.CDLISTA,5,5) 
      )LOOP

         /*PROCURA GRUPOS DE PRATOS NAO ASSOCIADOS AO SERVICO DESTINO PARA INSERIR NA LISTA DE ERROS*/
         FOR C_ERROS IN (SELECT G.CDGRUPOPRATO, G.NMGRUPOPRATO, G.NRORG
                           FROM UTILPRATOSERV R INNER JOIN LISTA L ON L.NRLISTA = P_NRLISTA AND L.CDLISTA = R.NRUTILPRATOSERV
                                                  INNER JOIN GRUPOPRATOSERV GS ON GS.NRGRUPOPRATOSERV = R.NRGRUPOPRATOSERV
                                                  INNER JOIN GRUPOPRATO G ON G.NRGRUPOPRATO = GS.NRGRUPOPRATO
                           WHERE NOT EXISTS (SELECT GS2.NRGRUPOPRATO
                                              FROM GRUPOPRATOSERV GS2 
                                             WHERE GS2.NRGRUPOPRATO = GS.NRGRUPOPRATO AND
                                                   GS2.CDSERVFILI = C_DEST.CDSERVFILI)
         )LOOP
            /*INSERE NA TABELA DE ERROS*/
            V_CDCHAVE := (C_DEST.CDFILIAL||'|'||C_DEST.CDSERVFILI||'|'||C_ERROS.CDGRUPOPRATO);
            V_MENSAGEM := MSG('CONSISTE_GRUPOPRATO',C_DEST.CDFILIAL, C_DEST.CDSERVFILI, C_ERROS.CDGRUPOPRATO||' - '||C_ERROS.NMGRUPOPRATO);
            INSERE_LISTA_ERROS(C_DEST.CDFILIAL,V_MENSAGEM,P_CDOPERADOR, C_ERROS.NRORG, V_LISTA_ERROS, NULL, V_CDCHAVE);
         END LOOP;   

         /*SE A OPCAO FOR SOBREPOR ENTAO VAI EXCLUIR OS ITENS NA VIGENCIA DESTINO SE EXISTIR*/
         IF P_IDOPCAO = 'SOBREPOR' THEN
            DELETE 
              FROM UTILPRATOSERV
             WHERE NRVIGENCIA = C_DEST.NRVIGENCIA AND
                   CDSERVFILI = C_DEST.CDSERVFILI;
         END IF;

         /*INSERE OS ITENS DA VIGENCIA NO SERVICO DESTINO ACRESCENTANDO OS QUE AINDA NAO EXISTEM*/
         INSERT INTO UTILPRATOSERV (NRUTILPRATOSERV, NRVIGENCIA, CDSERVFILI, NRGRUPOPRATOSERV, IDUTILPRATOSERVSEG, IDUTILPRATOSERVTER, IDUTILPRATOSERVQUA, IDUTILPRATOSERVQUI, IDUTILPRATOSERVSEX, IDUTILPRATOSERVSAB, IDUTILPRATOSERVDOM, 
                                    IDUTILPRATOSERVFERI, IDUTILPRATOSERVPRIM, IDUTILPRATOSERVULT, IDUTILPRATOSERVSEM2, IDUTILPRATOSERVSEM3, IDUTILPRATOSERVSEM4, DTINCLUSAO, CDOPERINCLUSAO)
         (SELECT RETORNA_NOVO_CODIGO('UTILPRATOSERV', 1), C_DEST.NRVIGENCIA, C_DEST.CDSERVFILI, NRGRUPOPRATOSERV, IDUTILPRATOSERVSEG, IDUTILPRATOSERVTER, IDUTILPRATOSERVQUA, IDUTILPRATOSERVQUI, IDUTILPRATOSERVSEX, IDUTILPRATOSERVSAB, IDUTILPRATOSERVDOM,
                 IDUTILPRATOSERVFERI, IDUTILPRATOSERVPRIM, IDUTILPRATOSERVULT, IDUTILPRATOSERVSEM2, IDUTILPRATOSERVSEM3, IDUTILPRATOSERVSEM4, SYSDATE, P_CDOPERADOR
            FROM(SELECT GS2.NRGRUPOPRATOSERV, IDUTILPRATOSERVSEG, IDUTILPRATOSERVTER, IDUTILPRATOSERVQUA, IDUTILPRATOSERVQUI, IDUTILPRATOSERVSEX, IDUTILPRATOSERVSAB, IDUTILPRATOSERVDOM,
                        IDUTILPRATOSERVFERI, IDUTILPRATOSERVPRIM, IDUTILPRATOSERVULT, IDUTILPRATOSERVSEM2, IDUTILPRATOSERVSEM3, IDUTILPRATOSERVSEM4
                   FROM UTILPRATOSERV R INNER JOIN LISTA L ON L.NRLISTA = P_NRLISTA AND L.CDLISTA = R.NRUTILPRATOSERV
                                          INNER JOIN GRUPOPRATOSERV GS ON GS.NRGRUPOPRATOSERV = R.NRGRUPOPRATOSERV
                                          INNER JOIN GRUPOPRATOSERV GS2 ON GS2.NRGRUPOPRATO = GS.NRGRUPOPRATO AND GS2.CDSERVFILI = C_DEST.CDSERVFILI
                  WHERE NOT EXISTS (SELECT R2.NRGRUPOPRATOSERV
                                      FROM UTILPRATOSERV R2 
                                     WHERE R2.NRVIGENCIA = C_DEST.NRVIGENCIA AND
                                           R2.CDSERVFILI = C_DEST.CDSERVFILI AND
                                           R2.NRGRUPOPRATOSERV = GS2.NRGRUPOPRATOSERV))
         );
         COMMIT;
      END LOOP;
      P_LISTA_ERROS := V_LISTA_ERROS;
   END;


   /*PROCEDURE PARA EXPORTAR ITENS SELECIONADOS DE UMA VIGENCIA DE FREQUENCIA DE PRATO NO MES*/
   PROCEDURE EXPORTA_ITEM_FREQ_PRAT_MES(
      P_NRVIGENCIA IN NUMBER, -- NUMERO DA VIGENCIA DE ORIGEM
      P_CDFILIAL IN FILIAL.CDFILIAL%TYPE, -- CODIGO DA FILIAL DE ORIGEM
      P_CDSERVFILI IN SERVICO.CDSERVFILI%TYPE, -- CODIGO DO SERVICO DE ORIGEM
      P_IDTIPORESTRICAO IN VARCHAR2, -- TIPO DE RESTRICAO CONTRATUAL = PLANEJADO OU CONTRATO
      P_NRLISTA_DEST IN LISTA.NRLISTA%TYPE, -- NUMERO DE UMA LISTA CUJO CAMPO CDLISTA COMPOSTO DE CDFILIAL||CDSERVFILI||NRVIGENCIA
      P_NRLISTA IN LISTA.NRLISTA%TYPE, -- NUMERO DE UMA LISTA CUJO CAMPO CDLISTA CONTEM A PK DOS ITENS SELECIONADO
      P_IDOPCAO IN VARCHAR2, -- SOBREPOR OU ACRESCENTAR 
      P_CDOPERADOR IN OPERADOR.CDOPERADOR%TYPE,-- CODIGO DO OPERADOR LOGADO
      P_LISTA_ERROS OUT VARCHAR2 -- LISTA DE ERROS RETORNADOS
      )
   AS
      V_FREQ_DEST VARCHAR2(20);
      V_LISTA_ERROS VARCHAR2(20);
      V_CDCHAVE VARCHAR2(500);
      V_MENSAGEM VARCHAR2(4000);      
   BEGIN
    
      /*CURSOR PARA FAZER UM LOOP NAS FILIAIS/SERVICOS DESTINOS E SUAS VIGENCIAS A EXPORTAR*/ 
      FOR C_DEST IN (SELECT V.NRVIGENCIA, V.DTVIGENCIA, V.DESCRICAO, V.CDFILIAL, SUBSTR(L.CDLISTA,5,5) AS CDSERVFILI, F.NRFREQPRATMES
                       FROM LISTA L INNER JOIN VIGFREQPRATMES V ON SUBSTR(L.CDLISTA,1,4) = V.CDFILIAL AND SUBSTR(L.CDLISTA,10) = V.NRVIGENCIA
                                    LEFT JOIN FREQPRATMES F ON F.CDFILIAL = SUBSTR(L.CDLISTA,1,4) AND F.CDSERVFILI = SUBSTR(L.CDLISTA,5,5) AND F.NRVIGENCIA = SUBSTR(L.CDLISTA,10)
                      WHERE L.NRLISTA = P_NRLISTA_DEST AND
                            V.IDTIPORESTRICAO = P_IDTIPORESTRICAO
                     ORDER BY V.NRVIGENCIA, SUBSTR(L.CDLISTA,5,5) 
      )LOOP
         /*PROCURA GRUPOS DE PRATOS NAO ASSOCIADOS AO SERVICO DESTINO PARA INSERIR NA LISTA DE ERROS*/
         FOR C_ERROS IN (SELECT I.CDPRATO, I.CDFILAUXPRAT, P.NMPRATO, P.NRORG
                           FROM ITFREQPRATMES I INNER JOIN LISTA L ON L.NRLISTA = P_NRLISTA AND L.CDLISTA = I.NRITFREQPRATMES
                                                INNER JOIN PRATO P ON P.CDFILAUXPRAT = I.CDFILAUXPRAT AND P.CDPRATO = I.CDPRATO
                          WHERE I.CDFILAUXPRAT = P_CDFILIAL AND
                                NOT EXISTS (SELECT P2.CDPRATO
                                              FROM PRATO P2 
                                             WHERE (P2.CDFILAUXPRAT = 'P' OR P2.CDFILAUXPRAT = C_DEST.CDFILIAL) AND
                                                   P2.CDPRATO = P.CDPRATO AND P2.NMPRATO = P.NMPRATO)
         )LOOP
            /*INSERE NA TABELA DE ERROS*/
            V_CDCHAVE := (C_DEST.CDFILIAL||'|'||C_DEST.CDSERVFILI||'|'||C_ERROS.CDPRATO);
            V_MENSAGEM := MSG('CONSISTE_PRATO',C_DEST.CDFILIAL, C_DEST.CDSERVFILI, C_ERROS.CDPRATO||' - '||C_ERROS.NMPRATO);
            INSERE_LISTA_ERROS(C_DEST.CDFILIAL,V_MENSAGEM,P_CDOPERADOR, C_ERROS.NRORG, V_LISTA_ERROS, NULL, V_CDCHAVE);
         END LOOP;   

         /*SE NAO EXISTE A FREQUENCIA PARA O SERVICO DESTINO ENTAO INSERE A FREQUENCIA PARA O SERVICO PRIMEIRO*/
         IF C_DEST.NRFREQPRATMES IS NULL THEN
            NOVO_CODIGO('FREQPRATMES',V_FREQ_DEST);
            INSERT INTO FREQPRATMES (NRFREQPRATMES, CDFILIAL, CDSERVFILI, DTVIGENCIA, DSFREQPRATMES, DTINCLUSAO, CDOPERINCLUSAO, NRVIGENCIA) VALUES
                                      (V_FREQ_DEST, C_DEST.CDFILIAL, C_DEST.CDSERVFILI, C_DEST.DTVIGENCIA, C_DEST.DESCRICAO, SYSDATE, P_CDOPERADOR, C_DEST.NRVIGENCIA);            
         END IF;
         /*SE A OPCAO FOR SOBREPOR ENTAO VAI EXCLUIR OS ITENS NA VIGENCIA DESTINO SE EXISTIR*/
         IF P_IDOPCAO = 'SOBREPOR' AND C_DEST.NRFREQPRATMES IS NOT NULL THEN
            DELETE 
              FROM ITFREQPRATMES
             WHERE NRFREQPRATMES = C_DEST.NRFREQPRATMES;
         END IF;
         V_FREQ_DEST := NVL(C_DEST.NRFREQPRATMES, V_FREQ_DEST);   

         /*INSERE OS ITENS DA VIGENCIA NO SERVICO DESTINO ACRESCENTANDO OS QUE AINDA NAO EXISTEM*/
         INSERT INTO ITFREQPRATMES (NRITFREQPRATMES, NRFREQPRATMES, CDFILAUXPRAT, CDPRATO, NRMINFREQPRATMES, NRMAXFREQPRATMES, NRMAXFREQPRATSEM, DTINCLUSAO, CDOPERINCLUSAO)
         (SELECT RETORNA_NOVO_CODIGO('ITFREQPRATMES', 1), V_FREQ_DEST, CDFILAUXPRAT, CDPRATO, NRMINFREQPRATMES, NRMAXFREQPRATMES, NRMAXFREQPRATSEM, SYSDATE, P_CDOPERADOR
            FROM(SELECT P2.CDFILAUXPRAT, I.CDPRATO, I.NRMINFREQPRATMES, I.NRMAXFREQPRATMES, I.NRMAXFREQPRATSEM
                   FROM ITFREQPRATMES I INNER JOIN LISTA L ON L.NRLISTA = P_NRLISTA AND L.CDLISTA = I.NRITFREQPRATMES
                                        INNER JOIN PRATO P ON P.CDFILAUXPRAT = I.CDFILAUXPRAT AND P.CDPRATO = I.CDPRATO
                                        INNER JOIN (SELECT MIN(CDFILAUXPRAT) AS CDFILAUXPRAT, CDPRATO, NMPRATO
                                                      FROM PRATO P
                                                     WHERE CDFILAUXPRAT = 'P' OR CDFILAUXPRAT = C_DEST.CDFILIAL
                                                    GROUP BY CDPRATO, NMPRATO) P2 ON P2.CDPRATO = P.CDPRATO AND P2.NMPRATO = P.NMPRATO
                  WHERE NOT EXISTS (SELECT I2.CDPRATO
                                      FROM ITFREQPRATMES I2 
                                     WHERE I2.NRFREQPRATMES = V_FREQ_DEST AND
                                           I2.CDPRATO = P2.CDPRATO AND
                                           I2.CDFILAUXPRAT = P2.CDFILAUXPRAT))
         );
         COMMIT;
      END LOOP;
      P_LISTA_ERROS := V_LISTA_ERROS;
   END;

   
END UTIL_OTIMIZADOR;
/