br_nfe 1.0.0 → 1.0.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (68) hide show
  1. checksums.yaml +4 -4
  2. data/Gemfile.lock +4 -1
  3. data/README.markdown +263 -1
  4. data/br_nfe.gemspec +14 -5
  5. data/lib/br_nfe/base.rb +6 -1
  6. data/lib/br_nfe/helper/cpf_cnpj.rb +0 -5
  7. data/lib/br_nfe/helper/have_address.rb +1 -5
  8. data/lib/br_nfe/helper/have_rps.rb +7 -0
  9. data/lib/br_nfe/servico/betha/base.rb +52 -41
  10. data/lib/br_nfe/servico/betha/build_response.rb +141 -0
  11. data/lib/br_nfe/servico/betha/v1/build_response.rb +4 -102
  12. data/lib/br_nfe/servico/betha/v1/consulta_lote_rps.rb +3 -1
  13. data/lib/br_nfe/servico/betha/v1/consulta_nfs_por_rps.rb +5 -2
  14. data/lib/br_nfe/servico/betha/v1/consulta_nfse.rb +2 -1
  15. data/lib/br_nfe/servico/betha/v1/gateway.rb +66 -56
  16. data/lib/br_nfe/servico/betha/v1/recepcao_lote_rps.rb +16 -8
  17. data/lib/br_nfe/servico/betha/v2/build_response.rb +159 -0
  18. data/lib/br_nfe/servico/betha/v2/cancelamento_nfs.rb +8 -3
  19. data/lib/br_nfe/servico/betha/v2/consulta_lote_rps.rb +7 -4
  20. data/lib/br_nfe/servico/betha/v2/consulta_nfse_por_rps.rb +5 -5
  21. data/lib/br_nfe/servico/betha/v2/envio_lote_rps_sincrono.rb +7 -3
  22. data/lib/br_nfe/servico/betha/v2/gateway.rb +79 -56
  23. data/lib/br_nfe/servico/betha/v2/gera_nfse.rb +8 -3
  24. data/lib/br_nfe/servico/betha/v2/recepcao_lote_rps.rb +9 -4
  25. data/lib/br_nfe/servico/betha/v2/substituicao_nfse.rb +8 -4
  26. data/lib/br_nfe/servico/response/nota_fiscal.rb +13 -4
  27. data/lib/br_nfe/servico/rps.rb +2 -2
  28. data/lib/br_nfe/version.rb +1 -1
  29. data/lib/br_nfe.rb +2 -1
  30. data/test/br_nfe/base_test.rb +55 -1
  31. data/test/br_nfe/destinatario_test.rb +19 -0
  32. data/test/br_nfe/emitente_test.rb +20 -0
  33. data/test/br_nfe/endereco_test.rb +9 -0
  34. data/test/br_nfe/helper/cpf_cnpj_test.rb +61 -0
  35. data/test/br_nfe/servico/base_test.rb +28 -0
  36. data/test/br_nfe/servico/betha/base_test.rb +61 -32
  37. data/test/br_nfe/servico/betha/v1/build_response_test.rb +6 -7
  38. data/test/br_nfe/servico/betha/v1/cancelamento_nfs_test.rb +6 -0
  39. data/test/br_nfe/servico/betha/v1/consulta_lote_rps_test.rb +4 -0
  40. data/test/br_nfe/servico/betha/v1/consulta_nfse_test.rb +17 -0
  41. data/test/br_nfe/servico/betha/v1/gateway_test.rb +17 -40
  42. data/test/br_nfe/servico/betha/v1/recepcao_lote_rps_test.rb +12 -2
  43. data/test/br_nfe/servico/betha/v2/cancelamento_nfs_test.rb +40 -0
  44. data/test/br_nfe/servico/betha/v2/consulta_lote_rps_test.rb +38 -0
  45. data/test/br_nfe/servico/betha/v2/consulta_nfse_por_rps_test.rb +36 -0
  46. data/test/br_nfe/servico/betha/v2/envio_lote_rps_sincrono_test.rb +46 -0
  47. data/test/br_nfe/servico/betha/v2/gateway_test.rb +372 -0
  48. data/test/br_nfe/servico/betha/v2/gera_nfse_test.rb +58 -0
  49. data/test/br_nfe/servico/betha/v2/recepcao_lote_rps_test.rb +103 -0
  50. data/test/br_nfe/servico/betha/v2/substituicao_nfse_test.rb +80 -0
  51. data/test/br_nfe/servico/intermediario_test.rb +16 -0
  52. data/test/br_nfe/servico/rps_test.rb +141 -0
  53. data/test/factories/servico/betha/v1/gateway.rb +1 -1
  54. data/test/factories/servico/betha/v2/cancelamento_nfs.rb +7 -0
  55. data/test/factories/servico/betha/v2/consulta_lote_rps.rb +6 -0
  56. data/test/factories/servico/betha/v2/consulta_nfse_por_rps.rb +6 -0
  57. data/test/factories/servico/betha/v2/envio_lote_rps_sincrono.rb +5 -0
  58. data/test/factories/servico/betha/v2/gateway.rb +5 -0
  59. data/test/factories/servico/betha/v2/gera_nfse.rb +6 -0
  60. data/test/factories/servico/betha/v2/recepcao_lote_rps.rb +5 -0
  61. data/test/factories/servico/betha/v2/substituicao_nfse.rb +8 -0
  62. metadata +50 -17
  63. data/Gemfile +0 -15
  64. data/Rakefile +0 -13
  65. data/lib/br_nfe/seed.rb +0 -195
  66. data/lib/br_nfe/servico/betha/v2/response.rb +0 -23
  67. data/test/certificado.rb +0 -12
  68. data/test/test_helper.rb +0 -39
@@ -31,7 +31,13 @@ module BrNfe
31
31
 
32
32
  def set_response(resp)
33
33
  method_response = (method_wsdl.to_s + "_response").to_sym
34
- @response = BrNfe::Servico::Betha::V2::Response.new(xml: resp.hash[:envelope][:body][method_response][:return], nfe_method: method_wsdl)
34
+ @builder = BrNfe::Servico::Betha::V2::BuildResponse.new(xml: resp.hash[:envelope][:body][method_response][:return], nfe_method: method_wsdl)
35
+ @original_response = @builder.messages
36
+ @response = @builder.response
37
+ end
38
+
39
+ def builder
40
+ @builder
35
41
  end
36
42
 
37
43
  def cabecalho
@@ -49,10 +55,14 @@ module BrNfe
49
55
  def content_xml
50
56
  Nokogiri::XML::Builder.new do
51
57
  nfseDadosMsg do
52
- cdata(xml_builder)
58
+ cdata(canonical_xml_builder)
53
59
  end
54
60
  end.doc.root.to_s
55
61
  end
62
+
63
+ def canonical_xml_builder
64
+ canonicalize xml_builder.doc.root
65
+ end
56
66
 
57
67
  private
58
68
 
@@ -64,88 +74,101 @@ module BrNfe
64
74
  canonicalize xml.to_s
65
75
  end
66
76
 
67
- def tag_intermediario_servico(xml, intermediario)
68
- return unless intermediario
69
- xml.Intermediario{
70
- xml.IdentificacaoIntermediario{
71
- xml.CpfCnpj{
72
- tag_cpf_cnpj(xml, intermediario.cpf_cnpj)
77
+ def xml_intermediario_servico(intermediario)
78
+ return Nokogiri::XML::Builder.new unless intermediario
79
+ Nokogiri::XML::Builder.new(:encoding => 'UTF-8') do |xml|
80
+ xml.Intermediario{
81
+ xml.IdentificacaoIntermediario{
82
+ xml.CpfCnpj{
83
+ tag_cpf_cnpj(xml, intermediario.cpf_cnpj)
84
+ }
85
+ xml.InscricaoMunicipal "#{intermediario.inscricao_municipal}".max_size(15) unless intermediario.inscricao_municipal.blank?
73
86
  }
74
- xml.InscricaoMunicipal "#{intermediario.inscricao_municipal}".max_size(15) unless intermediario.inscricao_municipal.blank?
87
+ xml.RazaoSocial "#{intermediario.razao_social}".max_size(150)
75
88
  }
76
- xml.RazaoSocial "#{intermediario.razao_social}".max_size(150)
77
- }
89
+ end
78
90
  end
79
91
 
80
- def tag_prestador(xml)
81
- xml.Prestador{
82
- xml.CpfCnpj{
83
- tag_cpf_cnpj(xml, emitente.cnpj)
84
- }
85
- xml.InscricaoMunicipal "#{emitente.inscricao_municipal}".max_size(15) if !emitente.inscricao_municipal.blank? && env == :production
86
- }
87
- end
88
-
89
- def tag_dados_servico(xml, rps)
90
- xml.Servico {
91
- xml.Valores {
92
- xml.ValorServicos value_monetary(rps.valor_servicos, 2)
93
- xml.ValorDeducoes value_monetary(rps.valor_deducoes, 2) unless rps.valor_deducoes.blank?
94
- xml.ValorPis value_monetary(rps.valor_pis, 2) unless rps.valor_pis.blank?
95
- xml.ValorCofins value_monetary(rps.valor_cofins, 2) unless rps.valor_cofins.blank?
96
- xml.ValorInss value_monetary(rps.valor_inss, 2) unless rps.valor_inss.blank?
97
- xml.ValorIr value_monetary(rps.valor_ir, 2) unless rps.valor_ir.blank?
98
- xml.ValorCsll value_monetary(rps.valor_csll, 2) unless rps.valor_csll.blank?
99
- xml.OutrasRetencoes value_monetary(rps.outras_retencoes, 2) unless rps.outras_retencoes.blank?
100
- xml.ValorIss value_monetary(rps.valor_iss, 2) unless rps.valor_iss.blank?
101
- xml.Aliquota value_monetary(rps.aliquota, 2) unless rps.aliquota.blank?
102
- xml.DescontoIncondicionado value_monetary(rps.desconto_incondicionado, 2) unless rps.desconto_incondicionado.blank?
103
- xml.DescontoCondicionado value_monetary(rps.desconto_condicionado, 2) unless rps.desconto_condicionado.blank?
92
+ def xml_prestador
93
+ Nokogiri::XML::Builder.new(:encoding => 'UTF-8') do |xml|
94
+ xml.Prestador{
95
+ xml.CpfCnpj{
96
+ tag_cpf_cnpj(xml, emitente.cnpj)
97
+ }
98
+ xml.InscricaoMunicipal "#{emitente.inscricao_municipal}".max_size(15) if !emitente.inscricao_municipal.blank? && env == :production
104
99
  }
100
+ end
101
+ end
105
102
 
106
- xml.IssRetido value_true_false(rps.iss_retido?)
107
- xml.ResponsavelRetencao "#{rps.responsavel_retencao}".max_size(1) unless rps.responsavel_retencao.blank?
108
- xml.ItemListaServico BrNfe::Helper.only_number(rps.item_lista_servico).rjust(4,'0').max_size(5)
109
- xml.CodigoCnae BrNfe::Helper.only_number(rps.codigo_cnae).max_size(7) unless rps.codigo_cnae.blank?
110
- xml.CodigoTributacaoMunicipio "#{rps.codigo_tributacao_municipio}".max_size(20) unless rps.codigo_tributacao_municipio.blank?
111
- xml.Discriminacao "#{rps.discriminacao}".max_size(2_000).remove_accents
112
- xml.CodigoMunicipio "#{rps.codigo_municipio}".max_size(7)
113
- # Não posso enviar o CodigoPais se a exigibilidade_iss não for 4 (exportação) - by bethagambis.com
114
- xml.CodigoPais rps.codigo_pais.max_size(4) if !rps.codigo_pais.blank? && rps.exigibilidade_iss == '4'
115
- xml.ExigibilidadeISS "#{rps.exigibilidade_iss}".max_size(2)
116
- xml.MunicipioIncidencia rps.municipio_incidencia.max_size(4) unless rps.municipio_incidencia.blank?
117
- xml.NumeroProcesso rps.numero_processo.max_size(30) unless rps.numero_processo.blank?
118
- }
103
+ def xml_dados_servico(rps)
104
+ Nokogiri::XML::Builder.new(:encoding => 'UTF-8') do |xml|
105
+ xml.Servico {
106
+ xml.Valores {
107
+ xml.ValorServicos value_monetary(rps.valor_servicos, 2)
108
+ xml.ValorDeducoes value_monetary(rps.valor_deducoes, 2) unless rps.valor_deducoes.blank?
109
+ xml.ValorPis value_monetary(rps.valor_pis, 2) unless rps.valor_pis.blank?
110
+ xml.ValorCofins value_monetary(rps.valor_cofins, 2) unless rps.valor_cofins.blank?
111
+ xml.ValorInss value_monetary(rps.valor_inss, 2) unless rps.valor_inss.blank?
112
+ xml.ValorIr value_monetary(rps.valor_ir, 2) unless rps.valor_ir.blank?
113
+ xml.ValorCsll value_monetary(rps.valor_csll, 2) unless rps.valor_csll.blank?
114
+ xml.OutrasRetencoes value_monetary(rps.outras_retencoes, 2) unless rps.outras_retencoes.blank?
115
+ xml.ValorIss value_monetary(rps.valor_iss, 2) unless rps.valor_iss.blank?
116
+ xml.Aliquota value_monetary(rps.aliquota, 2) unless rps.aliquota.blank?
117
+ xml.DescontoIncondicionado value_monetary(rps.desconto_incondicionado, 2) unless rps.desconto_incondicionado.blank?
118
+ xml.DescontoCondicionado value_monetary(rps.desconto_condicionado, 2) unless rps.desconto_condicionado.blank?
119
+ }
120
+
121
+ xml.IssRetido value_true_false(rps.iss_retido?)
122
+ xml.ResponsavelRetencao "#{rps.responsavel_retencao}".max_size(1) unless rps.responsavel_retencao.blank?
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?
125
+ xml.CodigoTributacaoMunicipio "#{rps.codigo_tributacao_municipio}".max_size(20) unless rps.codigo_tributacao_municipio.blank?
126
+ xml.Discriminacao "#{rps.discriminacao}".max_size(2_000).remove_accents
127
+ xml.CodigoMunicipio BrNfe::Helper.only_number(rps.codigo_municipio).max_size(7)
128
+ # Não posso enviar o CodigoPais se a exigibilidade_iss não for 4 (exportação) - by bethagambis.com
129
+ xml.CodigoPais BrNfe::Helper.only_number(rps.codigo_pais).max_size(4) if !rps.codigo_pais.blank? && rps.exigibilidade_iss == '4'
130
+ xml.ExigibilidadeISS "#{rps.exigibilidade_iss}".max_size(2)
131
+ xml.MunicipioIncidencia BrNfe::Helper.only_number(rps.municipio_incidencia).max_size(7) unless rps.municipio_incidencia.blank?
132
+ xml.NumeroProcesso rps.numero_processo.max_size(30) unless rps.numero_processo.blank?
133
+ }
134
+ end
119
135
  end
120
136
 
121
137
  def xml_inf_declaracao_prestacao_servico(rps)
122
138
  Nokogiri::XML::Builder.new(encoding: 'UTF-8') do |xml|
123
139
  xml.InfDeclaracaoPrestacaoServico('Id' => "rps#{rps.numero}") {
124
140
  xml.Rps {
125
- tag_identificacao_rps(xml, rps)
141
+ # Identificação RPS
142
+ xml.__send__ :insert, Nokogiri::XML::DocumentFragment.parse( xml_identificacao_rps(rps).doc.root.to_s )
126
143
 
127
144
  xml.DataEmissao value_date(rps.data_emissao)
128
145
  xml.Status "#{rps.status}".max_size(1)
129
146
 
130
- tag_rps_substituido(xml, rps)
147
+ # RPS subistituido
148
+ xml.__send__ :insert, Nokogiri::XML::DocumentFragment.parse( xml_rps_substituido(rps).doc.root.to_s )
131
149
  }
132
150
 
133
151
  # Dia, mês e ano da prestação do serviço
134
152
  # Quando houver RPS, a nota será gerada com base na <DataEmissao> do RPS, caso contrário utilizará a <Competencia>
135
153
  xml.Competencia value_date(rps.competencia)
136
154
 
137
- tag_dados_servico(xml, rps)
155
+ # Dados do(s) serviço(s)
156
+ xml.__send__ :insert, Nokogiri::XML::DocumentFragment.parse( xml_dados_servico(rps).doc.root.to_s )
138
157
 
139
- tag_prestador(xml)
158
+ # Pestador / Emitente
159
+ xml.__send__ :insert, Nokogiri::XML::DocumentFragment.parse( xml_prestador.doc.root.to_s )
140
160
 
141
- tag_dados_tomador(xml, rps.destinatario)
161
+ # Tomador / Destinatário
162
+ xml.__send__ :insert, Nokogiri::XML::DocumentFragment.parse( xml_dados_tomador(rps.destinatario).doc.root.to_s )
142
163
 
143
- tag_intermediario_servico(xml, rps.intermediario)
164
+ # Intermediario
165
+ xml.__send__ :insert, Nokogiri::XML::DocumentFragment.parse( xml_intermediario_servico(rps.intermediario).doc.root.to_s )
144
166
 
145
- tag_dados_construcao_civil(xml, rps)
167
+ # Dados Construção Civil
168
+ xml.__send__ :insert, Nokogiri::XML::DocumentFragment.parse( xml_dados_construcao_civil(rps).doc.root.to_s )
146
169
 
147
170
  # Código de identificação do regime especial de tributação: (1)Microempresa municipal, (2)Estimativa, (3)Sociedade de profissionais, (4)Cooperativa, (5)Microempresário Individual (MEI), (6)Microempresário e Empresa de Pequeno Porte (ME EPP) ,
148
- xml.RegimeEspecialTributacao emitente.regime_especial_tributacao.max_size(2) unless emitente.regime_especial_tributacao.blank?
171
+ xml.RegimeEspecialTributacao "#{emitente.regime_especial_tributacao}".max_size(2) unless emitente.regime_especial_tributacao.blank?
149
172
 
150
173
  xml.OptanteSimplesNacional value_true_false(emitente.optante_simples_nacional?) # (1)sim ----- (2)não
151
174
  xml.IncentivoFiscal value_true_false(emitente.incentivo_fiscal?) # (1)sim ----- (2)não
@@ -5,6 +5,12 @@ module BrNfe
5
5
  class GeraNfse < BrNfe::Servico::Betha::V2::Gateway
6
6
  include BrNfe::Helper::HaveRps
7
7
 
8
+ def certificado_obrigatorio?
9
+ true
10
+ end
11
+
12
+ validate :valida_rps_recepcao
13
+
8
14
  def method_wsdl
9
15
  :gerar_nfse
10
16
  end
@@ -14,10 +20,9 @@ module BrNfe
14
20
  xml.GerarNfseEnvio(xmlns: "http://www.betha.com.br/e-nota-contribuinte-ws") {
15
21
  xml.__send__ :insert, Nokogiri::XML::DocumentFragment.parse( xml_rps_assinado(rps).doc.root.to_s)
16
22
  }
17
- end.doc.root
18
-
19
- canonicalize xml
23
+ end
20
24
  end
25
+
21
26
  end
22
27
  end
23
28
  end
@@ -3,6 +3,14 @@ module BrNfe
3
3
  module Betha
4
4
  module V2
5
5
  class RecepcaoLoteRps < BrNfe::Servico::Betha::V2::Gateway
6
+
7
+ validate :validar_lote_rps
8
+ validates :numero_lote_rps, presence: true
9
+
10
+ def certificado_obrigatorio?
11
+ true
12
+ end
13
+
6
14
  def method_wsdl
7
15
  :recepcionar_lote_rps
8
16
  end
@@ -15,11 +23,8 @@ module BrNfe
15
23
  xml.__send__ :insert, Nokogiri::XML::DocumentFragment.parse( xml_lote_rps.to_s )
16
24
  xml.__send__ :insert, Nokogiri::XML::DocumentFragment.parse( assinatura_xml(xml_lote_rps.to_s, "#lote#{numero_lote_rps}") )
17
25
  }
18
- end.doc.root
19
-
20
- canonicalize xml
26
+ end
21
27
  end
22
-
23
28
 
24
29
  def lote_rps_xml
25
30
  xml = Nokogiri::XML::Builder.new(encoding: 'UTF-8') do |xml|
@@ -5,6 +5,13 @@ module BrNfe
5
5
  class SubstituicaoNfse < BrNfe::Servico::Betha::V2::Gateway
6
6
  include BrNfe::Helper::HaveRps
7
7
 
8
+ validate :valida_rps_recepcao
9
+ validates :numero_nfse, :codigo_cancelamento, presence: true
10
+
11
+ def certificado_obrigatorio?
12
+ true
13
+ end
14
+
8
15
  def method_wsdl
9
16
  :substituir_nfse
10
17
  end
@@ -16,12 +23,9 @@ module BrNfe
16
23
  xml.__send__ :insert, Nokogiri::XML::DocumentFragment.parse( xml_substituicao.to_s )
17
24
  xml.__send__ :insert, Nokogiri::XML::DocumentFragment.parse( assinatura_xml(xml_substituicao.to_s, "#substituicao") )
18
25
  }
19
- end.doc.root
20
-
21
- canonicalize xml
26
+ end
22
27
  end
23
28
 
24
-
25
29
  def xml_substituicao_nfse
26
30
  Nokogiri::XML::Builder.new do |xml|
27
31
  xml.SubstituicaoNfse(Id: "substituicao") {
@@ -17,9 +17,12 @@ module BrNfe
17
17
  attr_accessor :rps_serie
18
18
  attr_accessor :rps_tipo
19
19
  attr_accessor :rps_situacao
20
+ attr_accessor :rps_substituido_numero
21
+ attr_accessor :rps_substituido_serie
22
+ attr_accessor :rps_substituido_tipo
20
23
 
21
- attr_accessor :data_emissao_rps # Datetime
22
- attr_accessor :competencia #DateTime
24
+ attr_accessor :data_emissao_rps # Datetime
25
+ attr_accessor :competencia #DateTime
23
26
  attr_accessor :outras_informacoes
24
27
 
25
28
  # dados dos serviços
@@ -37,11 +40,17 @@ module BrNfe
37
40
  attr_accessor :valor_ir
38
41
  attr_accessor :valor_csll
39
42
  attr_accessor :iss_retido
43
+ attr_accessor :outras_retencoes
40
44
  attr_accessor :valor_iss
41
45
  attr_accessor :base_calculo
42
46
  attr_accessor :aliquota
43
- attr_accessor :desconto_condicionado
44
- attr_accessor :desconto_incondicionado
47
+ attr_accessor :valor_liquido # v2
48
+ attr_accessor :desconto_condicionado # v2
49
+ attr_accessor :desconto_incondicionado # v2
50
+
51
+ attr_accessor :responsavel_retencao
52
+ attr_accessor :numero_processo
53
+ attr_accessor :municipio_incidencia
45
54
 
46
55
  # Orgão gerador
47
56
  attr_accessor :orgao_gerador_municipio
@@ -89,13 +89,13 @@ module BrNfe
89
89
  def validar_intermediario
90
90
  return true unless intermediario
91
91
  if intermediario.invalid?
92
- intermediario.errors.full_messages.map{|msg| errors.add(:intermediario, msg) }
92
+ intermediario.errors.full_messages.map{|msg| errors.add(:base, "Intermediário: #{msg}") }
93
93
  end
94
94
  end
95
95
 
96
96
  def validar_destinatario
97
97
  if destinatario.invalid?
98
- destinatario.errors.full_messages.map{|msg| errors.add(:destinatario, msg) }
98
+ destinatario.errors.full_messages.map{|msg| errors.add(:base, "Destinatário: #{msg}") }
99
99
  end
100
100
  end
101
101
  end
@@ -2,7 +2,7 @@ module BrNfe
2
2
  module Version
3
3
  MAJOR = 1 #inclui alterações de API e pode quebrar compatibilidade com versões anteriores
4
4
  MINOR = 0 #inclui novas funcionalidades, sem quebrar APIs existentes
5
- PATCH = 0 #corrige bugs ou traz melhorias em implementações já existentes
5
+ PATCH = 1 #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
@@ -58,6 +58,7 @@ module BrNfe
58
58
  module Betha
59
59
  extend ActiveSupport::Autoload
60
60
  autoload :Base
61
+ autoload :BuildResponse
61
62
  module V1
62
63
  extend ActiveSupport::Autoload
63
64
  autoload :Gateway
@@ -72,7 +73,7 @@ module BrNfe
72
73
  module V2
73
74
  extend ActiveSupport::Autoload
74
75
  autoload :Gateway
75
- autoload :Response
76
+ autoload :BuildResponse
76
77
  autoload :CancelamentoNfs
77
78
  autoload :ConsultaNfsePorRps
78
79
  autoload :EnvioLoteRpsSincrono
@@ -10,6 +10,35 @@ describe BrNfe::Base do
10
10
  subject.stubs(:certificado).returns(certificado)
11
11
  end
12
12
 
13
+ describe "validations" do
14
+ context "obrigatoriedade do certificado" do
15
+ before { subject.unstub(:certificado) }
16
+ it "deve ser obrigatorio se certificado_obrigatorio? for true" do
17
+ subject.expects(:certificado_obrigatorio?).returns(true)
18
+ must validate_presence_of(:certificado)
19
+ end
20
+ 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
+ end
24
+ end
25
+ context "validação do emitente" do
26
+ it "se emitente for válido" do
27
+ emitente.stubs(:errors).returns(stub(full_messages: ["Erro rps"]))
28
+ emitente.expects(:invalid?).returns(false)
29
+ subject.valid?.must_equal true
30
+ subject.errors.full_messages.must_equal( [] )
31
+ end
32
+
33
+ it "se emitente for inválido" do
34
+ emitente.stubs(:errors).returns(stub(full_messages: ["Erro rps"]))
35
+ emitente.expects(:invalid?).returns(true)
36
+ subject.valid?.must_equal false
37
+ subject.errors.full_messages.must_equal( ["Emitente: Erro rps"] )
38
+ end
39
+ end
40
+ end
41
+
13
42
  describe "#emitente" do
14
43
  include BrNfeTest::HelperTest::HaveEmitenteTest
15
44
  end
@@ -24,6 +53,14 @@ describe BrNfe::Base do
24
53
  end
25
54
  end
26
55
 
56
+ describe "#wsdl_encoding" do
57
+ it { subject.wsdl_encoding.must_equal 'UTF-8' }
58
+ end
59
+
60
+ it "certificado_obrigatorio?" do
61
+ subject.certificado_obrigatorio?.must_equal false
62
+ end
63
+
27
64
  describe "#certificado_value" do
28
65
  it "se tiver algum valor setado deve retornar esse valor" do
29
66
  subject.certificado_value = "algum valor"
@@ -46,6 +83,16 @@ describe BrNfe::Base do
46
83
  end
47
84
  end
48
85
 
86
+ describe "#original_response" do
87
+ it "deve retornar o valor da variavel @original_response" do
88
+ subject.instance_variable_set(:@original_response, 'valor')
89
+ subject.original_response.must_equal 'valor'
90
+ end
91
+ it "valor default" do
92
+ subject.original_response.must_be_nil
93
+ end
94
+ end
95
+
49
96
  describe "#wsdl" do
50
97
  it "deve dar um erro por default" do
51
98
  assert_raises RuntimeError do
@@ -198,6 +245,8 @@ describe BrNfe::Base do
198
245
  end
199
246
 
200
247
  it "deve gerar o xml" do
248
+ certificado.stubs(:certificate).returns("-----BEGIN CERTIFICATE-----\nMCYwHAIBADAASDIHASDIASHDIAMAMGAQADAQAwAwYBAAMBAA==\n-----END CERTIFICATE-----\n")
249
+
201
250
  subject.stubs(:signed_info).with(xml, 'URI123').returns(xml_signed_info)
202
251
  subject.expects(:xml_signature_value).with('<Signature xmlns="http://www.w3.org/2000/09/xmldsig#"><Value>STUBADO</Value></Signature>').returns("KEYFORINFOSIGNED")
203
252
 
@@ -207,7 +256,7 @@ describe BrNfe::Base do
207
256
  assinatura.remove_namespaces!
208
257
  assinatura.xpath('Signature/Signature/Value').first.text.must_equal 'STUBADO'
209
258
  assinatura.xpath('Signature/SignatureValue').first.text.must_equal 'KEYFORINFOSIGNED'
210
- assinatura.xpath('Signature/KeyInfo/X509Data/X509Certificate').first.text.must_equal 'MCYwHAIBADADBgEAMAAwBB8AHwAwADAIMAMGAQADAQAwAwYBAAMBAA=='
259
+ assinatura.xpath('Signature/KeyInfo/X509Data/X509Certificate').first.text.must_equal 'MCYwHAIBADAASDIHASDIASHDIAMAMGAQADAQAwAwYBAAMBAA=='
211
260
  end
212
261
  end
213
262
 
@@ -225,8 +274,13 @@ describe BrNfe::Base do
225
274
  OpenSSL::PKCS12.expects(:new).never
226
275
  subject.certificado.must_equal certificado
227
276
  end
277
+ it "posso setar o certificado" do
278
+ subject.certificado = 'certificado 123'
279
+ subject.certificado.must_equal 'certificado 123'
280
+ end
228
281
  end
229
282
 
283
+
230
284
  describe "#client_wsdl" do
231
285
  before do
232
286
  # Stub metodos para configuração do client WSDL
@@ -4,6 +4,25 @@ require 'br_nfe/helper/have_address_test.rb'
4
4
  describe BrNfe::Destinatario do
5
5
  subject { FactoryGirl.build(:destinatario, endereco: endereco) }
6
6
  let(:endereco) { FactoryGirl.build(:endereco) }
7
+
8
+ describe "validations" do
9
+ it { must validate_presence_of(:cpf_cnpj) }
10
+ it { must validate_presence_of(:razao_social) }
11
+
12
+ describe "valida o endereco" do
13
+ it "deve ser inválido se endereco for invalido" do
14
+ subject.endereco.stubs(:valid?).returns(false)
15
+ subject.endereco.stubs(:errors).returns(stub(full_messages: ["Erro 1"] ))
16
+ subject.valid?.must_equal false
17
+ subject.errors.full_messages.include?("Endereço: Erro 1").must_equal true
18
+ end
19
+ it "deve ser válido se endereco for valido" do
20
+ subject.endereco.stubs(:valid?).returns(true)
21
+ subject.valid?.must_equal true
22
+ end
23
+ end
24
+ end
25
+
7
26
 
8
27
  describe "#endereco" do
9
28
  include BrNfeTest::HelperTest::HaveAddressTest
@@ -4,6 +4,26 @@ require 'br_nfe/helper/have_address_test.rb'
4
4
  describe BrNfe::Emitente do
5
5
  subject { FactoryGirl.build(:emitente, endereco: endereco) }
6
6
  let(:endereco) { FactoryGirl.build(:endereco) }
7
+
8
+ describe "validations" do
9
+ it { must validate_presence_of(:inscricao_municipal) }
10
+ it { must validate_presence_of(:natureza_operacao) }
11
+ it { must validate_presence_of(:cnpj) }
12
+ it { must validate_presence_of(:razao_social) }
13
+
14
+ describe "valida o endereco" do
15
+ it "deve ser inválido se endereco for invalido" do
16
+ subject.endereco.stubs(:valid?).returns(false)
17
+ subject.endereco.stubs(:errors).returns(stub(full_messages: ["Erro 1"] ))
18
+ subject.valid?.must_equal false
19
+ subject.errors.full_messages.include?("Endereço: Erro 1").must_equal true
20
+ end
21
+ it "deve ser válido se endereco for valido" do
22
+ subject.endereco.stubs(:valid?).returns(true)
23
+ subject.valid?.must_equal true
24
+ end
25
+ end
26
+ end
7
27
 
8
28
  describe "#endereco" do
9
29
  include BrNfeTest::HelperTest::HaveAddressTest
@@ -2,6 +2,15 @@ require 'test_helper'
2
2
 
3
3
  describe BrNfe::Endereco do
4
4
  subject { FactoryGirl.build(:endereco) }
5
+
6
+ describe "validations" do
7
+ it { must validate_presence_of(:logradouro) }
8
+ it { must validate_presence_of(:numero) }
9
+ it { must validate_presence_of(:bairro) }
10
+ it { must validate_presence_of(:codigo_municipio) }
11
+ it { must validate_presence_of(:uf) }
12
+ it { must validate_presence_of(:cep) }
13
+ end
5
14
 
6
15
  describe "#default_values" do
7
16
  it "for codigo_pais must equal to 1058 " do
@@ -0,0 +1,61 @@
1
+ require 'test_helper'
2
+
3
+ describe BrNfe::Helper::CpfCnpj do
4
+ describe "when is a cnpj" do
5
+ subject { BrNfe::Helper::CpfCnpj.new('64.147.776/0001-11') }
6
+
7
+ it "#cpf?" do
8
+ subject.cpf?.must_equal false
9
+ end
10
+
11
+ it "#cnpj?" do
12
+ subject.cnpj?.must_equal true
13
+ end
14
+
15
+ it "#cpf_ou_cnpj?" do
16
+ subject.cpf_ou_cnpj?.must_equal :cnpj
17
+ end
18
+
19
+ it "#sem_formatacao" do
20
+ subject.sem_formatacao.must_equal '64147776000111'
21
+ end
22
+
23
+ it "#com_formatacao" do
24
+ objeto = BrNfe::Helper::CpfCnpj.new('64147776000111')
25
+ subject.com_formatacao.must_equal '64.147.776/0001-11'
26
+ end
27
+
28
+ it "#formatado_com_label" do
29
+ subject.formatado_com_label.must_equal 'CNPJ 64.147.776/0001-11'
30
+ end
31
+
32
+ end
33
+ describe "when is a cpf" do
34
+ subject { BrNfe::Helper::CpfCnpj.new('845.076.668-05') }
35
+
36
+ it "#cpf?" do
37
+ subject.cpf?.must_equal true
38
+ end
39
+
40
+ it "#cnpj?" do
41
+ subject.cnpj?.must_equal false
42
+ end
43
+
44
+ it "#cpf_ou_cnpj?" do
45
+ subject.cpf_ou_cnpj?.must_equal :cpf
46
+ end
47
+
48
+ it "#sem_formatacao" do
49
+ subject.sem_formatacao.must_equal '84507666805'
50
+ end
51
+
52
+ it "#com_formatacao" do
53
+ objeto = BrNfe::Helper::CpfCnpj.new('84507666805')
54
+ subject.com_formatacao.must_equal '845.076.668-05'
55
+ end
56
+
57
+ it "#formatado_com_label" do
58
+ subject.formatado_com_label.must_equal 'CPF 845.076.668-05'
59
+ end
60
+ end
61
+ end
@@ -2,6 +2,7 @@ require 'test_helper'
2
2
 
3
3
  describe BrNfe::Servico::Base do
4
4
  subject { FactoryGirl.build(:br_nfe_servico_base) }
5
+ let(:rps) { FactoryGirl.build(:br_nfe_rps) }
5
6
 
6
7
  describe "#lote_rps" do
7
8
  it "deve inicializar como um vetor vazio" do
@@ -18,6 +19,33 @@ describe BrNfe::Servico::Base do
18
19
  subject.lote_rps = {valor: '2'}
19
20
  subject.lote_rps.must_equal [{valor: '2'}]
20
21
  end
22
+ end
21
23
 
24
+ describe "#validar_lote_rps" do
25
+ it "se não houver nenhum rps, deve add um erro" do
26
+ subject.lote_rps = []
27
+ subject.errors.full_messages.must_equal( [] )
28
+ subject.send(:validar_lote_rps)
29
+ subject.errors.full_messages.must_equal( ["Deve conter ao menos 1 RPS"] )
30
+ end
31
+ context "deve validar o rps setando a opcao validar_recepcao_rps" do
32
+ before { subject.lote_rps = [rps] }
33
+ it "quando o rps for válido não deve setar nenhuma mensagem no objeto" do
34
+ rps.stubs(:errors).returns(stub(full_messages: ["Erro rps"]))
35
+ sequence_1 = sequence('sequence_1')
36
+ rps.expects(:validar_recepcao_rps=).with(true).in_sequence(sequence_1)
37
+ rps.expects(:invalid?).returns(false).in_sequence(sequence_1)
38
+ subject.send(:validar_lote_rps)
39
+ subject.errors.full_messages.must_equal( [] )
40
+ end
41
+ it "quando o rps for inválido deve setar mensagem de erro no objeto" do
42
+ rps.stubs(:errors).returns(stub(full_messages: ["Erro rps"]))
43
+ sequence_1 = sequence('sequence_1')
44
+ rps.expects(:validar_recepcao_rps=).with(true).in_sequence(sequence_1)
45
+ rps.expects(:invalid?).returns(true).in_sequence(sequence_1)
46
+ subject.send(:validar_lote_rps)
47
+ subject.errors.full_messages.must_equal( ["RPS 1: Erro rps"] )
48
+ end
49
+ end
22
50
  end
23
51
  end