Skip to content

Commit 36b46ff

Browse files
committed
add support for LineItem#service_period_start / service_period_end
1 parent 186306b commit 36b46ff

File tree

2 files changed

+98
-0
lines changed

2 files changed

+98
-0
lines changed

lib/secretariat/line_item.rb

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,8 @@ module Secretariat
3232
:charge_amount,
3333
:origin_country_code,
3434
:currency_code,
35+
:service_period_start, # if start present start & end are required
36+
:service_period_end, # end has to be on or after start (secretariat does not validate this)
3537
keyword_init: true
3638
) do
3739

@@ -181,6 +183,22 @@ def to_xml(xml, line_item_index, version: 2, validate: true)
181183
xml['ram'].send(percent,Helpers.format(tax_percent))
182184
end
183185
end
186+
187+
if version == 2 && self.service_period_start && self.service_period_end
188+
xml['ram'].BillingSpecifiedPeriod do
189+
xml['ram'].StartDateTime do
190+
xml['udt'].DateTimeString(format: '102') do
191+
xml.text(service_period_start.strftime("%Y%m%d"))
192+
end
193+
end
194+
xml['ram'].EndDateTime do
195+
xml['udt'].DateTimeString(format: '102') do
196+
xml.text(service_period_end.strftime("%Y%m%d"))
197+
end
198+
end
199+
end
200+
end
201+
184202
monetary_summation = by_version(version, 'SpecifiedTradeSettlementMonetarySummation', 'SpecifiedTradeSettlementLineMonetarySummation')
185203
xml['ram'].send(monetary_summation) do
186204
Helpers.currency_element(xml, 'ram', 'LineTotalAmount', (quantity.negative? ? -charge_amount : charge_amount), currency_code, add_currency: version == 1)

test/invoice_test.rb

Lines changed: 80 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -57,6 +57,61 @@ def make_eu_invoice(tax_category: :REVERSECHARGE)
5757
)
5858
end
5959

60+
def make_eu_invoice_with_line_item_billing_period(tax_category: :REVERSECHARGE)
61+
seller = TradeParty.new(
62+
name: 'Depfu inc',
63+
street1: 'Quickbornstr. 46',
64+
city: 'Hamburg',
65+
postal_code: '20253',
66+
country_id: 'DE',
67+
vat_id: 'DE304755032'
68+
)
69+
buyer = TradeParty.new(
70+
name: 'Depfu inc',
71+
street1: 'Quickbornstr. 46',
72+
city: 'Hamburg',
73+
postal_code: '20253',
74+
country_id: 'SE',
75+
vat_id: 'SE304755032'
76+
)
77+
line_item = LineItem.new(
78+
name: 'Depfu Premium Plan',
79+
quantity: 1,
80+
gross_amount: BigDecimal('29'),
81+
net_amount: BigDecimal('29'),
82+
unit: :PIECE,
83+
charge_amount: BigDecimal('29'),
84+
tax_category: tax_category,
85+
tax_percent: 0,
86+
tax_amount: 0,
87+
origin_country_code: 'DE',
88+
currency_code: 'EUR',
89+
service_period_start: Date.today,
90+
service_period_end: Date.today + 30,
91+
)
92+
Invoice.new(
93+
id: '12345',
94+
issue_date: Date.today,
95+
# service_period on line_item. removed here to simplify testing of BillingSpecifiedPeriod presence
96+
# service_period_start: Date.today,
97+
# service_period_end: Date.today + 30,
98+
seller: seller,
99+
buyer: buyer,
100+
line_items: [line_item],
101+
currency_code: 'USD',
102+
payment_type: :CREDITCARD,
103+
payment_text: 'Kreditkarte',
104+
tax_category: tax_category,
105+
tax_amount: 0,
106+
basis_amount: BigDecimal('29'),
107+
grand_total_amount: BigDecimal('29'),
108+
due_amount: 0,
109+
paid_amount: 29,
110+
payment_due_date: Date.today + 14,
111+
notes: "This is a test invoice",
112+
)
113+
end
114+
60115
def make_foreign_invoice(tax_category: :TAXEXEMPT)
61116
seller = TradeParty.new(
62117
name: 'Depfu inc',
@@ -381,6 +436,31 @@ def test_simple_eu_invoice_v2
381436
puts e.errors
382437
end
383438

439+
def test_simple_eu_invoice_v2_with_line_item_billing_period
440+
begin
441+
xml = make_eu_invoice_with_line_item_billing_period.to_xml(version: 2)
442+
rescue ValidationError => e
443+
pp e.errors
444+
end
445+
446+
assert_match(/<ram:CategoryCode>AE<\/ram:CategoryCode>/, xml)
447+
assert_match(/<ram:ExemptionReason>Reverse Charge<\/ram:ExemptionReason>/, xml)
448+
assert_match(/<ram:RateApplicablePercent>/, xml)
449+
assert_match(/<ram:BillingSpecifiedPeriod>/, xml)
450+
451+
v = Validator.new(xml, version: 2)
452+
errors = v.validate_against_schema
453+
if !errors.empty?
454+
puts xml
455+
errors.each do |error|
456+
puts error
457+
end
458+
end
459+
assert_equal [], errors
460+
rescue ValidationError => e
461+
puts e.errors
462+
end
463+
384464
def test_simple_foreign_invoice_v2_taxexpempt
385465
begin
386466
xml = make_foreign_invoice(tax_category: :TAXEXEMPT).to_xml(version: 2)

0 commit comments

Comments
 (0)