cancel
Showing results for 
Search instead for 
Did you mean: 

NTB2B - XML com quebra no conteúdo

former_member347027
Participant
0 Kudos

Boa tarde senhores,

Estou tendo um problema com o cenário NTB2B.

Implementei a BadI /XNFE/IF_EX_EMAIL_B2B~GET_EMAIL para buscar email do fornecedor.

E utilizo javamapping para enviar o email.

O problema esta no xml anexado no email. Esta ocorrendo uma “quebra” no conteudo.


PI versão 7.31.

Alguém já passou por isso?


Accepted Solutions (1)

Accepted Solutions (1)

rhviana
Active Contributor
0 Kudos

M Faria boa tarde,

Estou desconfiando esse module para nomear o arquivo para .xml.

Por que você ja não fez isso direto no java mapping ?

content ="Content-Disposition: attachment; filename="+ " NF-e Cancelada EMPRESA X - " + chaveNFe +

".xml"+"\r\n\r\n"+ xmlString + "\r\n";

Com o codigo acima você não precisaria colocar nada no module.

Atenciosamente,

Ricardo Viana.

former_member347027
Participant
0 Kudos

Obrigado Ricardo!

Mudei o Content Enconding para base64 e alterei o module funcionou.

Agora tenho problema ao montar o corpo do email. =/

rhviana
Active Contributor
0 Kudos

M Faria boa noite,

Criei uma wiki a mais de um ano atrás explicando como fazer isso:

http://wiki.scn.sap.com/wiki/pages/viewpage.action?pageId=315524420

Da uma lida, acho que você consegue tranquilo.

            // Criando o corpo de texto do e-mail e o anexo

            BodyText texto = new BodyText(idNFe,getFrase(),inptxml);

            //Cria elemento Content

            Element content = docout.createElement("Content");

            root.appendChild(content);

            Text contentText;

            // substituir a sua empresa

            if ("NFE EMPRESA X : ".equalsIgnoreCase(getPrefixoSubject())){

                contentText = docout.createTextNode(texto.getnfeText());

            }

            // substituir a sua empresa

            else if("NFE CANCELADA EMPRESA X: ".equalsIgnoreCase(getPrefixoSubject())){

                contentText = docout.createTextNode(texto.getCnfeText());

            }

            else

            {

                contentText = docout.createTextNode(texto.getcceText());

            }

            //Cria valor campo contet Text

            content.appendChild(contentText);

....

public String getnfeText() {

        // Corpo de texto da NF-e autorizada

        nfeText ="Prezado cliente, "+getGap()+getGap()+

        "Segue arquivo anexo referente a Nota Fiscal Eletrônica "+ getGap()+ getGap()+

        "Número da NF-e Autorizada: "+ numeroNFe +  getGap()+

        "Série: "+ serieNFe+ getGap()+

        "Data emissão (MM/AAAA): " + dataNFe + getGap()+getGap()+

        "Atenciosamente,"+getGap()+getGap()+

        "EMPRESA X";

        // Preencher o campo Content com o corpo de texto e arquivo .XML em anexo.

        content = "----AaZz\r\n Content-Type: text/plain; charset=UTF-8\r\n" +

        "Content-Disposition: inline\r\n\r\n" + nfeText +

        "\r\n----AaZz\r\nContent-Disposition: attachment; filename="+ "NF-e EMPRESA X - " + chaveNFe +

        ".xml" +"\r\n\r\n" + xmlString + "\r\n";

        return content;

    }

No meu codigo estou utilizando o Mimes: multipart/mixed;boundary , para diferenciar o anexo do corpo de texto.

Abras,

Ricardo Viana.

Message was edited by: Ricardo Viana

rhviana
Active Contributor
0 Kudos

Faria boa tarde,

Progressos ? Dúvidas?

Posso ajudar ?

Abraçs,

Ricardo Viana.

former_member347027
Participant
0 Kudos

Obrigado Ricardo!!

Sem progressos. =/

Com o código em anexo, o corpo do email é preenchido corretamente, porém o xml em anexo não esta sendo montado corretamente.

Parece que ocorre 2 espaços em branco e uma quebra toda vez que chega em 990 caracteres.

Sabe o que pode ser?

Obrigado

rhviana
Active Contributor
0 Kudos

Faria,

Como você está montando o anexo ?

Por que você não faz como está explicado na minha wiki, monta o ANEXO + CORPO via java mapping ?

Vejo que o anexo você está montando via module, correto ?

Att,

former_member347027
Participant
0 Kudos

Obrigado Ricardo,

Estou montando via javamapping.

Montando o anexo e o corpo.

Segue código java em anexo.

Obrigado,

rhviana
Active Contributor
0 Kudos

Faria,

Acabei de ver seu código, está diferente do meu.

Essa variavel: "multipart/mixed;boundary=--AaZz" --AaZZ eu que criei, você pode utilizar qualquer coisa... tipo ---TextoXml bla.. mais tranquilo.

Outro ponto, você não precisa utilizar toda vez --AaZz (separador do Content-Type do Content-Disposition), no seu código para quase tudo você colocou isso, não sei se vai funcionar direito.

String output = new String("");     

              //output = "--AaZz" + CRLF + "Content-Type: text/plain; charset=UTF-8" + CRLF + "Content-Disposition: inline" + CRLF + CRLF + body + CRLF + "----AaZz" + CRLF + "Content_Type: application/xml; name=" + filename + CRLF + "Content-Disposition: attachment; filename=" + filename + CRLF + CRLF + attachment + CRLF;

                    //output = "--AaZz" + CRLF + "Content-Type: text/plain; charset=us-ascii" + CRLF + body + CRLF + "--AaZz" + CRLF + "Content_Type: application/xml; name=" + filename + CRLF + "Content-Disposition: attachment; filename=" + filename + CRLF + attachment + CRLF + "--AaZz";

                    //First part                    

                    output = "--" + "--AaZz" + CRLF

                                         + "Content-Type: text/plain; charset=UTF-8" + CRLF

                                         + "Content-Transfer-Encoding: 8bit" + CRLF

                                         + "Content-Disposition: inline" + CRLF

                                         + body + CRLF

              //Second part

                                         + "--" + "--AaZz" + CRLF

                                         + "Content-Type: Application/xml; name=" +filename + CRLF

                                         + "Content-Transfer-Encoding: 8bit" + CRLF

                                         //+ "Content-Transfer-Encoding: base64" + CRLF

                                         + "Content-Disposition: attachment; filename=" + filename + CRLF + CRLF

                                         + attachment;

Meu código:

public String getnfeText() {

        // Corpo de texto da NF-e autorizada

        nfeText ="Prezado cliente, "+getGap()+getGap()+

        "Segue arquivo anexo referente a Nota Fiscal Eletrônica "+ getGap()+ getGap()+

        "Número da NF-e Autorizada: "+ numeroNFe +  getGap()+

        "Série: "+ serieNFe+ getGap()+

        "Data emissão (MM/AAAA): " + dataNFe + getGap()+getGap()+

        "Atenciosamente,"+getGap()+getGap()+

        "EMPRESA X";

        // Preencher o campo Content com o corpo de texto e arquivo .XML em anexo.

        content = "----AaZz\r\n Content-Type: text/plain; charset=UTF-8\r\n" +

        "Content-Disposition: inline\r\n\r\n" + nfeText +

        "\r\n----AaZz\r\nContent-Disposition: attachment; filename="+ "NF-e EMPRESA X - " + chaveNFe +

        ".xml" +"\r\n\r\n" + xmlString + "\r\n";

        return content;

    }

nfeText - variavel tipo String , que recebe o corpo de texto.

content - variavel do tipo Element, repare que eu utilizo em dois momentos o separador ----AaZz - na hora de separar o texto (text/plain - formato UTF-8) do anexo attachment;filename.

Outro ponto que não tenho certeza, mais pode está ocorrendo uma "zica" é na hora dessa conversão:




//XML DA NF-e



String conteudo_xml = new String(""); 



conteudo_xml = (inptxml.replaceAll("<nm:", "<").replaceAll("</nm:", "</").replaceAll(System.getProperty("line.separator"), "").replaceAll("\n", "").replaceAll("\r", "").replaceAll("\t", "").replaceAll("\n\r", "").replaceAll("\n\t", "").replaceAll("\r\t", "").replaceAll("\r\n", "").replaceAll("\t\n", "").replaceAll("\t\r", "").replaceAll("\r\r", "").replaceAll("\n\n", "").replaceAll("\t\t", ""));

Não precisei fazer isso.

Mais você está no caminho velho, teste ai e poste o resultado !!

Boooaaa garoto , elite d+.

Abraçs,

Ricardo Viana.

Message was edited by: Ricardo Viana

former_member347027
Participant
0 Kudos

Obrigado Ricardo,

Fizemos um teste trocando o tratamento de montagem do xml por uma string fixa.

Mesmo assim o xml anexado chega com as quebras.

String contXML = "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX";

Será que não é alguma configuração faltando no PI?

Esse java mapping só funciona com o content encondig = None

Em anexo arquivo com o resultado gerado.

rhviana
Active Contributor
0 Kudos

Faria,

Sim com java mapping você coloca o encoding = None no adaptador de mail.

Não está faltando configuração, porém, você retirou a configuração que você tinha feito no module ?

Faria você sabe colocar trace no java mapping ?

Gostaria de verificar o trace para saber se essa quebra está ocorrendo devido esses replaces.

No seu teste, chegou o e-mail com o "corpo de texto" e o anexo "zuado", o que aconteceu ai ?

Cara amanhã eu posto novamente, deixei o note no office.

Abraço,

Ricardo Viana.

pedro_baroni3
Active Contributor
0 Kudos
Faria, bom dia.
Como você está usando o Mail Package não vai adiantar mecher no Encoding do Channel.
Pode ser que o Servidor de E-mail esteja fazendo esta quebra incorretamente.
Neste caso, o ideal seria você fazer o encoding para Base-64 dentro do seu Java Mapping.
Faça a substituição do Content-Transfer para:
Content-Transfer-Encoding: base64
Você precisará também codificar o XML da NF-e no próprio Java Mapping. Faça isto somente com o XML da NF-e antes de:
     + "Content-Disposition: attachment; filename=" + filename + CRLF + CRLF
Use os comandos:
import sun.misc.BASE64Encoder;
//Convertendo o XML String em Base 64
String xmlBase64 = "";
BASE64Encoder base64Encoder =
new BASE64Encoder();
xmlBase64 = base64Encoder.encode(attachment.getBytes("UTF-8"));
Então use a nova variável no e-mail:
     + "Content-Disposition: xmlBase64; filename=" + filename + CRLF + CRLF
Tente isso por favor.
Abraços.
Pedro Baroni
rhviana
Active Contributor
0 Kudos

Faria bom dia,

Voltando ao assunto.

Ajustei o seu código adicionando a lib: import com.sap.aii.mapping.api.AbstractTrace;, e todos os pontos de trace.

Ajusta na sxmb_adm o parametro de trace para lvl 3, assim você consegue ver tudo o que está ocorrendo no seu java mapping via sxi_monitor.

Adicionei essas linhas:

// Criando objeto de log de mensagens

AbstractTrace absTraceLog = this.getTrace();

absTraceLog.addDebugMessage("JAVAMAPPING --- INICIANDO O JAVAMAPPING - Faria")

......

//Transforma mensagem em entrada em string

String inptxml = this.stream2string(in);

absTraceLog.addDebugMessage("String do XML"+inptxml);

...

//Obtendo dados para o envio de e-mail

String idNFe = "";

idNFe = inptxml.substring(inptxml.indexOf("Id=\"NFe")+7,inptxml.indexOf("Id=\"NFe")+51);

absTraceLog.addDebugMessage("Chave de acesso da NF-e "+idNFe);

....

Após o replace,obs: Não vejo necessidade disso.

//XML DA NF-e

String conteudo_xml = new String(""); 

conteudo_xml = (inptxml.replaceAll("<nm:", "<").replaceAll("</nm:", "</").replaceAll(System.getProperty("line.separator"), "").replaceAll("\n", "").replaceAll("\r", "").replaceAll("\t", "").replaceAll("\n\r", "").replaceAll("\n\t", "").replaceAll("\r\t", "").replaceAll("\r\n", "").replaceAll("\t\n", "").replaceAll("\t\r", "").replaceAll("\r\r", "").replaceAll("\n\n", "").replaceAll("\t\t", ""));

absTraceLog.addDebugMessage("Qual atual conteúdo do XML "+conteudo_xml);

...

// Preencher o campo Content com o corpo de texto e arquivo .XML em anexo.

String conteudo_email = generateContentWithAttachment(texto_email,conteudo_xml,nome_arquivo);

absTraceLog.addDebugMessage("Qual valor da variavel conteudo_email "+conteudo_email);

Faria não sou javeiro de "natureza" sou fuçador, mais acredito que com isso, você vai visualizar o trace na sxi_monitor e vai descobrir se é o javamapping ou module que está "quebrando" o anexo.

Recomendo retirar aquela configuração do module sobre o Content_Disposition, não utilizei isso, como você pode verificar na wiki.

Olha acho que esse é o caminho, qualquer coisa posta, beleza ?

Abraços,

Ricardo Viana.

brigolo
Explorer
0 Kudos

Bom Dia.

Teste dessa forma, comigo funcionou, mas antes o anexo precisa estar em BASE64 como exemplo mencionado pelo Pedro acima.

String ls = System.getProperty("line.separator");

String CRLF = ls;

output = "--" + "--AaZz" + CRLF + "Content-Type: text/html; charset=UTF-8" + CRLF + "Content-Disposition: inline" + CRLF + CRLF + body + CRLF + "--" + "--AaZz" + CRLF + "Content-Type: application/xml; charset=UTF-8 ; name=" + filename + CRLF + "Content-Disposition: attachment; filename=" + filename + CRLF + "Content-Transfer-Encoding: base64" + CRLF + CRLF + attachment + CRLF;

Abs.

former_member347027
Participant
0 Kudos

Obrigado Ricardo,

Segue o trace em anexo.

former_member347027
Participant
0 Kudos

Obrigado pela resposta Baroni,

Estou fazendo as alterações, já posto aqui.

rhviana
Active Contributor
0 Kudos

Faria,

Não consegui visualizar a chamada do JavaMapping, você realmente colocou o trace ?

Procurei por essa msg

  1. absTraceLog.addDebugMessage("JAVAMAPPING --- INICIANDO O JAVAMAPPING - Faria"

Não achei.

Refaça o teste.

Abraçs

former_member347027
Participant
0 Kudos

Obrigado Ricardo,

Procurei em todos os Traces aqui por: absTraceLog.addDebugMessage("JAVAMAPPING --- INICIANDO O JAVAMAPPING - Faria")


e não encontro.

former_member347027
Participant
0 Kudos

Obrigado Barone,

Com essas alterações funcionou...

Email na caixa com o corpo de email formatado certinho e xml anexo validando na SEFAZ.

Muito obrigado,

pedro_baroni3
Active Contributor
0 Kudos

Maravilha, parabéns.

Se puder compartilhar o código do Java Mapping com a galera seria uma boa, pois tem muita gente que sofre com esse problema de XML mal formatado.

Um Blog com essa solução também seria interessante.

Abraços.

Pedro Baroni

rhviana
Active Contributor
0 Kudos

Na realidade voce só deve buscar por:

JAVAMAPPING --- INICIANDO O JAVAMAPPING

Mais pelo visto você não conseguiu implementar, pois, no seu exemplo não encontro essa chamada.

former_member347027
Participant
0 Kudos

Obrigado Baroni!

Agradeço a todos pela ajuda.

http://scn.sap.com/people/ricardo.viana

http://scn.sap.com/people/brigolo

http://scn.sap.com/people/pedro.baroni3

http://scn.sap.com/people/bruno.xavier

O Código java inicial é mérito do Bruno.

Segue em anexo print do canal de comunicação (Parameters e Module) e o código do javamapping.

[]'s

rhviana
Active Contributor
0 Kudos

Sucesso Faria.

Parabéns, elite !!

Answers (2)

Answers (2)

Former Member
0 Kudos

Olá Faria!

Pelo que entendi você já resolveu. Por favor feche a thread qualificando as respostas que lhe foram dadas.

Grato

Eduardo Chagas

pedro_baroni3
Active Contributor
0 Kudos

Boa tarde.

Você já viu a thread:

B2B - Servidor SMTP tornando conteúdo do XML inválido

Att.,

Baroni

former_member347027
Participant
0 Kudos

Obrigado Pedro!

Mudei o Content Enconding para base64 e funcionou.

O xml é anexado corretamente.

Agora o problema é montar o corpo do email no javamapping.

Utilizei o código de exemplo do Carlos Rodrigo http://scn.sap.com/thread/3257778, acrescentando a parte do corpo do email.

//Texto do corpo do e-mail

                              String texto_email = "Prezados Senhores,";

 

                              // Preencher o campo Content com o corpo de texto e arquivo .XML em anexo.

                              String conteudo_email = generateContentWithAttachment(texto_email);

                              Text contentText = docout.createTextNode(conteudo_email); //Cria valor campo

                              content.appendChild(contentText);

 

 

                              //Fecha o XML

                              DOMSource domS = new DOMSource(docout);

                              transform.transform((domS), new StreamResult(out));

Porém apresenta erro de mapping.

SAP:Stack>&quot;SYSTEM FAILURE&quot; durante a chamada JCo. java.lang.reflect.UndeclaredThrowableException</SAP:Stack>

Obrigado!