cfdi40 0.4.1 → 0.4.3
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 +4 -4
- data/Gemfile.lock +1 -1
- data/lib/cfdi40/complemento.rb +18 -0
- data/lib/cfdi40/comprobante.rb +12 -0
- data/lib/cfdi40/docto_relacionado.rb +10 -0
- data/lib/cfdi40/impuestos_dr.rb +11 -0
- data/lib/cfdi40/node.rb +0 -2
- data/lib/cfdi40/pago.rb +17 -7
- data/lib/cfdi40/pagos.rb +46 -3
- data/lib/cfdi40/traslados_dr.rb +7 -0
- data/lib/cfdi40/version.rb +1 -1
- data/lib/cfdi40/xml_loader.rb +8 -0
- metadata +2 -2
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: 463e9e9afbe82401d3664da4e110e8c3be599db170884715b0b2a43762aad5b8
|
|
4
|
+
data.tar.gz: c688efebca0b62e00c85d0edc2d24be6d3b5add127aa8ee1f9217dd9234be17d
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: aac1fa7a86a1a8fcffe9b435b718f3ce665777da9a27f747e2a170d4d28b675b37e7e9656d2a522558926674dcaaafc08776448ad6652be5f3ab678d58d83d50
|
|
7
|
+
data.tar.gz: abedeb3fad410bd0e338b91279ceec3652b4dbf182acd884da53c8fdeee88e1259e698e798b3c264d430ea315dcfd8d184d13a02965494658350794cd191ddba
|
data/Gemfile.lock
CHANGED
data/lib/cfdi40/complemento.rb
CHANGED
|
@@ -8,6 +8,11 @@ module Cfdi40
|
|
|
8
8
|
pagos.add_pago(attributes)
|
|
9
9
|
end
|
|
10
10
|
|
|
11
|
+
def add_splitted_pago(attributes = {})
|
|
12
|
+
pagos.totales_node
|
|
13
|
+
pagos.add_splitted_pago(attributes)
|
|
14
|
+
end
|
|
15
|
+
|
|
11
16
|
def pago_nodes
|
|
12
17
|
return [] unless defined?(@pagos)
|
|
13
18
|
|
|
@@ -23,6 +28,19 @@ module Cfdi40
|
|
|
23
28
|
@pagos
|
|
24
29
|
end
|
|
25
30
|
|
|
31
|
+
def load_pagos(pagos_node)
|
|
32
|
+
@pagos = Cfdi40::Pagos.new
|
|
33
|
+
@pagos.load_from_ng_node(pagos_node)
|
|
34
|
+
@pagos.parent_node = self
|
|
35
|
+
pagos_node.xpath("//pago20:Pago", Cfdi40::Pagos::NG_NAMESPACE).each do |pago_node|
|
|
36
|
+
@pagos.load_pago(pago_node)
|
|
37
|
+
end
|
|
38
|
+
totales_node = pagos_node.xpath("//pago20:Totales", Cfdi40::Pagos::NG_NAMESPACE).first
|
|
39
|
+
@pagos.load_totales(totales_node) unless totales_node.nil?
|
|
40
|
+
@children_nodes << @pagos
|
|
41
|
+
@pagos
|
|
42
|
+
end
|
|
43
|
+
|
|
26
44
|
def timbre
|
|
27
45
|
@children_nodes.select { |children| children.is_a?(Cfdi40::Timbre) }.first
|
|
28
46
|
end
|
data/lib/cfdi40/comprobante.rb
CHANGED
|
@@ -198,6 +198,14 @@ module Cfdi40
|
|
|
198
198
|
complemento.pagos.remove_pago(index.to_i)
|
|
199
199
|
end
|
|
200
200
|
|
|
201
|
+
# See test_adding_pago_with_n_docto_relacionados in file test/test_cfdi40_rep.rb
|
|
202
|
+
def add_splitted_pago(attributes = {})
|
|
203
|
+
raise Error, "CFDi debe ser tipo 'P'" unless tipo_de_comprobante == "P"
|
|
204
|
+
|
|
205
|
+
add_node_concepto_actividad_pago
|
|
206
|
+
complemento.add_splitted_pago(attributes)
|
|
207
|
+
end
|
|
208
|
+
|
|
201
209
|
def to_s
|
|
202
210
|
to_xml
|
|
203
211
|
end
|
|
@@ -282,6 +290,10 @@ module Cfdi40
|
|
|
282
290
|
timbre
|
|
283
291
|
end
|
|
284
292
|
|
|
293
|
+
def load_pagos(pagos_node)
|
|
294
|
+
complemento.load_pagos(pagos_node)
|
|
295
|
+
end
|
|
296
|
+
|
|
285
297
|
def timbre
|
|
286
298
|
return nil unless defined?(@complemento)
|
|
287
299
|
|
|
@@ -64,5 +64,15 @@ module Cfdi40
|
|
|
64
64
|
@children_nodes << @impuestos_dr
|
|
65
65
|
@impuestos_dr
|
|
66
66
|
end
|
|
67
|
+
|
|
68
|
+
def load_impuestos_dr(impuestos_dr_node)
|
|
69
|
+
@impuestos_dr = ImpuestosDR.new
|
|
70
|
+
@impuestos_dr.load_from_ng_node(impuestos_dr_node)
|
|
71
|
+
@impuestos_dr.parent_node = self
|
|
72
|
+
@children_nodes << @impuestos_dr
|
|
73
|
+
tr_dr_node = impuestos_dr_node.xpath("//pago20:TrasladosDR", Cfdi40::Pagos::NG_NAMESPACE).first
|
|
74
|
+
@impuestos_dr.load_traslados_dr(tr_dr_node) unless tr_dr_node.nil?
|
|
75
|
+
@impuestos_dr
|
|
76
|
+
end
|
|
67
77
|
end
|
|
68
78
|
end
|
data/lib/cfdi40/impuestos_dr.rb
CHANGED
|
@@ -10,5 +10,16 @@ module Cfdi40
|
|
|
10
10
|
@children_nodes << @traslados_dr
|
|
11
11
|
@traslados_dr
|
|
12
12
|
end
|
|
13
|
+
|
|
14
|
+
def load_traslados_dr(traslados_dr_node)
|
|
15
|
+
@traslados_dr = TrasladosDR.new
|
|
16
|
+
@traslados_dr.load_from_ng_node(traslados_dr_node)
|
|
17
|
+
@traslados_dr.parent_node = self
|
|
18
|
+
@children_nodes << @traslados_dr
|
|
19
|
+
traslados_dr_node.xpath("//pago20:TrasladoDR", Cfdi40::Pagos::NG_NAMESPACE).each do |tr_dr_node|
|
|
20
|
+
@traslados_dr.load_traslado_dr(tr_dr_node)
|
|
21
|
+
end
|
|
22
|
+
@traslados_dr
|
|
23
|
+
end
|
|
13
24
|
end
|
|
14
25
|
end
|
data/lib/cfdi40/node.rb
CHANGED
data/lib/cfdi40/pago.rb
CHANGED
|
@@ -14,15 +14,15 @@ module Cfdi40
|
|
|
14
14
|
# Generate docto_relacionado node
|
|
15
15
|
# Data for dcto_relacionado node is obtained from de accessors
|
|
16
16
|
# uuid, serie, folio
|
|
17
|
-
def add_docto_relacionado
|
|
17
|
+
def add_docto_relacionado(attributes = {})
|
|
18
18
|
docto_relacionado = DoctoRelacionado.new
|
|
19
19
|
docto_relacionado.parent_node = self
|
|
20
|
-
docto_relacionado.id_documento = uuid
|
|
21
|
-
docto_relacionado.serie = serie
|
|
22
|
-
docto_relacionado.folio = folio
|
|
23
|
-
docto_relacionado.num_parcialidad = num_parcialidad
|
|
24
|
-
docto_relacionado.imp_saldo_ant = importe_saldo_anterior.round(2)
|
|
25
|
-
docto_relacionado.imp_pagado =
|
|
20
|
+
docto_relacionado.id_documento = attributes[:uuid]
|
|
21
|
+
docto_relacionado.serie = attributes[:serie]
|
|
22
|
+
docto_relacionado.folio = attributes[:folio]
|
|
23
|
+
docto_relacionado.num_parcialidad = attributes[:num_parcialidad]
|
|
24
|
+
docto_relacionado.imp_saldo_ant = attributes[:importe_saldo_anterior].round(2)
|
|
25
|
+
docto_relacionado.imp_pagado = attributes[:imp_pagado]
|
|
26
26
|
docto_relacionado.calculate!
|
|
27
27
|
@children_nodes << docto_relacionado
|
|
28
28
|
end
|
|
@@ -55,5 +55,15 @@ module Cfdi40
|
|
|
55
55
|
end
|
|
56
56
|
@summary = summary
|
|
57
57
|
end
|
|
58
|
+
|
|
59
|
+
def load_dr(dr_node)
|
|
60
|
+
dr = DoctoRelacionado.new
|
|
61
|
+
dr.load_from_ng_node(dr_node)
|
|
62
|
+
dr.parent_node = self
|
|
63
|
+
@children_nodes << dr
|
|
64
|
+
imp_dr_node = dr_node.xpath("//pago20:ImpuestosDR", Cfdi40::Pagos::NG_NAMESPACE).first
|
|
65
|
+
dr.load_impuestos_dr(imp_dr_node) unless imp_dr_node.nil?
|
|
66
|
+
dr
|
|
67
|
+
end
|
|
58
68
|
end
|
|
59
69
|
end
|
data/lib/cfdi40/pagos.rb
CHANGED
|
@@ -2,6 +2,7 @@
|
|
|
2
2
|
|
|
3
3
|
module Cfdi40
|
|
4
4
|
class Pagos < Node
|
|
5
|
+
NG_NAMESPACE = { "pago20" => "http://www.sat.gob.mx/Pagos20" }
|
|
5
6
|
define_namespace "pago20", "http://www.sat.gob.mx/Pagos20"
|
|
6
7
|
define_attribute :schema_location,
|
|
7
8
|
xml_attribute: "xsi:schemaLocation",
|
|
@@ -13,18 +14,41 @@ module Cfdi40
|
|
|
13
14
|
def add_pago(attributes = {})
|
|
14
15
|
pago = Pago.new
|
|
15
16
|
pago.parent_node = self
|
|
17
|
+
attributes_doc_rel = { imp_pagado: attributes[:monto] }
|
|
18
|
+
doc_rel_keys = [:uuid, :serie, :folio, :num_parcialidad, :importe_saldo_anterior, :objeto_impuestos]
|
|
19
|
+
attributes.each do |key, value|
|
|
20
|
+
if doc_rel_keys.include?(key)
|
|
21
|
+
attributes_doc_rel[key] = value
|
|
22
|
+
else
|
|
23
|
+
method_name = "#{key}=".to_sym
|
|
24
|
+
raise Error, ":#{key} no se puede asignar al nodo Pago" unless pago.respond_to?(method_name)
|
|
25
|
+
|
|
26
|
+
pago.public_send(method_name, value)
|
|
27
|
+
end
|
|
28
|
+
end
|
|
29
|
+
pago.monto = pago.monto.round(2)
|
|
30
|
+
pago.add_docto_relacionado(attributes_doc_rel)
|
|
31
|
+
pago.add_impuestos_p
|
|
32
|
+
@children_nodes << pago
|
|
33
|
+
update_totales
|
|
34
|
+
true
|
|
35
|
+
end
|
|
36
|
+
|
|
37
|
+
def add_splitted_pago(attributes = {})
|
|
38
|
+
pago = Pago.new
|
|
39
|
+
pago.parent_node = self
|
|
40
|
+
docs = attributes.delete(:docs)
|
|
16
41
|
attributes.each do |key, value|
|
|
17
42
|
method_name = "#{key}=".to_sym
|
|
18
43
|
raise Error, ":#{key} no se puede asignar al nodo Pago" unless pago.respond_to?(method_name)
|
|
19
44
|
|
|
20
45
|
pago.public_send(method_name, value)
|
|
21
46
|
end
|
|
22
|
-
|
|
23
|
-
pago.
|
|
47
|
+
docs.each { |doc_attributes| pago.add_docto_relacionado(doc_attributes) }
|
|
48
|
+
pago.monto = docs.map { |doc_attributes| doc_attributes[:imp_pagado].to_f }.sum.round(2)
|
|
24
49
|
pago.add_impuestos_p
|
|
25
50
|
@children_nodes << pago
|
|
26
51
|
update_totales
|
|
27
|
-
true
|
|
28
52
|
end
|
|
29
53
|
|
|
30
54
|
def remove_pago(index)
|
|
@@ -75,5 +99,24 @@ module Cfdi40
|
|
|
75
99
|
def pago_nodes
|
|
76
100
|
@children_nodes.select { |node| node.instance_of?(::Cfdi40::Pago) }
|
|
77
101
|
end
|
|
102
|
+
|
|
103
|
+
def load_pago(pago_node)
|
|
104
|
+
pago = Pago.new
|
|
105
|
+
pago.load_from_ng_node(pago_node)
|
|
106
|
+
pago.parent_node = self
|
|
107
|
+
@children_nodes << pago
|
|
108
|
+
pago_node.xpath("//pago20:DoctoRelacionado", { "pago20" => "http://www.sat.gob.mx/Pagos20" }).each do |dr_node|
|
|
109
|
+
pago.load_dr(dr_node)
|
|
110
|
+
end
|
|
111
|
+
pago
|
|
112
|
+
end
|
|
113
|
+
|
|
114
|
+
def load_totales(totales_node)
|
|
115
|
+
cp_totales = CpTotales.new
|
|
116
|
+
cp_totales.load_from_ng_node(totales_node)
|
|
117
|
+
cp_totales.parent_node = self
|
|
118
|
+
@children_nodes << cp_totales
|
|
119
|
+
cp_totales
|
|
120
|
+
end
|
|
78
121
|
end
|
|
79
122
|
end
|
data/lib/cfdi40/traslados_dr.rb
CHANGED
data/lib/cfdi40/version.rb
CHANGED
data/lib/cfdi40/xml_loader.rb
CHANGED
|
@@ -17,6 +17,7 @@ module Cfdi40
|
|
|
17
17
|
load_receptor
|
|
18
18
|
load_conceptos
|
|
19
19
|
load_impuestos
|
|
20
|
+
load_pagos
|
|
20
21
|
load_tfd
|
|
21
22
|
|
|
22
23
|
@cfdi.lock if readonly?
|
|
@@ -71,5 +72,12 @@ module Cfdi40
|
|
|
71
72
|
|
|
72
73
|
@cfdi.load_tfd(tfd_node)
|
|
73
74
|
end
|
|
75
|
+
|
|
76
|
+
def load_pagos
|
|
77
|
+
pagos_node = xml_doc.xpath("//pago20:Pagos", Cfdi40::Pagos::NG_NAMESPACE).first
|
|
78
|
+
return if pagos_node.nil?
|
|
79
|
+
|
|
80
|
+
@cfdi.load_pagos(pagos_node)
|
|
81
|
+
end
|
|
74
82
|
end
|
|
75
83
|
end
|
metadata
CHANGED
|
@@ -1,14 +1,14 @@
|
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: cfdi40
|
|
3
3
|
version: !ruby/object:Gem::Version
|
|
4
|
-
version: 0.4.
|
|
4
|
+
version: 0.4.3
|
|
5
5
|
platform: ruby
|
|
6
6
|
authors:
|
|
7
7
|
- Israel Benítez
|
|
8
8
|
autorequire:
|
|
9
9
|
bindir: exe
|
|
10
10
|
cert_chain: []
|
|
11
|
-
date: 2025-12-
|
|
11
|
+
date: 2025-12-05 00:00:00.000000000 Z
|
|
12
12
|
dependencies:
|
|
13
13
|
- !ruby/object:Gem::Dependency
|
|
14
14
|
name: nokogiri
|