Skip to content

Commit

Permalink
Merge pull request #26 from invopop/fix-missing-tax-totals
Browse files Browse the repository at this point in the history
Fix missing tax totals
  • Loading branch information
samlown authored Jan 29, 2025
2 parents 10c0f2b + ba2f376 commit b6eda17
Show file tree
Hide file tree
Showing 18 changed files with 116 additions and 48 deletions.
7 changes: 5 additions & 2 deletions doc/breakdown.go
Original file line number Diff line number Diff line change
Expand Up @@ -94,6 +94,9 @@ type taxInfo struct {
}

func newTipoDesglose(gobl *bill.Invoice) *TipoDesglose {
if gobl.Totals == nil || gobl.Totals.Taxes == nil {
return nil
}
catTotal := gobl.Totals.Taxes.Category(tax.CategoryVAT)
if catTotal == nil {
return nil
Expand Down Expand Up @@ -265,7 +268,7 @@ func (t taxInfo) isNoSujeta(r *tax.RateTotal) bool {
if t.customerRates {
return true
}
return r.Percent == nil && r.Ext[tbai.ExtKeyExemption].Code().In(notSubjectExemptionCodes...)
return r.Percent == nil && r.Ext[tbai.ExtKeyExemption].In(notSubjectExemptionCodes...)
}

func (t taxInfo) causaNoSujeta(r *tax.RateTotal) string {
Expand All @@ -276,5 +279,5 @@ func (t taxInfo) causaNoSujeta(r *tax.RateTotal) string {
}

func (taxInfo) isExenta(r *tax.RateTotal) bool {
return r.Percent == nil && !r.Ext[tbai.ExtKeyExemption].Code().In(notSubjectExemptionCodes...)
return r.Percent == nil && !r.Ext[tbai.ExtKeyExemption].In(notSubjectExemptionCodes...)
}
27 changes: 17 additions & 10 deletions doc/invoice.go
Original file line number Diff line number Diff line change
Expand Up @@ -3,8 +3,8 @@ package doc
import (
"github.com/invopop/gobl/addons/es/tbai"
"github.com/invopop/gobl/bill"
"github.com/invopop/gobl/cbc"
"github.com/invopop/gobl/num"
"github.com/invopop/gobl/org"
"github.com/invopop/gobl/regimes/es"
"github.com/invopop/gobl/tax"
)
Expand Down Expand Up @@ -109,22 +109,24 @@ func newDatosFactura(inv *bill.Invoice) (*DatosFactura, error) {
}, nil
}

func newDescription(notes []*cbc.Note) (string, error) {
func newDescription(notes []*org.Note) (string, error) {
for _, note := range notes {
if note.Key == cbc.NoteKeyGeneral {
if note.Key == org.NoteKeyGeneral {
return note.Text, nil
}
}
return "", validationErr(`notes: missing note with key '%s'`, cbc.NoteKeyGeneral)
return "", validationErr(`notes: missing note with key '%s'`, org.NoteKeyGeneral)
}

func newImporteTotal(inv *bill.Invoice) string {
totalWithDiscounts := inv.Totals.Total

totalTaxes := num.MakeAmount(0, 2)
for _, category := range inv.Totals.Taxes.Categories {
if !category.Retained {
totalTaxes = totalTaxes.Add(category.Amount)
if inv.Totals.Taxes != nil {
for _, category := range inv.Totals.Taxes.Categories {
if !category.Retained {
totalTaxes = totalTaxes.Add(category.Amount)
}
}
}

Expand All @@ -133,9 +135,11 @@ func newImporteTotal(inv *bill.Invoice) string {

func newRetencionSoportada(inv *bill.Invoice) string {
totalRetention := num.MakeAmount(0, 2)
for _, category := range inv.Totals.Taxes.Categories {
if category.Retained {
totalRetention = totalRetention.Add(category.Amount)
if inv.Totals.Taxes != nil {
for _, category := range inv.Totals.Taxes.Categories {
if category.Retained {
totalRetention = totalRetention.Add(category.Amount)
}
}
}

Expand Down Expand Up @@ -204,6 +208,9 @@ func newFacturasRectificadasSustituidas(inv *bill.Invoice) *FacturasRectificadas
}

func hasSurchargedLines(inv *bill.Invoice) bool {
if inv.Totals == nil || inv.Totals.Taxes == nil {
return false
}
vat := inv.Totals.Taxes.Category(tax.CategoryVAT)
if vat == nil {
return false
Expand Down
7 changes: 3 additions & 4 deletions doc/invoice_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,6 @@ import (
"github.com/invopop/gobl/addons/es/tbai"
"github.com/invopop/gobl/bill"
"github.com/invopop/gobl/cal"
"github.com/invopop/gobl/cbc"
"github.com/invopop/gobl/num"
"github.com/invopop/gobl/org"
"github.com/invopop/gobl/regimes/es"
Expand Down Expand Up @@ -67,8 +66,8 @@ func TestFacturaConversion(t *testing.T) {

t.Run("should fill invoice description from general note", func(t *testing.T) {
goblInvoice := test.LoadInvoice("sample-invoice.json")
goblInvoice.Notes = []*cbc.Note{
{Key: cbc.NoteKeyGeneral, Text: "Description of invoice"},
goblInvoice.Notes = []*org.Note{
{Key: org.NoteKeyGeneral, Text: "Description of invoice"},
}

invoice, _ := doc.NewTicketBAI(goblInvoice, ts, role, doc.ZoneBI)
Expand All @@ -79,7 +78,7 @@ func TestFacturaConversion(t *testing.T) {

t.Run("should return error if no description (general note) found", func(t *testing.T) {
goblInvoice := test.LoadInvoice("sample-invoice.json")
goblInvoice.Notes = []*cbc.Note{}
goblInvoice.Notes = []*org.Note{}

_, err := doc.NewTicketBAI(goblInvoice, ts, role, doc.ZoneBI)

Expand Down
2 changes: 1 addition & 1 deletion doc/parties.go
Original file line number Diff line number Diff line change
Expand Up @@ -75,7 +75,7 @@ func newDestinatario(party *org.Party) (*IDDestinatario, error) {
}

if len(party.Addresses) > 0 && party.Addresses[0].Code != "" {
d.CodigoPostal = party.Addresses[0].Code
d.CodigoPostal = party.Addresses[0].Code.String()
d.Direccion = formatAddress(party.Addresses[0])
}

Expand Down
5 changes: 4 additions & 1 deletion document.go
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,9 @@ func (c *Client) Convert(env *gobl.Envelope) (*doc.TicketBAI, error) {
if inv.Supplier.TaxID.Country != l10n.ES.Tax() {
return nil, ErrValidation.withMessage("only spanish invoices are supported")
}
if inv.Totals == nil || inv.Totals.Taxes == nil {
return nil, ErrValidation.withMessage("missing taxes")
}

zone := zoneFor(inv)
if zone == "" {
Expand All @@ -36,7 +39,7 @@ func (c *Client) Convert(env *gobl.Envelope) (*doc.TicketBAI, error) {
out, err := doc.NewTicketBAI(inv, c.CurrentTime(), c.issuerRole, zone)
if err != nil {
if _, ok := err.(*doc.ValidationError); ok {
return nil, ErrValidation.withMessage(err.Error())
return nil, ErrValidation.withMessage(err.Error()) //nolint:govet
}

return nil, err
Expand Down
2 changes: 1 addition & 1 deletion go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ toolchain go1.22.1

require (
github.com/go-resty/resty/v2 v2.13.1
github.com/invopop/gobl v0.204.2-0.20241105091334-a418e60fb2b5
github.com/invopop/gobl v0.208.0
github.com/invopop/xmldsig v0.10.0
github.com/joho/godotenv v1.5.1
github.com/lestrrat-go/libxml2 v0.0.0-20231124114421-99c71026c2f5
Expand Down
2 changes: 2 additions & 0 deletions go.sum
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,8 @@ github.com/inconshreveable/mousetrap v1.1.0 h1:wN+x4NVGpMsO7ErUn/mUI3vEoE6Jt13X2
github.com/inconshreveable/mousetrap v1.1.0/go.mod h1:vpF70FUmC8bwa3OWnCshd2FqLfsEA9PFc4w1p2J65bw=
github.com/invopop/gobl v0.204.2-0.20241105091334-a418e60fb2b5 h1:MLlwU4olYRx1FFa5pLur6PTTaXdaLfT7gscZ6DjkxTw=
github.com/invopop/gobl v0.204.2-0.20241105091334-a418e60fb2b5/go.mod h1:DmPohPel8b3ta4nDKnXRNzWQlB89cN74e0/WwPUEZUU=
github.com/invopop/gobl v0.208.0 h1:qy5GHXELMy7qBtvgLL8m4d/aBgBaxq0bdAaae4a2luE=
github.com/invopop/gobl v0.208.0/go.mod h1:DmPohPel8b3ta4nDKnXRNzWQlB89cN74e0/WwPUEZUU=
github.com/invopop/jsonschema v0.12.0 h1:6ovsNSuvn9wEQVOyc72aycBMVQFKz7cPdMJn10CvzRI=
github.com/invopop/jsonschema v0.12.0/go.mod h1:ffZ5Km5SWWRAIN6wbDXItl95euhFz2uON45H2qjYt+0=
github.com/invopop/validation v0.7.0 h1:NBPLqvYGmLZLQuk5jh0PbaBBetJW7f2VEk/BTWJkGBU=
Expand Down
12 changes: 9 additions & 3 deletions test/data/credit-note-es-es-tbai.json
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
"uuid": "0192237d-4943-72a7-b1d0-51dca3e8bc71",
"dig": {
"alg": "sha256",
"val": "f7165b79e26a6d53e163030b0312e80d15f8af189e0eb51d98864cb06c64e9fc"
"val": "c703a148a9395e3a14882d582618fe6503ab4719007715449c752eaf5cc22831"
}
},
"doc": {
Expand Down Expand Up @@ -86,7 +86,10 @@
"item": {
"name": "Development services",
"price": "90.00",
"unit": "h"
"unit": "h",
"ext": {
"es-tbai-product": "services"
}
},
"sum": "1800.00",
"discounts": [
Expand All @@ -110,7 +113,10 @@
"quantity": "1",
"item": {
"name": "Financial service",
"price": "10.00"
"price": "10.00",
"ext": {
"es-tbai-product": "services"
}
},
"sum": "10.00",
"discounts": [
Expand Down
17 changes: 13 additions & 4 deletions test/data/invoice-es-es-b2c.json
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
"uuid": "0192d3c7-2dc5-74cf-b263-5892feb44432",
"dig": {
"alg": "sha256",
"val": "58a808907be339175b8fa53ff5f326f1f074641cfbb653f7f1619763e1f4f2d7"
"val": "57cfc9eb9cc3c8b0013b7ad7ff6fc8b0320d9afbeda923eea05c463bd3cc16cd"
}
},
"doc": {
Expand Down Expand Up @@ -56,7 +56,10 @@
"item": {
"name": "Development services",
"price": "90.00",
"unit": "h"
"unit": "h",
"ext": {
"es-tbai-product": "services"
}
},
"sum": "1800.00",
"discounts": [
Expand All @@ -83,7 +86,10 @@
"quantity": "1",
"item": {
"name": "Some merch",
"price": "90.00"
"price": "90.00",
"ext": {
"es-tbai-product": "services"
}
},
"sum": "90.00",
"taxes": [
Expand All @@ -103,7 +109,10 @@
"quantity": "1",
"item": {
"name": "Some essential needs merch",
"price": "30.00"
"price": "30.00",
"ext": {
"es-tbai-product": "services"
}
},
"sum": "30.00",
"taxes": [
Expand Down
17 changes: 13 additions & 4 deletions test/data/invoice-es-nl-b2c.json
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
"uuid": "0192237d-4965-7c4b-914e-3a62f8e074e5",
"dig": {
"alg": "sha256",
"val": "0ab95209a3a9da3f9e4500a39cd9685f142ff86d42e3d143de14042fe6639749"
"val": "b796c7ee85d32112c3ce7690f4ba5498eaf196ab9df57ea3a2128fe90247b612"
}
},
"doc": {
Expand Down Expand Up @@ -68,7 +68,10 @@
"item": {
"name": "Development services",
"price": "90.00",
"unit": "h"
"unit": "h",
"ext": {
"es-tbai-product": "services"
}
},
"sum": "1800.00",
"discounts": [
Expand Down Expand Up @@ -96,7 +99,10 @@
"quantity": "1",
"item": {
"name": "Some merch",
"price": "90.00"
"price": "90.00",
"ext": {
"es-tbai-product": "services"
}
},
"sum": "90.00",
"taxes": [
Expand All @@ -117,7 +123,10 @@
"quantity": "1",
"item": {
"name": "Some essential needs merch",
"price": "30.00"
"price": "30.00",
"ext": {
"es-tbai-product": "services"
}
},
"sum": "30.00",
"taxes": [
Expand Down
7 changes: 5 additions & 2 deletions test/data/invoice-es-nl-tbai-b2c-explicit.json
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
"uuid": "0192237d-498e-7273-bc95-6a1daf16cb37",
"dig": {
"alg": "sha256",
"val": "bc1cc3c6887e628c94e42d011041522695a73005a3daf4b0f521b9a297e9e97f"
"val": "68b6594f9204664935f572e9fc537e84f680c86a4a325f61ddd646685ffcbde7"
}
},
"doc": {
Expand Down Expand Up @@ -65,7 +65,10 @@
"item": {
"name": "Development services",
"price": "90.00",
"unit": "h"
"unit": "h",
"ext": {
"es-tbai-product": "services"
}
},
"sum": "1800.00",
"discounts": [
Expand Down
7 changes: 5 additions & 2 deletions test/data/invoice-es-nl-tbai-exempt.json
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
"uuid": "0192237d-49c2-79a7-8249-4280119d8ade",
"dig": {
"alg": "sha256",
"val": "0294246ded2b071f8c6eb6011251f3bd254726613b5e7402abcbc2c91e96ecd1"
"val": "f9db4d04b45e555f37068e2d363c153d0a36e29bbdfd828452a78a92491babec"
}
},
"doc": {
Expand Down Expand Up @@ -60,7 +60,10 @@
"item": {
"name": "Development services",
"price": "90.00",
"unit": "h"
"unit": "h",
"ext": {
"es-tbai-product": "services"
}
},
"sum": "1800.00",
"discounts": [
Expand Down
7 changes: 5 additions & 2 deletions test/data/invoice-ss.json
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
"uuid": "0192fbbc-005b-7eea-8973-210ca4c0ffdc",
"dig": {
"alg": "sha256",
"val": "265465a226476105b9339754dd8e8856033fca217b8b6e89a984295de402b4b6"
"val": "38e8aef5c956bd0ca7ab99d559bdb13174a3f6af82feab70e1e7242bfe10abe7"
}
},
"doc": {
Expand Down Expand Up @@ -74,7 +74,10 @@
"quantity": "10",
"item": {
"name": "Item being purchased",
"price": "100.00"
"price": "100.00",
"ext": {
"es-tbai-product": "services"
}
},
"sum": "1000.00",
"discounts": [
Expand Down
7 changes: 5 additions & 2 deletions test/data/invoice-vi.json
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
"uuid": "0192fd51-6cd8-73f2-a182-8c4d3901d125",
"dig": {
"alg": "sha256",
"val": "a9fcef2ca22b63043a5c66137a39f8ad2be7db01c42ad94f4c5c80ee060c49b0"
"val": "6503a793d90d96cefdfd1652d219a43e44472eb5e8f741d43cf86cb8f984b2ec"
}
},
"doc": {
Expand Down Expand Up @@ -74,7 +74,10 @@
"quantity": "10",
"item": {
"name": "Item being purchased",
"price": "100.00"
"price": "100.00",
"ext": {
"es-tbai-product": "services"
}
},
"sum": "1000.00",
"discounts": [
Expand Down
Loading

0 comments on commit b6eda17

Please sign in to comment.