Ir para conteúdo
  • Cadastre-se

dev botao

Erro de "CoInitialize" na emissão de nfe usando Thread.


carlosmarian
  • Este tópico foi criado há 2558 dias atrás.
  • Talvez seja melhor você criar um NOVO TÓPICO do que postar uma resposta aqui.

Recommended Posts

Olá,

  Estou efetuando a migração para a trunk2, a primeira etapa de instalação já consegui ultrapassar.

  Estou agora adaptando o sistema as alterações do ACBr.

  Minha aplicação efetua emissão de notas(transmissão para sefaz) usando threads, na versão trunk foram efetuados ajustes adicionando as chamadas aos métodos de "CoInitialize" e "CoUninitialize" em alguns pontos do processo(exemplo: "ValidaMSXML", "AssinarMSXML", ..).

  Agora na nova versão(trunk2) a chamada("CoInitialize" e "CoUninitialize") ficou restrita ao "initialization" e "finalization" da classe "ACBrDFeCapicom".
    Este ajuste esta trazendo alguns erros ao consumir webservice(consulta de status), assinatura e/ou validação do XML, apresenta falha "CoInitialize não foi chamado, ClassID: {XXXXX".
    Analisando o código fiz alguns ajustes e consegui eliminar estes erros. Gostaria de avaliar com vcs se estes ajustes são válidos e se podem ser adicionados ao repositório.

   Os ajustes se são no fonte(ACBrDFeCapicom.pas) e basicamente a chamada do "CoInitialize" e "CoUninitialize" dentro do método de assinatura e validação e tbm no "CarregarCertificado".
   Segue em anexo o fonte ajustado.

 

No aguardo.   

ACBrDFeCapicom.pas

Carlos H. Marian

Analista de Sistemas

|/-\|

Link para o comentário
Compartilhar em outros sites

  • Fundadores

Antes de analisar a sua correção, é necessário compreender como o problema ocorre...

Como reproduzir o problema usando o Demo do ACBrNFe ?

Consultor SAC ACBr

Daniel Simões de Almeida
O melhor TEF, é com o Projeto ACBr - Clique e Conheça
Ajude o Projeto ACBr crescer - Assine o SAC

Projeto ACBr     Telefone:(15) 2105-0750 WhatsApp(15)99790-2976.

Link para o comentário
Compartilhar em outros sites

  • Fundadores
Consultor SAC ACBr

Daniel Simões de Almeida
O melhor TEF, é com o Projeto ACBr - Clique e Conheça
Ajude o Projeto ACBr crescer - Assine o SAC

Projeto ACBr     Telefone:(15) 2105-0750 WhatsApp(15)99790-2976.

Link para o comentário
Compartilhar em outros sites

Olá,
  Eu vi que neste post que vc comentou foram feitos outros ajustes, tratamentos para a falha quando era executado uma segunda solicitação ao certificado. Neste momento o "CoInitialize" já estava no bloco "initialization". Nesta revisão 18/08 o "CoInitialize" já estava no bloco "initialization" do form.
  Vi que a alteração que passou "CoInitialize" para o bloco "initialization" ocorreu na revisão 9657, antes desta revisão a chamada ocorria no momento de carregar os certificados.

 No nosso projeto não usando mais os certificados A3(), então não tenho como garantir que a alteração não possa gerar impacto a outros usuários.

 Vc comentou anteriormente sobre como simular o erro, eu poderia tentar implementar algo no Demo da NFe mas como não usamos as maquinas de impressão do ACBr, o projeto demo não roda no meu ambiente. Vou ver se consigo de outra forma.

  

Carlos H. Marian

Analista de Sistemas

|/-\|

Link para o comentário
Compartilhar em outros sites

  • Fundadores

Se você usa apenas A1... recomendo usar OpenSSL... Com ele você não precisa instalar o certificado na máquina... apenas aponta para o PFX e pronto;;;

Consultor SAC ACBr

Daniel Simões de Almeida
O melhor TEF, é com o Projeto ACBr - Clique e Conheça
Ajude o Projeto ACBr crescer - Assine o SAC

Projeto ACBr     Telefone:(15) 2105-0750 WhatsApp(15)99790-2976.

Link para o comentário
Compartilhar em outros sites

Olá.

  Adicionei ao form principal do exemplo de Nfe(ACBrNFe_demo) duas rotinas usando Thread.
  A primeira é a consulta dos status do serviço, que ocorre sem erro.
  A segunda, é a emissão de uma nota e neste caso é apresentado erro no momento em que o acbr tenta assinar a nota.

  Estou anexando o form(Unit1) com a rotina para simulação.

  Tbm anexei o ponto onde ocorre o erro no método de assinatura do XML.

Unit1.dfm

Unit1.pas

Ponto do erro 01.png

Ponto do erro 02-Detalhe.png

Carlos H. Marian

Analista de Sistemas

|/-\|

Link para o comentário
Compartilhar em outros sites

  • Fundadores

Fiz testes aqui, movendo a chamada a "CoInitialize(nil); para o Create e "CoUninitialize" para o Destroy... e aparentemente o problema com o A3 não se repetiu...

Realmente CoInitialize deve ser chamada para cada thread:  https://msdn.microsoft.com/en-us/library/windows/desktop/ms678543(v=vs.85).aspx

A correção para o problema do A3, foi na verdade, manter uma lista de Certificados onde a Senha já foi informada previamente... isso continua como está...

Por favor atualize e teste...

  • Curtir 1
Consultor SAC ACBr

Daniel Simões de Almeida
O melhor TEF, é com o Projeto ACBr - Clique e Conheça
Ajude o Projeto ACBr crescer - Assine o SAC

Projeto ACBr     Telefone:(15) 2105-0750 WhatsApp(15)99790-2976.

Link para o comentário
Compartilhar em outros sites

Olá.
   Atualizei os fontes e ao executar a consulta do status do serviço(com Thread) o erro não ocorre.
  Agora ao executar o teste de envio de NFe(com thread) o erro permanece, estou usando um certificado A1.  

  Quando a thread chama a rotina de envio(GNFe.Enviar linha 3388 do demo), é efetuada assinatura do xml(TDFeCapicom.Assinar).
    Neste método(TDFeCapicom.Assinar) tem a chamada para o "CarregarCertificadoSeNecessario"(ACBrDFeCapicom.pas linha 427), como o atributo "FNumCertCarregado" esta diferente de vazio, então ele não chama no método "CarregarCertificado". Talvez pq ele já tenha sido chamado em outro momento.

   Call Stack:
:7c812aeb kernel32.RaiseException + 0x52
:004eb189 OleError + $19
ACBrMSXML2_TLB.CoDOMDocument50.Create
ACBrDFeCapicom.TDFeCapicom.Assinar(???,???,'infNFe')
ACBrDFeSSL.TDFeSSL.Assinar(???,'NFe','infNFe')
ACBrNFeNotasFiscais.NotaFiscal.Assinar
ACBrNFeNotasFiscais.TNotasFiscais.Assinar
ACBrNFe.TACBrNFe.Enviar('11',False,False)
Unit1.TNFEThread.GerarEnviarNfeThread
Unit1.TNFEThread.Execute
:0061e69d TNFEThread.Execute + $19
:00405866 ThreadWrapper + $2A
:7c80b713 ; C:\WINDOWS\system32\kernel32.dll

  

AssinaturaXML01.png

Carlos H. Marian

Analista de Sistemas

|/-\|

Link para o comentário
Compartilhar em outros sites

  • Fundadores

Acho que podemos adotar sua solução, de Try  / Finally...

O meu receio é saber se a chamada a: CoUninitialize não irá atrapalhar outras Threads em execução...

Consultor SAC ACBr

Daniel Simões de Almeida
O melhor TEF, é com o Projeto ACBr - Clique e Conheça
Ajude o Projeto ACBr crescer - Assine o SAC

Projeto ACBr     Telefone:(15) 2105-0750 WhatsApp(15)99790-2976.

Link para o comentário
Compartilhar em outros sites

  • Fundadores

Sua implementação parece mais correta, por fazer melhor uso e liberação dos recursos... e nos meus testes de múltiplas instâncias do ACBrNFe (na mesma thread), continuam funcionando...

Enviei as correções para o SVN

  • Curtir 1
Consultor SAC ACBr

Daniel Simões de Almeida
O melhor TEF, é com o Projeto ACBr - Clique e Conheça
Ajude o Projeto ACBr crescer - Assine o SAC

Projeto ACBr     Telefone:(15) 2105-0750 WhatsApp(15)99790-2976.

Link para o comentário
Compartilhar em outros sites

  • 1 ano depois...

Olá... já tem um bom tempo que já passaram com o erro do CoInitialize, não sei exatamente porque esta me apresentando esse erro, fui olhando os fontes percebi que estava fazendo a chamada duas vezes do CoInitialize. 

Problema esse acontecendo nos EVENTO então é passado no TDFeSSLXmlSignMsXmlCapicom.Assinar que tem o CoInitialize ai no meio do processo do assinar chama outras funções que chega no TDFeCapicom.CarregarCertificado que também tem o CoInitialize e no final da função tem o CoUninitialize que então ao voltar para o TDFeSSLXmlSignMsXmlCapicom.Assinar da erro pois foi utilizado o coUninitialize.

Segue em anexo a alteração que fiz para resolver a minha questão, fiz com base na ideia utilizado no TDFeSSLXmlSignMsXmlCapicom.Assinar que foi criado uma variável para saber se fez o CoInitialize, Se puder subir para o SVN, agradeço.

ACBrDFeCapicom.pas

Atenciosamente.

Eliomar.

Link para o comentário
Compartilhar em outros sites

Olá... Então bem estranho processo e no ACBr_Demo não consegui simular o processo esta assim: 

Tenho um NFePrincipal.pas que tenho algumas funções:

fpuCancelarXML(ipNro_Serie_Token, ipSenha_Token, etc); 
fpuCarta_Correcao(ipNro_Serie_Token, ipSenha_Token, etc); 
fpuConsultaNota(ipNro_Serie_Token, ipSenha_Token, etc); 
fpuEnviarXML(ipNro_Serie_Token, ipSenha_Token, etc); 
fpuInutilizarXML(ipNro_Serie_Token, ipSenha_Token, etc); 

Então tenho um Server.exe que utiliza a NFePrincipal.pas e faço a chamada a essas funções que dentro delas faço uso ao acbr e tudo roda ok blz. 

Ai tenho um EmiteNota.exe que utiliza também a NFePrincipal e faço a mesma chamada a essas funções, nesse EmiteNota.exe que apresenta o problema, que consegui solucionar utilizando a alteração que passei nos comentários anteriores. Já conferi um monte aqui o que estão diferente de cada um dos EXE já que os dois estão usando o mesmo NFeParincipal.pas, porém não encontrei o que pode ser até chegar no acbr.

Atenciosamente.

Eliomar.

Link para o comentário
Compartilhar em outros sites

  • Fundadores

Obrigado pela analise e correção... Realmente trata-se de uma regressão...

Enviei sua sugestão para o SVN, com pequenas modificações...

Consultor SAC ACBr

Daniel Simões de Almeida
O melhor TEF, é com o Projeto ACBr - Clique e Conheça
Ajude o Projeto ACBr crescer - Assine o SAC

Projeto ACBr     Telefone:(15) 2105-0750 WhatsApp(15)99790-2976.

Link para o comentário
Compartilhar em outros sites

  • Este tópico foi criado há 2558 dias atrás.
  • Talvez seja melhor você criar um NOVO TÓPICO do que postar uma resposta aqui.

Crie uma conta ou entre para comentar

Você precisar ser um membro para fazer um comentário

Criar uma conta

Crie uma nova conta em nossa comunidade. É fácil!

Crie uma nova conta

Entrar

Já tem uma conta? Faça o login.

Entrar Agora
×
×
  • Criar Novo...

Informação Importante

Colocamos cookies em seu dispositivo para ajudar a tornar este site melhor. Você pode ajustar suas configurações de cookies, caso contrário, assumiremos que você está bem para continuar.

The popup will be closed in 10 segundos...