电子邮件格式化 Oracle
E-mail Formatting Oracle
我在这个过程中需要一些帮助。我需要在一封电子邮件中包含第一个光标 (C1) 上 select 的全部结果。
该过程现在的工作方式是,它会为找到的每一行发送一封电子邮件。结果是,如果游标找到 100 行,将发送 100 封电子邮件,我不希望发生这种情况,我需要一封电子邮件中的 100 行,在“V_MENSAGEM”之后结构。
create or replace PROCEDURE PR_ENVIA_EMAIL_LOTE_ESTOQUE IS
V_REMETENTE VARCHAR2(50) := 'servidor@oracle.com.br';
V_SAUDACAO VARCHAR2(50);
V_ASSUNTO VARCHAR2(200);
V_ASSINATURA VARCHAR2(100);
V_MENSAGEM VARCHAR2(6000);
V_COD_ERRO NUMBER(2);
V_MSG_ERRO VARCHAR2(1);
TDESCRI_ARMAZEM VARCHAR2(50);
TDESCRI VARCHAR2(60);
BEGIN
FOR C1 IN (SELECT TBLOTE.NNOTFIS NOTA_FISCAL,
TBLOTE.CLOTE LOTE,
TBARMAZ.TDESCRI ARMAZEM,
TBNOTF.DDTFATU DATA_FAT_NF,
TBLOTE.DRECEBTO DATA_RECEBTO,
TBLOTE.CPRODUT COD_PRODUTO,
TBPRODU.TDESCRI PRODUTO,
TBLOTAR.QQTESTQ QTD_ESTOQUE,
Decode(TBLOTE.F_ARMAZENAGEM, 'S', 'SIM', 'N', 'NÃO') ARMAZENAGEM,
Decode(TBLOTE.SLTENCR, 'S', 'SIM', 'N', 'NÃO') ENCERRADO,
TO_DATE(Sysdate, 'dd/mm/yyyy') - TO_DATE(TBLOTE.DRECEBTO, 'dd/mm/yyyy')DIAS_EM_ESTOQUE
FROM TBLOTE,
TBLOTAR,
TBPRODU,
TBARMAZ,
TBNOTF
WHERE TBLOTE.CPRODUT = TBPRODU.CPRODUT
AND TBLOTE.CLOTE = TBLOTAR.CLOTE
AND TBLOTAR.CARMAZE = TBARMAZ.CARMAZE
AND TBLOTE.NNOTFIS = TBNOTF.NNOTFIS
AND TBLOTE.CEMPRES = TBNOTF.CEMPRES
AND TBLOTE.SLTENCR = 'N'
AND TBLOTE.F_ARMAZENAGEM = 'S'
AND TBLOTE.NNOTFIS IS NOT NULL
AND TO_DATE(Sysdate, 'dd/mm/yyyy') - TO_DATE(TBLOTE.DRECEBTO, 'dd/mm/yyyy') >= 165
ORDER BY DIAS_EM_ESTOQUE DESC)
LOOP
DBMS_OUTPUT.PUT_LINE('LENDO '||C1.NOTA_FISCAL|| ' - ' ||C1.LOTE|| ' - ' ||C1.ARMAZEM|| ' - ' ||C1.PRODUTO|| ' - Dias em Estoque: ' || C1.DIAS_EM_ESTOQUE);
BEGIN
IF TO_NUMBER(TO_CHAR(SYSDATE,'HH24')) < 12 THEN
V_SAUDACAO:= 'Bom Dia!';
ELSIF TO_NUMBER(TO_CHAR(SYSDATE,'HH24')) >= 12 AND
TO_NUMBER(TO_CHAR(SYSDATE,'HH24')) < 18 THEN
V_SAUDACAO:= 'Boa tarde!';
ELSE
V_SAUDACAO:= 'Boa noite!';
END IF;
V_ASSUNTO := 'AVISO: Lotes em estoque.';
V_MENSAGEM := ' Os seguintes lotes ja estao há pelo menos 165 dias em nosso estoque, favor verificar: '||CHR(10)||CHR(10);
V_MENSAGEM := V_MENSAGEM ||'Nota Fiscal : '||C1.NOTA_FISCAL||CHR(10)||
'Lote : '||C1.LOTE||CHR(10)||
'Armazem : '||C1.ARMAZEM||CHR(10)||
'Dt. Faturamento : '||To_Date(C1.DATA_FAT_NF, 'DD/MM/YYYY')||CHR(10)||
'Dt. Recebimento : '||C1.DATA_RECEBTO||CHR(10)||
'Produto : '||C1.PRODUTO||CHR(10)||CHR(10)||
'Qtd. em Estoque : '||C1.QTD_ESTOQUE||CHR(10)||
'Dias em Estoque : '||C1.DIAS_EM_ESTOQUE||CHR(10)||CHR(10)||
'Estamos a disposiçao.'||CHR(10)||CHR(10)||CHR(10)||
'Att. '||CHR(10)||CHR(10)||
'Departamento de T.I'||CHR(10)||
'---';
V_MENSAGEM := V_SAUDACAO||CHR(10)||CHR(10)||
V_MENSAGEM||
CHR(10)||CHR(10)||CHR(10)||CHR(10)||
V_ASSINATURA;
FOR C2 IN (SELECT EMAIL_USUARIO
FROM TBEMAIL_INTERNO
WHERE F_LOTE_ESTOQUE = 'S'
AND F_EXCLUSAO_LOGICA = 'N')
LOOP
PR_ENVIA_EMAIL(V_REMETENTE,
C2.EMAIL_USUARIO,
V_ASSUNTO,
V_MENSAGEM,
V_COD_ERRO,
V_MSG_ERRO);
END LOOP;
END;
END LOOP ;
EXCEPTION
WHEN OTHERS THEN
dbms_output.put_line('ATENÇÃO: ERRO AO CHAMAR ROTINA PR_ENVIA_EMAIL_LOTE_ESTOQUE: '||SQLERRM);
END PR_ENVIA_EMAIL_LOTE_ESTOQUE;
您在通过游标 C1 的循环的每次迭代中发送电子邮件的原因是通过 C2(发送电子邮件的循环)的循环是 在 循环中通过 C1。此更改应该可以解决您的问题:
...
V_MENSAGEM := V_SAUDACAO||CHR(10)||CHR(10)||
V_MENSAGEM||
CHR(10)||CHR(10)||CHR(10)||CHR(10)||
V_ASSINATURA;
END;
END LOOP ;
FOR C2 IN (SELECT EMAIL_USUARIO
FROM TBEMAIL_INTERNO
WHERE F_LOTE_ESTOQUE = 'S'
AND F_EXCLUSAO_LOGICA = 'N')
LOOP
PR_ENVIA_EMAIL(V_REMETENTE,
C2.EMAIL_USUARIO,
V_ASSUNTO,
V_MENSAGEM,
V_COD_ERRO,
V_MSG_ERRO);
END LOOP;
EXCEPTION
...
我在这个过程中需要一些帮助。我需要在一封电子邮件中包含第一个光标 (C1) 上 select 的全部结果。 该过程现在的工作方式是,它会为找到的每一行发送一封电子邮件。结果是,如果游标找到 100 行,将发送 100 封电子邮件,我不希望发生这种情况,我需要一封电子邮件中的 100 行,在“V_MENSAGEM”之后结构。
create or replace PROCEDURE PR_ENVIA_EMAIL_LOTE_ESTOQUE IS
V_REMETENTE VARCHAR2(50) := 'servidor@oracle.com.br';
V_SAUDACAO VARCHAR2(50);
V_ASSUNTO VARCHAR2(200);
V_ASSINATURA VARCHAR2(100);
V_MENSAGEM VARCHAR2(6000);
V_COD_ERRO NUMBER(2);
V_MSG_ERRO VARCHAR2(1);
TDESCRI_ARMAZEM VARCHAR2(50);
TDESCRI VARCHAR2(60);
BEGIN
FOR C1 IN (SELECT TBLOTE.NNOTFIS NOTA_FISCAL,
TBLOTE.CLOTE LOTE,
TBARMAZ.TDESCRI ARMAZEM,
TBNOTF.DDTFATU DATA_FAT_NF,
TBLOTE.DRECEBTO DATA_RECEBTO,
TBLOTE.CPRODUT COD_PRODUTO,
TBPRODU.TDESCRI PRODUTO,
TBLOTAR.QQTESTQ QTD_ESTOQUE,
Decode(TBLOTE.F_ARMAZENAGEM, 'S', 'SIM', 'N', 'NÃO') ARMAZENAGEM,
Decode(TBLOTE.SLTENCR, 'S', 'SIM', 'N', 'NÃO') ENCERRADO,
TO_DATE(Sysdate, 'dd/mm/yyyy') - TO_DATE(TBLOTE.DRECEBTO, 'dd/mm/yyyy')DIAS_EM_ESTOQUE
FROM TBLOTE,
TBLOTAR,
TBPRODU,
TBARMAZ,
TBNOTF
WHERE TBLOTE.CPRODUT = TBPRODU.CPRODUT
AND TBLOTE.CLOTE = TBLOTAR.CLOTE
AND TBLOTAR.CARMAZE = TBARMAZ.CARMAZE
AND TBLOTE.NNOTFIS = TBNOTF.NNOTFIS
AND TBLOTE.CEMPRES = TBNOTF.CEMPRES
AND TBLOTE.SLTENCR = 'N'
AND TBLOTE.F_ARMAZENAGEM = 'S'
AND TBLOTE.NNOTFIS IS NOT NULL
AND TO_DATE(Sysdate, 'dd/mm/yyyy') - TO_DATE(TBLOTE.DRECEBTO, 'dd/mm/yyyy') >= 165
ORDER BY DIAS_EM_ESTOQUE DESC)
LOOP
DBMS_OUTPUT.PUT_LINE('LENDO '||C1.NOTA_FISCAL|| ' - ' ||C1.LOTE|| ' - ' ||C1.ARMAZEM|| ' - ' ||C1.PRODUTO|| ' - Dias em Estoque: ' || C1.DIAS_EM_ESTOQUE);
BEGIN
IF TO_NUMBER(TO_CHAR(SYSDATE,'HH24')) < 12 THEN
V_SAUDACAO:= 'Bom Dia!';
ELSIF TO_NUMBER(TO_CHAR(SYSDATE,'HH24')) >= 12 AND
TO_NUMBER(TO_CHAR(SYSDATE,'HH24')) < 18 THEN
V_SAUDACAO:= 'Boa tarde!';
ELSE
V_SAUDACAO:= 'Boa noite!';
END IF;
V_ASSUNTO := 'AVISO: Lotes em estoque.';
V_MENSAGEM := ' Os seguintes lotes ja estao há pelo menos 165 dias em nosso estoque, favor verificar: '||CHR(10)||CHR(10);
V_MENSAGEM := V_MENSAGEM ||'Nota Fiscal : '||C1.NOTA_FISCAL||CHR(10)||
'Lote : '||C1.LOTE||CHR(10)||
'Armazem : '||C1.ARMAZEM||CHR(10)||
'Dt. Faturamento : '||To_Date(C1.DATA_FAT_NF, 'DD/MM/YYYY')||CHR(10)||
'Dt. Recebimento : '||C1.DATA_RECEBTO||CHR(10)||
'Produto : '||C1.PRODUTO||CHR(10)||CHR(10)||
'Qtd. em Estoque : '||C1.QTD_ESTOQUE||CHR(10)||
'Dias em Estoque : '||C1.DIAS_EM_ESTOQUE||CHR(10)||CHR(10)||
'Estamos a disposiçao.'||CHR(10)||CHR(10)||CHR(10)||
'Att. '||CHR(10)||CHR(10)||
'Departamento de T.I'||CHR(10)||
'---';
V_MENSAGEM := V_SAUDACAO||CHR(10)||CHR(10)||
V_MENSAGEM||
CHR(10)||CHR(10)||CHR(10)||CHR(10)||
V_ASSINATURA;
FOR C2 IN (SELECT EMAIL_USUARIO
FROM TBEMAIL_INTERNO
WHERE F_LOTE_ESTOQUE = 'S'
AND F_EXCLUSAO_LOGICA = 'N')
LOOP
PR_ENVIA_EMAIL(V_REMETENTE,
C2.EMAIL_USUARIO,
V_ASSUNTO,
V_MENSAGEM,
V_COD_ERRO,
V_MSG_ERRO);
END LOOP;
END;
END LOOP ;
EXCEPTION
WHEN OTHERS THEN
dbms_output.put_line('ATENÇÃO: ERRO AO CHAMAR ROTINA PR_ENVIA_EMAIL_LOTE_ESTOQUE: '||SQLERRM);
END PR_ENVIA_EMAIL_LOTE_ESTOQUE;
您在通过游标 C1 的循环的每次迭代中发送电子邮件的原因是通过 C2(发送电子邮件的循环)的循环是 在 循环中通过 C1。此更改应该可以解决您的问题:
...
V_MENSAGEM := V_SAUDACAO||CHR(10)||CHR(10)||
V_MENSAGEM||
CHR(10)||CHR(10)||CHR(10)||CHR(10)||
V_ASSINATURA;
END;
END LOOP ;
FOR C2 IN (SELECT EMAIL_USUARIO
FROM TBEMAIL_INTERNO
WHERE F_LOTE_ESTOQUE = 'S'
AND F_EXCLUSAO_LOGICA = 'N')
LOOP
PR_ENVIA_EMAIL(V_REMETENTE,
C2.EMAIL_USUARIO,
V_ASSUNTO,
V_MENSAGEM,
V_COD_ERRO,
V_MSG_ERRO);
END LOOP;
EXCEPTION
...