teodoro 0.0.7 → 0.0.12

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.
Files changed (35) hide show
  1. checksums.yaml +4 -4
  2. data/bin/teodoro +1 -1
  3. data/lib/teodoro.rb +68 -1
  4. data/lib/teodoro/arquivo_de_evento.rb +15 -27
  5. data/lib/teodoro/arquivo_de_evento_de_tabela.rb +1 -11
  6. data/lib/teodoro/arquivo_de_evento_exceto_de_exclusao.rb +25 -0
  7. data/lib/teodoro/arquivo_de_evento_nao_periodico.rb +10 -15
  8. data/lib/teodoro/arquivo_de_origem.rb +1 -1
  9. data/lib/teodoro/arquivo_xml.rb +71 -55
  10. data/lib/teodoro/console.rb +2 -6
  11. data/lib/teodoro/empresa.rb +48 -15
  12. data/lib/teodoro/leiaute.rb +24 -0
  13. data/lib/teodoro/{leiaute_2_4_1 → leiaute}/arquivo_s1000.rb +1 -1
  14. data/lib/teodoro/{leiaute_2_4_1 → leiaute}/arquivo_s1005.rb +1 -1
  15. data/lib/teodoro/{leiaute_2_4_1 → leiaute}/arquivo_s1010.rb +7 -3
  16. data/lib/teodoro/{leiaute_2_4_1 → leiaute}/arquivo_s1020.rb +1 -1
  17. data/lib/teodoro/{leiaute_2_4_1 → leiaute}/arquivo_s1030.rb +1 -1
  18. data/lib/teodoro/{leiaute_2_4_1 → leiaute}/arquivo_s1040.rb +1 -1
  19. data/lib/teodoro/{leiaute_2_4_1 → leiaute}/arquivo_s1050.rb +1 -1
  20. data/lib/teodoro/{leiaute_2_4_1 → leiaute}/arquivo_s1070.rb +1 -1
  21. data/lib/teodoro/{leiaute_2_4_1 → leiaute}/arquivo_s2190.rb +1 -1
  22. data/lib/teodoro/{leiaute_2_4_1 → leiaute}/arquivo_s2200.rb +46 -9
  23. data/lib/teodoro/{leiaute_2_4_1 → leiaute}/arquivo_s2205.rb +2 -2
  24. data/lib/teodoro/{leiaute_2_4_1 → leiaute}/arquivo_s2206.rb +1 -1
  25. data/lib/teodoro/{leiaute_2_4_1 → leiaute}/arquivo_s2230.rb +1 -1
  26. data/lib/teodoro/{leiaute_2_4_1 → leiaute}/arquivo_s2250.rb +2 -2
  27. data/lib/teodoro/leiaute/arquivo_s2299.rb +310 -0
  28. data/lib/teodoro/{leiaute_2_4_1 → leiaute}/arquivo_s2300.rb +20 -2
  29. data/lib/teodoro/{leiaute_2_4_1 → leiaute}/arquivo_s2306.rb +1 -1
  30. data/lib/teodoro/leiaute/arquivo_s2399.rb +303 -0
  31. data/lib/teodoro/leiaute/arquivo_s3000.rb +41 -0
  32. data/lib/teodoro/obj.rb +5 -0
  33. metadata +24 -20
  34. data/lib/teodoro/execucao.rb +0 -73
  35. data/lib/teodoro/leiaute_2_4_1.rb +0 -21
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: b847466dec2ee0dfa4debb804d5af16dd183dcceeeb28664d0adea46b3f4ec95
4
- data.tar.gz: 4c7aacf5cfdaf9af17298538947fb59cdfa82fd069d1136f06300cde54d3f463
3
+ metadata.gz: bb82ca01d0e6d8a70fb3c77d09e5d89a03e473fa632f4382221cdffefb21feed
4
+ data.tar.gz: 7bc8f92129a1828c5c4fa4cd7fcc5f3e87ed6c21c524f334959c26e782fc8e26
5
5
  SHA512:
6
- metadata.gz: 2dc6d426102161726682f79f701f2b481bf14c9a65f4838663d808c31cdf804a1fd651bc4f3116cc8a82ba7efec16405e8d336ea4ae484e26b2e8c651cbfdbf9
7
- data.tar.gz: 07ce6e6d6f2e57a3358dd77d6a218c28e09b92f8abe1420924dd79d4c22fe62cfb1695cd4b0b9630d7e6bbca9fab27caee932258bc6fc8dbba6b44f7dedff23e
6
+ metadata.gz: dce1dc08d6027a38f86f3ed22b0f4876bb95a977637ccd2f18daee65087dd1c8bfacfec9a970809c9ede277fd72ba8eefba2aa8356067e89a48800608dad5a21
7
+ data.tar.gz: f363698c4d43d83faea482d15e3ccd0299d1396c93c3ea214c8285c467514f2273400c182bae85425d90ee3c01cc3537f3c4c874dbc8423c44921f35f8933b20
data/bin/teodoro CHANGED
@@ -1,3 +1,3 @@
1
1
  #!/usr/bin/env ruby
2
2
  require 'teodoro'
3
- Teodoro::Execucao.new(ARGV).call
3
+ Teodoro.call(ARGV)
data/lib/teodoro.rb CHANGED
@@ -2,7 +2,74 @@ require 'nokogiri'
2
2
  require 'os'
3
3
  require 'zip'
4
4
 
5
- require_relative 'teodoro/execucao'
5
+ require_relative 'teodoro/console'
6
+ require_relative 'teodoro/empresa'
7
+ require_relative 'teodoro/obj'
6
8
 
7
9
  module Teodoro
10
+ def self.call(args)
11
+ Execution.new(args).call
12
+ end
13
+
14
+ class Execution
15
+ NOME_DO_PROGRAMA = 'teodoro'.freeze
16
+
17
+ private
18
+
19
+ def initialize(args)
20
+ @args = args
21
+ end
22
+
23
+ attr_reader :args
24
+
25
+ public
26
+
27
+ def call
28
+ validar_argumentos
29
+ validar_existencia_do_diretorio_de_origem
30
+ validar_que_diretorio_de_origem_nao_esta_vazio
31
+ validar_que_diretorio_de_destino_esta_vazio
32
+
33
+ processar_empresas
34
+ end
35
+
36
+ private
37
+
38
+ def validar_argumentos
39
+ erro "#{NOME_DO_PROGRAMA} [diretório de origem] [diretório de destino]" unless args.size == 2
40
+ end
41
+
42
+ def validar_existencia_do_diretorio_de_origem
43
+ erro 'Diretório de origem não existe.' unless File.directory?(origem)
44
+ end
45
+
46
+ def origem
47
+ @origem ||= args[0]
48
+ end
49
+
50
+ def validar_que_diretorio_de_origem_nao_esta_vazio
51
+ erro 'Diretório de origem vazio.' if Dir.empty?(origem)
52
+ end
53
+
54
+ def validar_que_diretorio_de_destino_esta_vazio
55
+ erro 'Diretório de destino deve estar vazio.' unless Dir.empty?(destino)
56
+ end
57
+
58
+ def destino
59
+ @destino ||= args[1]
60
+ end
61
+
62
+ def erro(erro)
63
+ puts erro
64
+ exit
65
+ end
66
+
67
+ def processar_empresas
68
+ empresas.each(&:processar)
69
+ end
70
+
71
+ def empresas
72
+ Dir[File.join(origem, '*')].map { |caminho| Empresa.new(caminho: caminho, destino: destino) }
73
+ end
74
+ end
8
75
  end
@@ -2,48 +2,36 @@ module Teodoro
2
2
  module ArquivoDeEvento
3
3
  private
4
4
 
5
- attr_reader :xml_do_evento, :xml_do_recibo, :destino_dos_arquivos_data
5
+ def initialize(empresa:, versao_do_leiaute:, evento:, recibo:)
6
+ @empresa = empresa
7
+ @versao_do_leiaute = versao_do_leiaute
8
+ @evento = evento
9
+ @recibo = recibo
10
+ end
6
11
 
7
- def criar_arquivo_data
8
- raise if File.exist?(caminho_do_arquivo_data)
12
+ attr_reader :empresa, :versao_do_leiaute, :evento, :recibo
9
13
 
10
- File.write(caminho_do_arquivo_data, conteudo_do_arquivo_data)
14
+ def leiaute_simplificado?
15
+ versao_do_leiaute.start_with?('_S_')
11
16
  end
12
17
 
13
- def caminho_do_arquivo_data
14
- criar_caminho_do_arquivo_data(nome_do_arquivo_data)
18
+ def processo_de_emissao_do_evento
19
+ evento["#{noh_principal_do_evento}/ideEvento/procEmi"]
15
20
  end
16
21
 
17
22
  def criar_caminho_do_arquivo_data(nome_do_arquivo)
18
- # FIXME: Tales demais caracteres especiais
19
23
  File.join(
20
24
  destino_dos_arquivos_data,
21
25
  "#{windows? ? nome_do_arquivo.gsub(%r{[<|>:"/\\?*]}, '_') : nome_do_arquivo}.data"
22
26
  )
23
27
  end
24
28
 
25
- def windows?
26
- OS.windows?
27
- end
28
-
29
- def evento
30
- @evento ||= XML.new(xml_do_evento)
31
- end
32
-
33
- def conteudo_do_arquivo_data
34
- (itens_do_conteudo_do_arquivo_data.map { "#{_1}=#{_2}" } + ['']).join("\n")
29
+ def destino_dos_arquivos_data
30
+ empresa.destino_dos_arquivos_data
35
31
  end
36
32
 
37
- def versao_do_aplicativo_de_processamento_do_evento
38
- recibo['retornoEvento/processamento/versaoAppProcessamento']
39
- end
40
-
41
- def tipo_de_inscricao_do_empregador
42
- @tipo_de_inscricao_do_empregador ||= evento["#{noh_principal_do_evento}/ideEmpregador/tpInsc"]
43
- end
44
-
45
- def recibo
46
- @recibo ||= XML.new(xml_do_recibo)
33
+ def windows?
34
+ OS.windows?
47
35
  end
48
36
  end
49
37
  end
@@ -1,16 +1,6 @@
1
1
  module Teodoro
2
2
  module ArquivoDeEventoDeTabela
3
- include ArquivoDeEvento
4
-
5
- private
6
-
7
- def initialize(xml_do_evento:, xml_do_recibo:, destino_dos_arquivos_data:)
8
- @xml_do_evento = xml_do_evento
9
- @xml_do_recibo = xml_do_recibo
10
- @destino_dos_arquivos_data = destino_dos_arquivos_data
11
- end
12
-
13
- public
3
+ include ArquivoDeEventoExcetoDeExclusao
14
4
 
15
5
  def processar
16
6
  deletar_arquivo_data_original if alteracao? || exclusao?
@@ -0,0 +1,25 @@
1
+ module Teodoro
2
+ module ArquivoDeEventoExcetoDeExclusao
3
+ include ArquivoDeEvento
4
+
5
+ private
6
+
7
+ def criar_arquivo_data
8
+ raise caminho_do_arquivo_data if File.exist?(caminho_do_arquivo_data)
9
+
10
+ File.write(caminho_do_arquivo_data, conteudo_do_arquivo_data)
11
+ end
12
+
13
+ def conteudo_do_arquivo_data
14
+ (itens_do_conteudo_do_arquivo_data.map { "#{_1}=#{_2}" } + ['']).join("\n")
15
+ end
16
+
17
+ def versao_do_aplicativo_de_processamento_do_evento
18
+ recibo['retornoEvento/processamento/versaoAppProcessamento']
19
+ end
20
+
21
+ def tipo_de_inscricao_do_empregador
22
+ @tipo_de_inscricao_do_empregador ||= evento["#{noh_principal_do_evento}/ideEmpregador/tpInsc"]
23
+ end
24
+ end
25
+ end
@@ -1,19 +1,6 @@
1
1
  module Teodoro
2
2
  module ArquivoDeEventoNaoPeriodico
3
- include ArquivoDeEvento
4
-
5
- private
6
-
7
- def initialize(xml_do_evento:, xml_do_recibo:, destino_dos_arquivos_data:, de_recibo_para_nome_do_arquivo_data:)
8
- @xml_do_evento = xml_do_evento
9
- @xml_do_recibo = xml_do_recibo
10
- @destino_dos_arquivos_data = destino_dos_arquivos_data
11
- @de_recibo_para_nome_do_arquivo_data = de_recibo_para_nome_do_arquivo_data
12
- end
13
-
14
- attr_reader :de_recibo_para_nome_do_arquivo_data
15
-
16
- public
3
+ include ArquivoDeEventoExcetoDeExclusao
17
4
 
18
5
  def processar
19
6
  deletar_arquivo_data_original if retificacao?
@@ -39,8 +26,12 @@ module Teodoro
39
26
  de_recibo_para_nome_do_arquivo_data[numero_do_recibo_a_retificar]
40
27
  end
41
28
 
29
+ def de_recibo_para_nome_do_arquivo_data
30
+ empresa.de_recibo_para_nome_do_arquivo_data
31
+ end
32
+
42
33
  def numero_do_recibo_a_retificar
43
- @numero_do_recibo_a_retificar ||= evento["#{noh_principal_do_evento}/ideEvento/nrRecibo"]
34
+ evento["#{noh_principal_do_evento}/ideEvento/nrRecibo"]
44
35
  end
45
36
 
46
37
  def registrar_recibo
@@ -50,5 +41,9 @@ module Teodoro
50
41
  def numero_do_recibo
51
42
  recibo['retornoEvento/recibo/nrRecibo']
52
43
  end
44
+
45
+ def caminho_do_arquivo_data
46
+ criar_caminho_do_arquivo_data(nome_do_arquivo_data)
47
+ end
53
48
  end
54
49
  end
@@ -14,7 +14,7 @@ module Teodoro
14
14
  public
15
15
 
16
16
  def descompactar
17
- puts File.basename(caminho)
17
+ Console.print "descompactando #{File.basename(caminho)}..."
18
18
 
19
19
  Zip::File.open(caminho) do |zip|
20
20
  zip
@@ -1,112 +1,128 @@
1
1
  require_relative 'arquivo_de_evento'
2
+ require_relative 'arquivo_de_evento_exceto_de_exclusao'
2
3
  require_relative 'arquivo_de_evento_de_tabela'
3
4
  require_relative 'arquivo_de_evento_nao_periodico'
4
5
  require_relative 'cnpj'
5
- require_relative 'leiaute_2_4_1'
6
+ require_relative 'leiaute'
6
7
  require_relative 'xml'
7
8
 
8
9
  module Teodoro
9
10
  class ArquivoXML
11
+ TIPOS_DE_EVENTO_PROCESSAVEIS = %w[
12
+ S1000
13
+ S1005
14
+ S1010
15
+ S1020
16
+ S1030
17
+ S1040
18
+ S1050
19
+ S1070
20
+ S2190
21
+ S2200
22
+ S2205
23
+ S2206
24
+ S2230
25
+ S2250
26
+ S2299
27
+ S2300
28
+ S2306
29
+ S2399
30
+ S3000
31
+ ].freeze
32
+
10
33
  private
11
34
 
12
- def initialize(caminho:, destino_dos_arquivos_data:, de_recibo_para_nome_do_arquivo_data:)
35
+ def initialize(empresa:, caminho:)
36
+ @empresa = empresa
13
37
  @caminho = caminho
14
- @destino_dos_arquivos_data = destino_dos_arquivos_data
15
- @de_recibo_para_nome_do_arquivo_data = de_recibo_para_nome_do_arquivo_data
16
38
  end
17
39
 
18
- attr_reader :caminho, :destino_dos_arquivos_data, :de_recibo_para_nome_do_arquivo_data
40
+ attr_reader :empresa, :caminho
19
41
 
20
42
  public
21
43
 
44
+ def processavel?
45
+ TIPOS_DE_EVENTO_PROCESSAVEIS.include?(tipo_de_evento)
46
+ end
47
+
48
+ def momento_de_processamento_pelo_e_social
49
+ # otimizacao do gerenciamento de memoria
50
+ carregar_xml
51
+ .then { |xml| Nokogiri::XML(xml.css('eSocial/retornoProcessamentoDownload/recibo/*').to_s) }
52
+ .then { |xml_do_recibo| XML.new(xml_do_recibo) }
53
+ .then { |recibo| recibo['retornoEvento/processamento/dhProcessamento'] }
54
+ end
55
+
22
56
  def nome
23
57
  @nome ||= File.basename(caminho, '.xml')
24
58
  end
25
59
 
26
60
  def processar
27
- return unless %w[S1000 S1005 S1010 S1020 S1030 S1040 S1050 S1070 S2190 S2200 S2205 S2206 S2230 S2250 S2300 S2306]
28
- .include?(tipo_de_evento)
29
-
30
- arquivo.processar
61
+ dar_feedback_para_o_usuario
62
+ validar_versao_do_leiaute
63
+ processar_arquivo
31
64
  end
32
65
 
33
66
  private
34
67
 
35
68
  def tipo_de_evento
36
- nome[-6..].delete('-')
69
+ @tipo_de_evento ||= nome[-6..].delete('-')
37
70
  end
38
71
 
39
- def arquivo
40
- if evento_de_tabela?
41
- evento_de_tabela
42
- elsif evento_nao_periodico?
43
- evento_nao_periodico
44
- end
72
+ def carregar_xml
73
+ Nokogiri::XML(carregar_conteudo)
45
74
  end
46
75
 
47
- def evento_de_tabela?
48
- tipo_de_evento.start_with?('S10')
76
+ def carregar_conteudo
77
+ File.read(caminho)
49
78
  end
50
79
 
51
- def evento_de_tabela
52
- classe_do_arquivo.new(
53
- xml_do_evento: xml_do_evento,
54
- xml_do_recibo: xml_do_recibo,
55
- destino_dos_arquivos_data: destino_dos_arquivos_data
56
- )
80
+ def dar_feedback_para_o_usuario
81
+ Console.print "processando #{nome}.xml..."
57
82
  end
58
83
 
59
- def evento_nao_periodico?
60
- tipo_de_evento.start_with?('S2')
84
+ def validar_versao_do_leiaute
85
+ raise unless %w[02_04_01 02_04_02 02_05_00 _S_01_00_00].include?(versao_do_leiaute)
61
86
  end
62
87
 
63
- def evento_nao_periodico
64
- classe_do_arquivo.new(
65
- xml_do_evento: xml_do_evento,
66
- xml_do_recibo: xml_do_recibo,
67
- destino_dos_arquivos_data: destino_dos_arquivos_data,
68
- de_recibo_para_nome_do_arquivo_data: de_recibo_para_nome_do_arquivo_data
69
- )
88
+ def versao_do_leiaute
89
+ @versao_do_leiaute ||= namespace_do_evento.match(%r{.+/v(.+)$})[1]
70
90
  end
71
91
 
72
- def classe_do_arquivo
73
- modulo_do_leiaute.const_get("Arquivo#{tipo_de_evento}")
92
+ def namespace_do_evento
93
+ xml_do_evento.css('eSocial')[0].namespace.href
94
+ end
95
+
96
+ def xml_do_evento
97
+ @xml_do_evento ||= Nokogiri::XML(xml.css('eSocial/retornoProcessamentoDownload/evento/*').to_s)
74
98
  end
75
99
 
76
- def modulo_do_leiaute
77
- {
78
- '02_04_01' => Leiaute_2_4_1,
79
- '02_04_02' => Leiaute_2_4_1, # FIXME: Tales
80
- '02_05_00' => Leiaute_2_4_1, # FIXME: Tales
81
- '01_00_00' => Leiaute_2_4_1 # FIXME: Tales
82
- }[versao_do_leiaute_no_xml]
100
+ def xml
101
+ @xml ||= carregar_xml
83
102
  end
84
103
 
85
- def versao_do_leiaute_no_xml
86
- namespace_do_evento.match(%r{.+/v(.+)$})[1]
104
+ def processar_arquivo
105
+ arquivo.processar
87
106
  end
88
107
 
89
- def namespace_do_evento
90
- xml_do_evento.css('eSocial')[0].namespace.href
108
+ def arquivo
109
+ classe_do_arquivo.new(empresa: empresa, versao_do_leiaute: versao_do_leiaute, evento: evento, recibo: recibo)
91
110
  end
92
111
 
93
- def xml_do_evento
94
- @xml_do_evento ||= Nokogiri::XML(xml.css('eSocial/retornoProcessamentoDownload/evento/*').to_s)
112
+ def classe_do_arquivo
113
+ Leiaute.const_get("Arquivo#{tipo_de_evento}")
95
114
  end
96
115
 
97
- def xml
98
- @xml ||= Nokogiri::XML(conteudo)
116
+ def evento
117
+ XML.new(xml_do_evento)
99
118
  end
100
119
 
101
- def conteudo
102
- File.read(caminho)
120
+ def recibo
121
+ @recibo ||= XML.new(xml_do_recibo)
103
122
  end
104
123
 
105
124
  def xml_do_recibo
106
125
  Nokogiri::XML(xml.css('eSocial/retornoProcessamentoDownload/recibo/*').to_s)
107
126
  end
108
-
109
- module Base
110
- end
111
127
  end
112
128
  end
@@ -1,9 +1,5 @@
1
1
  module Console
2
- class << self
3
- def print(*strings, color: nil)
4
- color_codes = { green: 32, red: 31 }
5
- strings = strings.map { |string| "\e[#{color_codes[color]}m#{string}\e[0m" } if color
6
- puts strings
7
- end
2
+ def self.print(string = nil)
3
+ Kernel.print "\r\e[2K#{string}"
8
4
  end
9
5
  end