Skip to content

feat: add Latvia tax regime - #879

Open
patricia-drt wants to merge 7 commits into
invopop:mainfrom
patricia-drt:feat/lv-tax-regime
Open

feat: add Latvia tax regime#879
patricia-drt wants to merge 7 commits into
invopop:mainfrom
patricia-drt:feat/lv-tax-regime

Conversation

@patricia-drt

Copy link
Copy Markdown

Summary

Introduced new tax regime for Latvia (LV) with VAT category support, including the standard, intermediate and reduced rates with comprehensive tax identity validation for both legal entities and individuals.

What's included

regimes/lv — regime definition.

  • VAT categories and rates:

    • Standard rate (21%) – applied to most goods and services. History anchored at 2013-01-01.
    • Intermediate rate (12%) – first reduced rate applied to essential goods and services (medicines, food supplies, etc.). History anchored at 2013-01-01.
    • Reduced rate (5%) – second reduced rate applied to books, press, and media publications. History anchored at 2018-01-01.

    Note: Latvia does not currently have a super-reduced VAT rate (< 5% as per EU directive).

  • VAT identity validation: Complete Latvian VAT/tax identity code validation:

    • 11-digit format (LV prefix optional, normalized away)
    • Legal entities (codes starting with 4-9): MOD-11 checksum validation using official weights
    • Legacy personal codes (DDMMYYCXXXX format): Date validation including leap year handling, century digit support (0=18xx, 1=19xx, 2=20xx)
    • Modern personal codes (starting with 3X, post-July 2017): Second digit validation (2-9 range)
    • Normalization strips LV prefix, removes hyphens, and yields clean numeric codes
  • Corrections: Credit notes and debit notes both recognized in Latvian VAT practice, following GOBL's default correction handling.

  • Scenarios: Reverse charge scenario for B2B intra-community supplies with automatic tax extension.

examples/lv — three invoice examples with golden outputs:

  1. invoice-standard.json — standard B2B invoice with 21% VAT
  2. invoice-reduced.json — multi-rate invoice with 5% and 12% VAT rates
  3. invoice-intermediate.json — B2C invoice with 12% VAT (food/medicines)

Generated data: data/regimes/lv.json, data/rules/lv.json, and regime-code schema via go generate.

Scope decisions

Decision Reasoning
No addon Latvia has no domestic B2B e-invoicing mandate; B2G uses Peppol/EN 16931, already covered by the existing eu-en16931-v2017 addon. A lv-* addon would be speculative at this point (pending ViDA implementation).
No withholding taxes No Latvian VAT-specific withholding mechanisms at the invoice level.
No OSS/IOSS handling EU-level machinery for one-stop-shop, handled at a higher level than single-invoice logic.
No VAT-group handling Registration arrangements are invisible at the single-invoice level.
No supplier tax ID requirement rule Unlike some EU countries, Latvia does not mandate VAT registration below the threshold. The regime provides validation when a tax ID is present, but does not enforce it.
Rate history anchored at 2013-01-01 This represents when Latvia joined the Eurozone. Earlier rates (pre-2013 at 22%) are documented but not included; happy to extend if primary sources confirm exact effective dates.

Sources

Pre-Review Checklist

  • Opened this PR as a draft
  • Read the CONTRIBUTING.md guide.
  • Performed a self-review of my code.
  • Added thorough tests with at least 90% code coverage.
  • Modified or created example GOBL documents to show my changes in use, if appropriate.
  • Added links to the source of the changes in tax regimes or addons, either structured or in the comments.
  • Run go generate . to ensure that the Schemas and Regime data are up to date.
  • Reviewed and fixed all linter warnings.
  • Been obsessive with pointer nil checks to avoid panics.
  • Updated the CHANGELOG.md with an overview of my changes.
  • Marked this PR as ready for review.

And if you are part of the org:

  • Requested a review from Copilot and fixed or dismissed (with a reason) all the feedback raised.
  • Requested a review from @samlown.

@patricia-drt
patricia-drt marked this pull request as ready for review June 28, 2026 18:39
@codecov

codecov Bot commented Jun 30, 2026

Copy link
Copy Markdown

Codecov Report

❌ Patch coverage is 86.72566% with 15 lines in your changes missing coverage. Please review.
✅ Project coverage is 94.71%. Comparing base (225e39d) to head (3b5f200).
⚠️ Report is 1 commits behind head on main.

Files with missing lines Patch % Lines
regimes/lv/tax_identity.go 80.76% 9 Missing and 6 partials ⚠️
Additional details and impacted files
@@            Coverage Diff             @@
##             main     #879      +/-   ##
==========================================
- Coverage   94.75%   94.71%   -0.05%     
==========================================
  Files         343      345       +2     
  Lines       18815    18928     +113     
==========================================
+ Hits        17829    17927      +98     
- Misses        600      609       +9     
- Partials      386      392       +6     

☔ View full report in Codecov by Harness.
📢 Have feedback on the report? Share it here.

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.
  • 📦 JS Bundle Analysis: Save yourself from yourself by tracking and limiting bundle sizes in JS merges.

@samlown samlown added the regime Related to a specific regime. label Jul 6, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

regime Related to a specific regime.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants