br_nfe 1.0.2 → 1.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 95a7593fa277c48b625c3acf17b6f8feb0bf5989
4
- data.tar.gz: d96d3e26d74c21df7d0195f1091d6b80b6dfa1bb
3
+ metadata.gz: 11fb152b3151c62d8608888d5ba95174e4d2a435
4
+ data.tar.gz: 23472fba54d77618bd59b9793295971597513638
5
5
  SHA512:
6
- metadata.gz: 3b6cd55de324a626cff4dbe8dc4afd9a0498e31263bd366fecbd43b7a3378986effa5a029267fe157bed1b5c39bcb1978ca0e9871bc889826faf54a4f34e4968
7
- data.tar.gz: d7db379de7593dff9b50fcb6d63ee158daf540b542ed180149f13ad96d56707ba24d03f0b07fad0dc7516189e3ce7cfdc317c44fb58ec1e3d80501cefefa98ca
6
+ metadata.gz: 732f08b5b62348717188127aca18718c09063a5a56014512825e12fa4528f0a0a37578a0ebb07febeac1d491e212e8ff3bcc689eb0ba73d5ced80d40efe0fe6b
7
+ data.tar.gz: 9cdb3eda197abddafaf1625dff5b4d275cae4cbf6ca7cab83e4dd66e34f286483e8943b415c213cf69c698ae53c38684a18e45cc6c024b2b7157aff4cbc49f2f
data/README.markdown CHANGED
@@ -8,8 +8,8 @@
8
8
  # **BrNfe**
9
9
  Gem para emissão de notas fiscais eletrônicas.
10
10
 
11
- ## Versão 1.0.1
12
11
  **Motivo e Objetivo**
12
+
13
13
  Devido a falta de padronização dos parâmetros e a forma de envio e resposta na transmissão de Notas Fiscais de Serviços (NFS), esta gem vem com o objetivo de obter uma forma padronizada dessa tarefa, e assim, facilitando a vida de muitos desenvolvedores.
14
14
 
15
15
  **O que essa gem faz?**
data/lib/br_nfe/base.rb CHANGED
@@ -3,22 +3,22 @@ module BrNfe
3
3
 
4
4
  include BrNfe::Helper::HaveEmitente
5
5
 
6
- attr_accessor :certificado_password
7
- attr_accessor :certificado_path
8
- attr_accessor :certificado_value
6
+ attr_accessor :certificate_pkcs12_password
7
+ attr_accessor :certificate_pkcs12_path
8
+ attr_accessor :certificate_pkcs12_value
9
9
 
10
10
  validate :validar_emitente
11
- validates :certificado, presence: true, if: :certificado_obrigatorio?
11
+ validates :certificate, :certificate_key, presence: true, if: :certificado_obrigatorio?
12
12
 
13
- # Método que deve ser sobrescrito para as ações que necessitam do certificado para assinatura
13
+ # Método que deve ser sobrescrito para as ações que necessitam do certificate_pkcs12 para assinatura
14
14
  def certificado_obrigatorio?
15
15
  false
16
16
  end
17
17
 
18
- # Caso não tenha o certificado salvo em arquivo, pode setar a string do certificado direto pelo atributo certificado_value
19
- # Caso tenha o certificado em arquivo, basta setar o atributo certificado_path e deixar o atributo certificado_value em branco
20
- def certificado_value
21
- @certificado_value ||= File.read(certificado_path)
18
+ # Caso não tenha o certificate_pkcs12 salvo em arquivo, pode setar a string do certificate_pkcs12 direto pelo atributo certificate_pkcs12_value
19
+ # Caso tenha o certificate_pkcs12 em arquivo, basta setar o atributo certificate_pkcs12_path e deixar o atributo certificate_pkcs12_value em branco
20
+ def certificate_pkcs12_value
21
+ @certificate_pkcs12_value ||= File.read(certificate_pkcs12_path)
22
22
  end
23
23
 
24
24
  attr_accessor :env
@@ -60,13 +60,13 @@ module BrNfe
60
60
  {}
61
61
  end
62
62
 
63
- def certificado
64
- @certificado ||= OpenSSL::PKCS12.new(certificado_value, certificado_password)
63
+ def certificate_pkcs12
64
+ @certificate_pkcs12 ||= OpenSSL::PKCS12.new(certificate_pkcs12_value, certificate_pkcs12_password)
65
65
  rescue
66
66
  end
67
67
 
68
- def certificado=(value)
69
- @certificado = value
68
+ def certificate_pkcs12=(value)
69
+ @certificate_pkcs12 = value
70
70
  end
71
71
 
72
72
  def wsdl_encoding
@@ -89,6 +89,22 @@ module BrNfe
89
89
  })
90
90
  end
91
91
 
92
+ def certificate=(value)
93
+ @certificate = value
94
+ end
95
+
96
+ def certificate
97
+ @certificate ||= certificate_pkcs12.try :certificate
98
+ end
99
+
100
+ def certificate_key
101
+ @certificate_key ||= certificate_pkcs12.try :key
102
+ end
103
+
104
+ def certificate_key=(value)
105
+ @certificate_key = value
106
+ end
107
+
92
108
  private
93
109
 
94
110
  def tag_cpf_cnpj(xml, cpf_cnpj)
@@ -113,7 +129,7 @@ module BrNfe
113
129
 
114
130
  signature.KeyInfo {
115
131
  signature.X509Data {
116
- signature.X509Certificate certificado.certificate.to_s.gsub(/\-\-\-\-\-[A-Z]+ CERTIFICATE\-\-\-\-\-/, "").gsub(/\n/,"")
132
+ signature.X509Certificate certificate.to_s.gsub(/\-\-\-\-\-[A-Z]+ CERTIFICATE\-\-\-\-\-/, "").gsub(/\n/,"")
117
133
  }
118
134
  }
119
135
  end
@@ -140,7 +156,7 @@ module BrNfe
140
156
 
141
157
  def xml_signature_value(xml)
142
158
  sign_canon = canonicalize(xml)
143
- signature_hash = certificado.key.sign(OpenSSL::Digest::SHA1.new, sign_canon)
159
+ signature_hash = certificate_key.sign(OpenSSL::Digest::SHA1.new, sign_canon)
144
160
  remove_quebras Base64.encode64( signature_hash )
145
161
  end
146
162
 
@@ -121,12 +121,21 @@ module BrNfe
121
121
  xml.IssRetido value_true_false(rps.iss_retido?)
122
122
  xml.ResponsavelRetencao "#{rps.responsavel_retencao}".max_size(1) unless rps.responsavel_retencao.blank?
123
123
  xml.ItemListaServico BrNfe::Helper.only_number(rps.item_lista_servico).rjust(4,'0').max_size(5) unless rps.item_lista_servico.blank?
124
- xml.CodigoCnae BrNfe::Helper.only_number(rps.codigo_cnae).max_size(7) unless rps.codigo_cnae.blank?
124
+
125
+ # Não devo enviar o CNAE na base de testes pois o municipio enviado será 0 (zero)
126
+ if env != :test
127
+ xml.CodigoCnae BrNfe::Helper.only_number(rps.codigo_cnae).max_size(7) unless rps.codigo_cnae.blank?
128
+ end
129
+
125
130
  xml.CodigoTributacaoMunicipio "#{rps.codigo_tributacao_municipio}".max_size(20) unless rps.codigo_tributacao_municipio.blank?
126
131
  xml.Discriminacao "#{rps.discriminacao}".max_size(2_000).remove_accents
127
- xml.CodigoMunicipio BrNfe::Helper.only_number(rps.codigo_municipio).max_size(7)
132
+
133
+ # Na base de testes devo enviar o código do município como 0 (zero)
134
+ xml.CodigoMunicipio (env == :test ? 0 : BrNfe::Helper.only_number(rps.codigo_municipio).max_size(7))
135
+
128
136
  # Não posso enviar o CodigoPais se a exigibilidade_iss não for 4 (exportação) - by bethagambis.com
129
137
  xml.CodigoPais BrNfe::Helper.only_number(rps.codigo_pais).max_size(4) if !rps.codigo_pais.blank? && rps.exigibilidade_iss == '4'
138
+
130
139
  xml.ExigibilidadeISS "#{rps.exigibilidade_iss}".max_size(2)
131
140
  xml.MunicipioIncidencia BrNfe::Helper.only_number(rps.municipio_incidencia).max_size(7) unless rps.municipio_incidencia.blank?
132
141
  xml.NumeroProcesso rps.numero_processo.max_size(30) unless rps.numero_processo.blank?
@@ -14,6 +14,7 @@ module BrNfe
14
14
  record.validates :data_emissao, :item_lista_servico, :discriminacao, :codigo_municipio,
15
15
  :valor_servicos, :base_calculo, presence: true
16
16
  record.validates :valor_iss, :aliquota, presence: true, unless: :iss_retido?
17
+ record.validates :municipio_incidencia, presence: true, if: :municipio_incidencia_obrigatorio?
17
18
 
18
19
  record.validates :valor_servicos, :valor_deducoes, :valor_pis, :valor_cofins, :valor_inss, :valor_ir,
19
20
  :valor_csll, :outras_retencoes, :valor_iss, :aliquota, :base_calculo,
@@ -98,6 +99,10 @@ module BrNfe
98
99
  destinatario.errors.full_messages.map{|msg| errors.add(:base, "Destinatário: #{msg}") }
99
100
  end
100
101
  end
102
+
103
+ def municipio_incidencia_obrigatorio?
104
+ "#{exigibilidade_iss}".in?(['1','01','6','06','7','07'])
105
+ end
101
106
  end
102
107
  end
103
108
  end
@@ -1,8 +1,8 @@
1
1
  module BrNfe
2
2
  module Version
3
3
  MAJOR = 1 #inclui alterações de API e pode quebrar compatibilidade com versões anteriores
4
- MINOR = 0 #inclui novas funcionalidades, sem quebrar APIs existentes
5
- PATCH = 2 #corrige bugs ou traz melhorias em implementações já existentes
4
+ MINOR = 1 #inclui novas funcionalidades, sem quebrar APIs existentes
5
+ PATCH = 0 #corrige bugs ou traz melhorias em implementações já existentes
6
6
  CURRENT = "#{MAJOR}.#{MINOR}.#{PATCH}"
7
7
  end
8
8
  end
data/lib/br_nfe.rb CHANGED
@@ -41,7 +41,6 @@ module BrNfe
41
41
  autoload :Destinatario
42
42
  autoload :Response
43
43
  autoload :Base
44
- autoload :Seed
45
44
  autoload :CondicaoPagamento
46
45
 
47
46
  module Servico
@@ -7,19 +7,23 @@ describe BrNfe::Base do
7
7
  let(:emitente) { FactoryGirl.build(:emitente) }
8
8
 
9
9
  before do
10
- subject.stubs(:certificado).returns(certificado)
10
+ subject.stubs(:certificate_pkcs12).returns(certificado)
11
11
  end
12
12
 
13
13
  describe "validations" do
14
14
  context "obrigatoriedade do certificado" do
15
- before { subject.unstub(:certificado) }
15
+ before { subject.unstub(:certificate_pkcs12) }
16
16
  it "deve ser obrigatorio se certificado_obrigatorio? for true" do
17
- subject.expects(:certificado_obrigatorio?).returns(true)
18
- must validate_presence_of(:certificado)
17
+ subject.stubs(:certificado_obrigatorio?).returns(true)
18
+ subject.certificate_pkcs12 = nil
19
+ must validate_presence_of(:certificate)
20
+ must validate_presence_of(:certificate_key)
19
21
  end
20
22
  it "não deve ser obrigatorio se certificado_obrigatorio? for false" do
21
- subject.expects(:certificado_obrigatorio?).returns(false)
22
- wont validate_presence_of(:certificado)
23
+ subject.stubs(:certificado_obrigatorio?).returns(false)
24
+ subject.certificate_pkcs12 = nil
25
+ wont validate_presence_of(:certificate)
26
+ wont validate_presence_of(:certificate_key)
23
27
  end
24
28
  end
25
29
  context "validação do emitente" do
@@ -61,15 +65,15 @@ describe BrNfe::Base do
61
65
  subject.certificado_obrigatorio?.must_equal false
62
66
  end
63
67
 
64
- describe "#certificado_value" do
68
+ describe "#certificate_pkcs12_value" do
65
69
  it "se tiver algum valor setado deve retornar esse valor" do
66
- subject.certificado_value = "algum valor"
67
- subject.certificado_value.must_equal "algum valor"
70
+ subject.certificate_pkcs12_value = "algum valor"
71
+ subject.certificate_pkcs12_value.must_equal "algum valor"
68
72
  end
69
73
  it "se não tiver um valor deve carregar o arquivo setado no atributo certificado_path" do
70
- subject.certificado_path = "algum/lugar.pfx"
74
+ subject.certificate_pkcs12_path = "algum/lugar.pfx"
71
75
  File.expects(:read).with("algum/lugar.pfx").returns("valor do arquivo")
72
- subject.certificado_value.must_equal "valor do arquivo"
76
+ subject.certificate_pkcs12_value.must_equal "valor do arquivo"
73
77
  end
74
78
  end
75
79
 
@@ -203,7 +207,7 @@ describe BrNfe::Base do
203
207
  it "deve assinar um xml com o certificado" do
204
208
  sh1 = OpenSSL::Digest::SHA1.new
205
209
  OpenSSL::Digest::SHA1.stubs(:new).returns(sh1)
206
- subject.certificado.key.expects(:sign).with(sh1, "<Um><Xml> Com valor</Xml></Um>").returns('mv\xBFH\xE3\xF5Z\x0F\xE1*0D')
210
+ subject.certificate_pkcs12.key.expects(:sign).with(sh1, "<Um><Xml> Com valor</Xml></Um>").returns('mv\xBFH\xE3\xF5Z\x0F\xE1*0D')
207
211
 
208
212
  subject.send(:xml_signature_value, xml).must_equal 'bXZceEJGSFx4RTNceEY1Wlx4MEZceEUxKjBE'
209
213
  end
@@ -260,23 +264,23 @@ describe BrNfe::Base do
260
264
  end
261
265
  end
262
266
 
263
- describe "#certificado" do
267
+ describe "#certificate_pkcs12" do
264
268
  before do
265
- subject.unstub(:certificado)
269
+ subject.unstub(:certificate_pkcs12)
266
270
  end
267
- it "deve ler o certificado PKCS12 do atributo certificado_value e com a senha do certificado_password" do
268
- subject.assign_attributes(certificado_value: "CERTIFICADO", certificado_password: 'pWd123')
269
- OpenSSL::PKCS12.expects(:new).with("CERTIFICADO", 'pWd123').returns('certificado')
270
- subject.certificado.must_equal 'certificado'
271
+ it "deve ler o certificate_pkcs12 PKCS12 do atributo certificate_pkcs12_value e com a senha do certificate_pkcs12_password" do
272
+ subject.assign_attributes(certificate_pkcs12: nil, certificate_pkcs12_value: "CERTIFICADO", certificate_pkcs12_password: 'pWd123')
273
+ OpenSSL::PKCS12.expects(:new).with("CERTIFICADO", 'pWd123').returns('certificate_pkcs12')
274
+ subject.certificate_pkcs12.must_equal 'certificate_pkcs12'
271
275
  end
272
- it "se já tem um certificado na variavel @certificado não deve ler novamente do PKCS12" do
273
- subject.instance_variable_set(:@certificado, certificado)
276
+ it "se já tem um certificate_pkcs12 na variavel @certificate_pkcs12 não deve ler novamente do PKCS12" do
277
+ subject.instance_variable_set(:@certificate_pkcs12, certificado)
274
278
  OpenSSL::PKCS12.expects(:new).never
275
- subject.certificado.must_equal certificado
279
+ subject.certificate_pkcs12.must_equal certificado
276
280
  end
277
- it "posso setar o certificado" do
278
- subject.certificado = 'certificado 123'
279
- subject.certificado.must_equal 'certificado 123'
281
+ it "posso setar o certificate_pkcs12" do
282
+ subject.certificate_pkcs12 = 'certificate_pkcs12 123'
283
+ subject.certificate_pkcs12.must_equal 'certificate_pkcs12 123'
280
284
  end
281
285
  end
282
286
 
@@ -11,7 +11,11 @@ describe BrNfe::Servico::Betha::V1::CancelamentoNfs do
11
11
  describe "validations" do
12
12
  it { must validate_presence_of(:numero_nfse) }
13
13
  it { must validate_presence_of(:codigo_cancelamento) }
14
- it { must validate_presence_of(:certificado) }
14
+ context "validações do certificado" do
15
+ before { subject.certificate_pkcs12 = nil }
16
+ it { must validate_presence_of(:certificate) }
17
+ it { must validate_presence_of(:certificate_key) }
18
+ end
15
19
  end
16
20
 
17
21
  describe "#wsdl" do
@@ -12,7 +12,11 @@ describe BrNfe::Servico::Betha::V1::RecepcaoLoteRps do
12
12
 
13
13
  describe "validations" do
14
14
  it { must validate_presence_of(:numero_lote_rps) }
15
- it { must validate_presence_of(:certificado) }
15
+ context "validações do certificado" do
16
+ before { subject.certificate_pkcs12 = nil }
17
+ it { must validate_presence_of(:certificate) }
18
+ it { must validate_presence_of(:certificate_key) }
19
+ end
16
20
 
17
21
  it "deve chamar o metodo validar_lote_rps" do
18
22
  subject.expects(:validar_lote_rps)
@@ -13,7 +13,11 @@ describe BrNfe::Servico::Betha::V2::CancelamentoNfs do
13
13
  describe "validations" do
14
14
  it { must validate_presence_of(:numero_nfse) }
15
15
  it { must validate_presence_of(:codigo_cancelamento) }
16
- it { must validate_presence_of(:certificado) }
16
+ context "validações do certificado" do
17
+ before { subject.certificate_pkcs12 = nil }
18
+ it { must validate_presence_of(:certificate) }
19
+ it { must validate_presence_of(:certificate_key) }
20
+ end
17
21
  end
18
22
 
19
23
  describe "#method_wsdl" do
@@ -10,7 +10,12 @@ describe BrNfe::Servico::Betha::V2::EnvioLoteRpsSincrono do
10
10
 
11
11
  describe "validations" do
12
12
  it { must validate_presence_of(:numero_lote_rps) }
13
- it { must validate_presence_of(:certificado) }
13
+
14
+ context "validações do certificado" do
15
+ before { subject.certificate_pkcs12 = nil }
16
+ it { must validate_presence_of(:certificate) }
17
+ it { must validate_presence_of(:certificate_key) }
18
+ end
14
19
 
15
20
  it "deve chamar o metodo validar_lote_rps" do
16
21
  subject.expects(:validar_lote_rps)
@@ -1,7 +1,7 @@
1
1
  require 'test_helper'
2
2
 
3
3
  describe BrNfe::Servico::Betha::V2::GeraNfse do
4
- subject { FactoryGirl.build(:br_nfe_servico_betha_v2_gera_nfse, emitente: emitente, rps: rps, certificado: certificado) }
4
+ subject { FactoryGirl.build(:br_nfe_servico_betha_v2_gera_nfse, emitente: emitente, rps: rps, certificate_pkcs12: certificado) }
5
5
  let(:emitente) { FactoryGirl.build(:emitente) }
6
6
  let(:rps) { FactoryGirl.build(:br_nfe_rps) }
7
7
  let(:certificado) { Certificado.new }
@@ -11,8 +11,12 @@ describe BrNfe::Servico::Betha::V2::GeraNfse do
11
11
  end
12
12
 
13
13
  describe "validations" do
14
- it { must validate_presence_of(:certificado) }
15
-
14
+
15
+ context "validações do certificado" do
16
+ before { subject.certificate_pkcs12 = nil }
17
+ it { must validate_presence_of(:certificate) }
18
+ it { must validate_presence_of(:certificate_key) }
19
+ end
16
20
  context "deve validar o rps" do
17
21
  it "quando o rps for válido não deve setar nenhuma mensagem no objeto" do
18
22
  rps.stubs(:errors).returns(stub(full_messages: ["Erro rps"]))
@@ -10,7 +10,12 @@ describe BrNfe::Servico::Betha::V2::RecepcaoLoteRps do
10
10
 
11
11
  describe "validations" do
12
12
  it { must validate_presence_of(:numero_lote_rps) }
13
- it { must validate_presence_of(:certificado) }
13
+
14
+ context "validações do certificado" do
15
+ before { subject.certificate_pkcs12 = nil }
16
+ it { must validate_presence_of(:certificate) }
17
+ it { must validate_presence_of(:certificate_key) }
18
+ end
14
19
 
15
20
  it "deve chamar o metodo validar_lote_rps" do
16
21
  subject.expects(:validar_lote_rps)
@@ -1,7 +1,7 @@
1
1
  require 'test_helper'
2
2
 
3
3
  describe BrNfe::Servico::Betha::V2::SubstituicaoNfse do
4
- subject { FactoryGirl.build(:br_nfe_servico_betha_v2_substituicao_nfse, emitente: emitente, rps: rps, certificado: certificado) }
4
+ subject { FactoryGirl.build(:br_nfe_servico_betha_v2_substituicao_nfse, emitente: emitente, rps: rps, certificate_pkcs12: certificado) }
5
5
  let(:emitente) { FactoryGirl.build(:emitente) }
6
6
  let(:rps) { FactoryGirl.build(:br_nfe_rps) }
7
7
  let(:certificado) { Certificado.new }
@@ -11,7 +11,11 @@ describe BrNfe::Servico::Betha::V2::SubstituicaoNfse do
11
11
  end
12
12
 
13
13
  describe "validations" do
14
- it { must validate_presence_of(:certificado) }
14
+ context "validações do certificado" do
15
+ before { subject.certificate_pkcs12 = nil }
16
+ it { must validate_presence_of(:certificate) }
17
+ it { must validate_presence_of(:certificate_key) }
18
+ end
15
19
  it { must validate_presence_of(:numero_nfse) }
16
20
  it { must validate_presence_of(:codigo_cancelamento) }
17
21
 
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: br_nfe
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.0.2
4
+ version: 1.1.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Bruno M. Mergen
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2015-09-29 00:00:00.000000000 Z
11
+ date: 2015-10-14 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: rake