Ir para conteúdo
  • Cadastre-se

dev botao

Implementação Nfse São Paulo


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

Recommended Posts

Boa tarde Senhores.
Venho a enviá-los a implementação parcial do provedor de São Paulo no ACBRNFSe.
O que foi desenvolvido foi: Envio de lote, Consulta de lote, Cancelamento e a Impressão do DANFSe.
Devido a falta de tempo, acabou não ficando redonda a implementação, necessitando de alguns ajustes, porém estaremos disponibilizando os fontes, e se alguém quiser terminar ela, será possível.
Tivemos que desenvolver uma dll para assinatura do RPS, já que a capicom assina a tag de assinatura junto com o xml, e a assinatura de rps do provedor de SP só deve ser feita em cima de uma string de aproximadamente 200 caracteres, que junta algumas informações do cliente.
A dll desenvolvida foi feita em C#, versão .net framework 2.0, e está nomeada como ACBRAssinaRPSSP.dll, juntamente com ela está o arquivo ACBRAssinaRPSSP.TLB, que se faz necessário para o uso no delphi.
Essa dll vai fazer a assinatura pela string que lhe é passada e pelo número do certificado digital, o qual fica dentro das configurações de webservice do ACBR e que alimenta a dll.
O código fonte e o projeto que gerou essa dll em C# está anexa como AcbrAssinaRPSSP-DLL.zip
Detalhe: Desenvolvemos no MS Visual Studio 2010.
Aliás, caso alguém saiba como fazer a assinatura de uma string com o algoritmo de rsa-sha1 via delphi, ou utilizando a capicom pelo certificado digital, seria de grande interesse o compartilhamento (Eliminaríamos essa dll que tivemos que desenvolver pelo menos).
 
Vamos aos fatos:
 
-Criamos o provedor como proSP, pois não sabíamos qual provedor é que atendia a cidade, já que encontramos Tiplan e Prodam como prestadores de serviço para a cidade de São Paulo.
 
-O layout desta NFSe não segue o padrão ABRASF, então foi necessário modificar algumas coisas em vários locais. Fiquem atentos a isso, caso irão mexer.
 
-A NFSe de São Paulo acabou desativando o ambiente de testes, fomos informados pela prefeitura através do email [email protected] (a qual vocês podem se dirigir caso tenham dúvidas referente a manuais ou formas de implementação): "Prezado(a) Sr(a).
Informamos que a Secretaria de Finanças da Prefeitura de São Paulo não está mais disponbilizando o ambiente para testes e homologação dos sistemas da NFS-e e NFTS.
A alternativa é utilizar o serviço TesteEnvioLoteRPS no ambiente de produção, como consta no Manual de Envio de Arquivo – Envio de Lotes de RPS, cujo acesso é por certificado digital da empresa.
Caso a resposta acima não seja suficiente, retorne o contato com maiores informações sobre o certificado utilizado e a descrição da situação na qual o erro ocorreu.
Consulte “Perguntas e Respostas” no endereço eletrônico http://nfpaulistana.prefeitura.sp.gov.br/informacoes_gerais.asp
Consulte, também, o link "Manuais" no mesmo endereço."
 
-Para condizer com o relatado acima, foi alterado o envelope que é enviado para o ambiente de produção. Um detalhe, no ambiente de produção com o envelope de testes, sempre é retornado o lote 0, ou seja, se uma nota é enviada para a prefeitura como teste, não é possível consultar a situação dela, pois o lote sempre é retornado como 0. Também entramos em contato com a prefeitura e confirmamos essa premissa, o que levou-nos a emitir uma nota fiscal em ambiente de produção para poder continuar a implementação.
 
-A dll que foi desenvolvida, será utilizada para envio do lote rps e também para assinar o cancelamento. Além disso, todos os documentos são assinados como normalmente são os outros, assinados pela capicom na tag <Signature>.
 
-Caso alguém tenha dúvidas ou não entenda da forma que fora desenvolvida, estou a disposição para ajudá-los.
 
-Em todos os lugares que foram feitas alterações, e que eu me lembrei de marcar, há um comentário do tipo "{add-SP}", mostrando o que foi alterado, e se não compreensível o porquê dele, haverá descrição do que foi feito.
 
-Pode ter acontecido de algumas informações ficarem omissas ou ainda, erradas, mas todas as que verifiquei me pareceram certas, e caso alguém encontre algum problema, será interessante reportar ele, pois, haverá maior facilidade de correção.
 
-Esse tópico do próprio ACBR nos ajudou bastante:
 
-Caso vocês notem a falta de algum arquivo, ou a falta de alguma função / procedure ou afins, comunique-me.
 
-Essa NF para esse provedor deverá ser mais testado, para ter certeza que tudo ficou certo.
 
 
Qualquer dúvida fico a disposição,
 
Atenciosamente,
Ariel.

ArquivosSP.zip

Editado por arieldll
  • Curtir 3
Link para o comentário
Compartilhar em outros sites

  • 2 semanas depois ...

Bom dia.

A princípio está funcionando, o que se faz necessário são testes para realmente efetivar que nada ficou esquecido.

Seria necessário mais alguns testes, e se na forma correta, enviar os fontes para o repositório oficial.

 

 

Atenciosamente,

Ariel.

Link para o comentário
Compartilhar em outros sites

Arieldll, Estou tendo o seguinte retorno da dll : "Erro ao assinar RPS"

 

 

 

store.Certificates.Find(X509FindType.FindBySerialNumber, serial, true) aparentemente não me retorna nada, testei com mais de um certificado!

 

Não posso instalar o Visual Studio aqui na empresa então se tiver alguma ideia do que pode ser ajudaria.

Link para o comentário
Compartilhar em outros sites

Sim estou usando a sua dll... não tenho como instalar aqui o Visual Studio pra debuga e localiza o problema.

 

Apenas na tag <Assinatura> veio "Erro ao assinar RPS"...

 

Busquei nos fontes e localizei o seguinte código em CAssinaRPSSP com esta mensagem: 

 

 

 public string AssinarRPSSP(string serial, string original)

        {
            //X509Store store = new X509Store(StoreLocation.LocalMachine); 
            X509Store store = new X509Store();
            store.Open(OpenFlags.ReadOnly);
            string sn = serial, criptografada; //" put here your certificate serial number "; 
            criptografada = "";
            X509Certificate2Collection coll = store.Certificates.Find(X509FindType.FindBySerialNumber, serial, true);
            X509Certificate2 cert = null;
 
            Console.WriteLine(coll.Count);
 
            if (coll.Count > 0 && coll[0] != null)
            {
                cert = coll[0];
            }
            else return "Erro ao assinar RPS";
 
            //recebe o certificado e a string a ser assinada 
            System.Text.ASCIIEncoding enc = new System.Text.ASCIIEncoding();
            RSACryptoServiceProvider rsa = new RSACryptoServiceProvider();
            //pega a chave privada do certificado digital 
            rsa = cert.PrivateKey as RSACryptoServiceProvider;
            //cria o array de bytes e realiza a conversao da string em array de bytes 
            byte[] sAssinaturaByte = enc.GetBytes(original);
 
            RSAPKCS1SignatureFormatter rsaf = new RSAPKCS1SignatureFormatter(rsa);
            SHA1CryptoServiceProvider sha1 = new SHA1CryptoServiceProvider();
 
            //cria a variavel hash que armazena o resultado do sha1 
            byte[] hash;
            hash = sha1.ComputeHash(sAssinaturaByte);
 
            //definimos o metodo a ser utilizado na criptografia e assinamos 
            rsaf.SetHashAlgorithm("SHA1");
            sAssinaturaByte = rsaf.CreateSignature(hash);
 
            //por fim fazemos a conversao do array de bytes para string 
            criptografada = Convert.ToBase64String(sAssinaturaByte);
            return criptografada;
        }
Link para o comentário
Compartilhar em outros sites

O que está ocorrendo na realidade, é que a instância "coll"  está sendo criada, mas ela é do tipo null, ou seja, nula, pois o certificado não está sendo encontrado para gerar uma instância do objeto do tipo X509Certificate2Collection. Neste trecho: 

X509Certificate2Collection coll = store.Certificates.Find(X509FindType.FindBySerialNumber, serial, true);

Verifique o que está indo como parâmetro para  a função que invoca a dll, nos parâmetros "serial" e "original". O serial deve ser o mesmo que está carregado no ACBRNFSe, e o original uma string contendo um conjunto de caracteres que são a assinatura em si.

 

Caso não consiga descobrir o que pode ser o problema, pegue um serial que você tenha certeza que esteja instalado, e alimente manualmente a dll para saber se há retorno ou não.

 

Atenciosamente,

Ariel.

Editado por arieldll
Link para o comentário
Compartilhar em outros sites

Sim, o numero de série do certificado esta indo da forma correta... Estou fazendo testes no Demo do ACBRNFSe,

 

verifiquei se havia algum carácter estranho no serial passado, o serial esta sem espaços em branco e com todas as letras maiúsculas:

 

9EE97BE21273858C47852A96058722C6

 

e a chave que estou passando:

 

00000000UNICA00000000023420140605TNN00000000016855000000000000000001.07299999999000191

 

O certificado esta devidamente instalado, porém este certificado foi gerado por mim, mas acredito que isso não faça diferença.

Link para o comentário
Compartilhar em outros sites

Você já tentou com outro certificado?

Caso não tenha tentado ainda, tente com outro. Nós testamos com um certificado emitido pela Serasa, e aparentemente não tivemos problemas.

Essa DLL foi compilada para o .net framework 2.0.

Esqueci de pedir, mas qual versão do windows você está utilizando?

 

Atenciosamente,

Ariel.

Editado por arieldll
Link para o comentário
Compartilhar em outros sites

Bom dia. 

Não quero causar divergências, apenas contribuir para a discussão.

Rafael, eu estou utilizando um certificado realmente emitido por uma empresa certificadora e alimentando a dll manualmente: não obtenho esse erro.

Não estou utilizando o componente ACBr,estou alimentando a dll manualmente.

 

Ariel, ao tentar registrar a dll obtenho o conhecido erro: "entry point was not found". Em resumo, tive que registrá-la pelo regasm do .net 2.0. É isso mesmo?

 

Obrigado.

Link para o comentário
Compartilhar em outros sites

Como adapto para usar no Demo do ACBrNFSe?

 

Edit: Consegui começar a rodar, mas na hora que vai assinar, chama o procedimento CoCAssinaRPSSP.Create, e dá erro de Classe Não Registrada.

 

Já adicionei o TLB ao Delphi e compilei, porém não consigo registrar a DLL de maneira alguma pelo regsvr32, como fizeram para registrar, ou até mesmo para gerar uma nova DLL?

Editado por F Almeida
Link para o comentário
Compartilhar em outros sites

Almeida, boa tarde.

Verifique se, em seu computador, existe o seguinte diretório:

C:\Windows\Microsoft.NET\Framework\v2.0.XXXXX (framework .net versão 2.0. Provavelmente seu computador possuirá estas e outras mais novas)

Dentro dele há um executável: RegAsm.exe

 

Execute-o, pela linha de comando, com esse formato: regasm mydll.dll /tlb:mydll.tlb.

No nosso caso: regasm AcbrAssinaRPSSP.dll /tlb:AcbrAssinaRPSSP.tlb.

 

Atente-se ao fato de que para executar o regasm, você deve precisa indicar o diretório em que ele se encontra, como por ex:

C:\Windows\Microsoft.NET\Framework\v2.0.XXXXX\regasm c:\windows\AcbrAssinaRPSSP.dll /tlb:AcbrAssinaRPSSP.tlb

Pelo que eu entendi, tudo isso deve-se ao fato dessa dll ser um deploy do .net.

Link para o comentário
Compartilhar em outros sites

cabongue,

 

Consegui seguindo esse procedimento, após uma busca encontrei em um fórum em inglês e foi a saída. Este mesmo comando.

 

Estou conseguindo gerar a NFSe até o fim, porém após executar todos os procedimentos e estar com o XML, na demo dá o erro "Falha de Validação, o documento não contem exatamente um nó raíz", verificando no código notei que o XML de Envio de Lote chega a um ponto que faz "<RPS> <infRps </RPS>", ou seja, falta toda a informação do RPS em si.

 

Irei tentar implementar estes componentes para um sistema que já emite NFSe para padrão GINFES, este componente teria alguma incompatibilidade ou ele suporta todos?

Editado por F Almeida
Link para o comentário
Compartilhar em outros sites

Caros, bom dia.

Referente a dll, não consegui fazer o delphi importar o assembly gerado pela dll se não fosse com o deploy. Se vocês souberem como fazer isso de uma forma mais funcional e elegante, por favor, compartilhem.

 

FAlmeida, pelo que entendi o padrão que você citou é o ABRASF, o qual o provedor de NFSe de São Paulo infelizmente não se adequa, pois, tem um layout próprio, e que em minha implementação, na hora em que o xml é gerado nesse ponto, há uma função personalizada especialmente para o provedor de SP. Seguem anexos os exemplos oficiais dos xmls disponibilizados pela prefeitura de São Paulo.

 

Não entendi sua última pergunta sobre incompatibilidade, poderia ser mais claro?

 

Atenciosamente,

Ariel.

exemplos.zip

Editado por arieldll
Link para o comentário
Compartilhar em outros sites

Bom dia Ariel,

 

Eu tenho duas pastas do ACBrNFSe, um com a versão oficial, que uso em um projeto que já gera a NFSe padrão de Guarulhos, e outra pasta com o ACBrNFSe que você disponibilizou para a NFSe de São Paulo, eu preciso fazer um sistema que já gera NFSe de Guarulhos gerar também a Paulistana, por isso pergunto se no seu componente ainda há as rotinas para os antigos padrões ou foi tudo mesmo modificado para a Paulistana, inutilizando as rotinas de outros padrões?

 

Estou gerando RPS sem problemas com seu componente, porém quando vou Gerar Lote de RPS e Enviar, dá o seguinte erro :

 

"O elemento '{http://www.prefeitura.sp.gov.br/nfe/PedidoEnvioLoteRPS_v01.xsd}RPS' é inesperado, de acordo com o modelo de conteúdo do elemento pai '{http://www.prefeitura.sp.gov.br/nfe}PedidoEnvioLoteRPS"

 

E quando vou apenas gerar e enviar uma NFSe de um único RPS:

"Falha de Validação, o documento não contem exatamente um nó raíz"

Link para o comentário
Compartilhar em outros sites

Continua normal, o que foi alterado são as funções que geram os xmls dentro do componente. Como você vai passar os dados, será de mesma forma que os outros provedores, apenas o que vai mudar talvez, são pequenos detalhes em alguns campos. Não foram inutilizadas as rotinas, mas é que elas simplesmente não se encaixam nesse tipo de xml, então quase todas as rotinas de leitura e escrita de xmls tiveram que ser novamente criadas especialmente para esse provedor, mas as dos outros provedores foram mantidas e não alteradas.

 

Você está utilizando as schemas que foram dispostas no meu primeiro envio da implementação?

Se não for com esses, não vai funcionar de jeito algum, pois o padrão é totalmente diferente.

 

Apenas utilize a função "Enviar", deve funcionar.

Qualquer coisa, poste o trecho do código do método de envio que você está fazendo.

 

Atenciosamente,

Ariel.

Editado por arieldll
Link para o comentário
Compartilhar em outros sites

Entendido, irei mudar o caminho e se necessário o nome do componente para poder adicionar e não substituir o componente que gera da NFSe de Guarulhos.

 

Estou usando os schemas que vieram dentro do .rar, extraídos para Schemas/SP, como o programa pediu.

 

No caso de gerar e enviar NFSe, ele dá o erro nesta rotinha:

   if FProvedorClass.GetValidarLote
    then begin
     if not(NotaUtil.Valida(FDadosMsg, FMsg,
                            FConfiguracoes.Geral.PathSchemas,
                            FConfiguracoes.WebServices.URL,
                            FConfiguracoes.WebServices.ServicoEnviar,
                            FConfiguracoes.WebServices.Prefixo4))
      then raise Exception.Create('Falha na validação do Lote ' +
                     IntToStr(TNFSeGerarNFSe(Self).NumeroRps) + sLineBreak + FMsg);

Salvo a variável FDadosMsg em um .txt e noto que tem ela está sem nada e com erro de sintáxe:

<PedidoEnvioRPS xmlns="http://www.prefeitura.sp.gov.br/nfe" xmlns="http://www.prefeitura.sp.gov.br/nfe/TiposNFe_v01.xsd">
	<LoteRps Id="1011" versao="2.2">
		<NumeroLote>1011</NumeroLote>
		<Cnpj>00647811000189</Cnpj>
		<InscricaoMunicipal>1170690014</InscricaoMunicipal>
		<QuantidadeRps>1</QuantidadeRps>
		<ListaRps>
			<Rps>
				<InfRps
			</Rps>
		</ListaRps>
	</LoteRps>
</PedidoEnvioRPS>

Enquanto salvo o XML inteiro e está tudo OK e sem erros, pelo visto algum bug quando ele gera o DadosMsg, na Função TNFSeG.Gera_DadosMsgGerarNFSe, dentro da Unit "pnfsNFSeG"

 

Att,

Felipe.

Link para o comentário
Compartilhar em outros sites

Fora implementado o PedidoEnvioLoteRPS, o qual você pode enviar 1 ou vários RPS.

Se você está tentando utilizar o PedidoEnvioRPS, terá que implementar ele, mas não vejo necessidade neste caso.

Não sei se entendi bem o que anda acontecendo, mas é muito estranho estar gerando esse xml, pois o de envio de lote RPS para o provedor SP é algo como:

<PedidoEnvioLoteRPS xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns="http://www.prefeitura.sp.gov.br/nfe">
  <Cabecalho Versao="1" xmlns="">
    <CPFCNPJRemetente>
      <CNPJ>04642554000143</CNPJ>
    </CPFCNPJRemetente>
    <transacao>false</transacao>
    <dtInicio>2007-01-20</dtInicio>
    <dtFim>2007-01-20</dtFim>
    <QtdRPS>2</QtdRPS>
    <ValorTotalServicos>2000</ValorTotalServicos>
    <ValorTotalDeducoes>200</ValorTotalDeducoes>
  </Cabecalho>
  <RPS xmlns="">
    <Assinatura>ro6Og7L5BMPpYZKXfSSITNe8U9C4a95P9dIspX8R0Okg1CRsA87N08Llaq+q6IVOGLhjGMkAELBIkQ8T0BGR3czgtJAuOcgMlOmGZlgziWAg3Kww3pFD+rYxE+DRgL2M5QXTaZEYwVNj0lZyJpt1nS9LHUqO7PB+ivYRk+ewUVA=</Assinatura>
    <ChaveRPS>
      <InscricaoPrestador>31000000</InscricaoPrestador>
      <SerieRPS>LLLLL</SerieRPS>
      <NumeroRPS>1</NumeroRPS>
    </ChaveRPS>
.
.
.
.
</PedidoEnvioLoteRPS>

Atenciosamente,

Ariel

Editado por arieldll
Link para o comentário
Compartilhar em outros sites

Edit: Encontrei o erro, eu estava passando o XMLNS da tag RPS como ""http://www.prefeitura.sp.gov.br/nfe", após isso o XML em si parece estar certo, porém a validação retorna um erro de "De acordo com o DTD ou o esquema, o conteúdo do elemento '{http://www.prefeitura.sp.gov.br/nfe}PedidoEnvioLoteRPS' está incompleto",  porque eu estava passando o XMLNS direto para o Schema, cujo a URL parece não existir, agora estou passando a URL apenas para a tag "pai", que é a PedidoEnvioLoteRPS, exatamente como está no exemplo que você postou e continuo tendo este erro, dizendo que falta algo no XML...

 

O XML está saindo assim:

<PedidoEnvioLoteRPS xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns="http://www.prefeitura.sp.gov.br/nfe">
	<Cabecalho xmlns="" Versao="1">
		<CPFCNPJRemetente>
			<CNPJ>00647811000189</CNPJ>
		</CPFCNPJRemetente>
		<transacao>false</transacao>
		<dtInicio>2014-06-10</dtInicio>
		<dtFim>2014-06-10</dtFim>
		<QtdRPS>1</QtdRPS>
		<ValorTotalServicos>1.00</ValorTotalServicos>
		<ValorTotalDeducoes>0.00</ValorTotalDeducoes>
	</Cabecalho>
	<RPS xmlns="">
		<Assinatura>VbgbLlqpuoaiwKaaVANOr+iQTGzexZqtJ9tCHTNhoxNanjy1OTES/9GVVbl1MtcMT9ZeCUYYR/TD2q4e/eprKGIi4A3NLMNw5QMwLtmGmPQSoiLHByMrLlp/Q4lHJwfxth5rC/HHjW5EvpaYpCW/OHSg1fl2XxvWDVT8xhmJXZYQHIslpi7bFp44WNx0Wi8iWzX0m1SzNEqZwWTH4AIgZGpWE7tLE+acMQ6+amq7r0ODSmwMDHoHvIBO0YQNhSiObvechHw9E3br1NiPpm3Tq02zXRuhQcU/R1ps72hk+EbQgeMAfI3yTYItCIa7uEFTtdcxfdJxz2kaXbHvPBVm3g==</Assinatura>
		<ChaveRPS>
			<InscricaoPrestador>11706900</InscricaoPrestador>
			<SerieRPS>UNICA</SerieRPS>
			<NumeroRPS>1011</NumeroRPS>
		</ChaveRPS>
.
.
.
.
               </RPS>
</PedidoEnvioLoteRPS>

 
 
 
 

Creio que isso seja problema com a URL de Schemas?

Editado por F Almeida
Link para o comentário
Compartilhar em outros sites

  • Este tópico foi criado há 2903 dias atrás.
  • Talvez seja melhor você criar um NOVO TÓPICO do que postar uma resposta aqui.
Visitante
Este tópico está agora fechado para novas respostas
×
×
  • 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.