Skip to content

cef: validate VATEX codes by pattern - #860

Open
alvarolivie wants to merge 1 commit into
mainfrom
vatex-pattern-addon-lists
Open

cef: validate VATEX codes by pattern#860
alvarolivie wants to merge 1 commit into
mainfrom
vatex-pattern-addon-lists

Conversation

@alvarolivie

@alvarolivie alvarolivie commented Jun 12, 2026

Copy link
Copy Markdown
Contributor
  • data/catalogues/cef.json: the cef-vatex enumeration of the 75 official codes is replaced by "pattern": "^VATEX-[A-Z]{2}(-[A-Z0-9]+)+$", so that profile-specific codes such as the French VATEX-FR-CGI* ones are accepted. Schematrons own the allowed list per profile.
  • Tests: the pattern is checked against official, country and malformed codes in catalogues/cef, plus a case in the EN16931 addon for a country code passing validation.

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.

@codecov

codecov Bot commented Jun 12, 2026

Copy link
Copy Markdown

Codecov Report

✅ All modified and coverable lines are covered by tests.
✅ Project coverage is 94.87%. Comparing base (43ca367) to head (90135ae).

Additional details and impacted files
@@           Coverage Diff           @@
##             main     #860   +/-   ##
=======================================
  Coverage   94.87%   94.87%           
=======================================
  Files         320      320           
  Lines       17431    17431           
=======================================
  Hits        16537    16537           
  Misses        553      553           
  Partials      341      341           

☔ 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 marked this pull request as draft June 15, 2026 12:57
@alvarolivie
alvarolivie force-pushed the vatex-pattern-addon-lists branch from e266bf7 to a22ae44 Compare July 29, 2026 12:17
@alvarolivie
alvarolivie requested a review from Copilot July 29, 2026 15:01
@alvarolivie
alvarolivie marked this pull request as ready for review July 29, 2026 15:01
@alvarolivie alvarolivie changed the title cef: validate VATEX codes by pattern; EN16931 addon owns the code list cef: validate VATEX codes by pattern Jul 29, 2026
The cef-vatex catalogue hard-enumerated the official CEF VATEX codes,
which left no room for the country codes that profiles admit, such as
the 24 VATEX-FR-CGI* codes of the French CTC Extended profile.

The catalogue now enforces the code shape only, via the pattern
^VATEX-[A-Z]{2}(-[A-Z0-9]+)+$, which covers all 75 official codes.
Schematrons own the allowed list for each profile.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
@alvarolivie
alvarolivie force-pushed the vatex-pattern-addon-lists branch from a22ae44 to 90135ae Compare July 29, 2026 15:04
@alvarolivie
alvarolivie marked this pull request as draft July 29, 2026 15:05

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR relaxes validation of the CEF VATEX exemption reason code extension by replacing the fixed enumeration list with a regex pattern, allowing profile/country-specific VATEX codes to pass base validation while leaving stricter allow-lists to profile-specific rules.

Changes:

  • Replaced the cef-vatex catalogue enumeration with a pattern-based validation rule in data/catalogues/cef.json.
  • Added tests in catalogues/cef to verify the new VATEX regex accepts official and country-specific codes and rejects malformed inputs.
  • Added an EN16931 addon test to confirm a country-specific VATEX code passes validation in context.

Reviewed changes

Copilot reviewed 4 out of 4 changed files in this pull request and generated 1 comment.

File Description
data/catalogues/cef.json Switches cef-vatex from enumerated values to a regex pattern for validation.
catalogues/cef/cef_test.go Adds unit tests asserting the VATEX pattern matches valid codes and rejects invalid ones.
addons/eu/en16931/tax_combo_test.go Adds an addon-context test ensuring a country-specific VATEX code is accepted.

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment thread data/catalogues/cef.json
Comment on lines 13 to +16
"desc": {
"en": "Codes for the reasons for VAT exemption as defined by the Connecting Europe Facility (CEF)."
},
"values": [
{
"code": "VATEX-EU-79-C",
"name": {
"en": "Exempt based on article 79, point c of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-132",
"name": {
"en": "Exempt based on article 132 of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-132-1A",
"name": {
"en": "Exempt based on article 132, section 1 (a) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-132-1B",
"name": {
"en": "Exempt based on article 132, section 1 (b) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-132-1C",
"name": {
"en": "Exempt based on article 132, section 1 (c) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-132-1D",
"name": {
"en": "Exempt based on article 132, section 1 (d) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-132-1E",
"name": {
"en": "Exempt based on article 132, section 1 (e) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-132-1F",
"name": {
"en": "Exempt based on article 132, section 1 (f) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-132-1G",
"name": {
"en": "Exempt based on article 132, section 1 (g) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-132-1H",
"name": {
"en": "Exempt based on article 132, section 1 (h) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-132-1I",
"name": {
"en": "Exempt based on article 132, section 1 (i) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-132-1J",
"name": {
"en": "Exempt based on article 132, section 1 (j) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-132-1K",
"name": {
"en": "Exempt based on article 132, section 1 (k) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-132-1L",
"name": {
"en": "Exempt based on article 132, section 1 (l) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-132-1M",
"name": {
"en": "Exempt based on article 132, section 1 (m) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-132-1N",
"name": {
"en": "Exempt based on article 132, section 1 (n) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-132-1O",
"name": {
"en": "Exempt based on article 132, section 1 (o) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-132-1P",
"name": {
"en": "Exempt based on article 132, section 1 (p) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-132-1Q",
"name": {
"en": "Exempt based on article 132, section 1 (q) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-143",
"name": {
"en": "Exempt based on article 143 of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-143-1A",
"name": {
"en": "Exempt based on article 143, section 1 (a) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-143-1B",
"name": {
"en": "Exempt based on article 143, section 1 (b) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-143-1C",
"name": {
"en": "Exempt based on article 143, section 1 (c) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-143-1D",
"name": {
"en": "Exempt based on article 143, section 1 (d) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-143-1E",
"name": {
"en": "Exempt based on article 143, section 1 (e) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-143-1F",
"name": {
"en": "Exempt based on article 143, section 1 (f) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-143-1FA",
"name": {
"en": "Exempt based on article 143, section 1 (fa) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-143-1G",
"name": {
"en": "Exempt based on article 143, section 1 (g) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-143-1H",
"name": {
"en": "Exempt based on article 143, section 1 (h) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-143-1I",
"name": {
"en": "Exempt based on article 143, section 1 (i) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-143-1J",
"name": {
"en": "Exempt based on article 143, section 1 (j) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-143-1K",
"name": {
"en": "Exempt based on article 143, section 1 (k) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-143-1L",
"name": {
"en": "Exempt based on article 143, section 1 (l) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-148",
"name": {
"en": "Exempt based on article 148 of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-148-A",
"name": {
"en": "Exempt based on article 148, section (a) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-148-B",
"name": {
"en": "Exempt based on article 148, section (b) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-148-C",
"name": {
"en": "Exempt based on article 148, section (c) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-148-D",
"name": {
"en": "Exempt based on article 148, section (d) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-148-E",
"name": {
"en": "Exempt based on article 148, section (e) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-148-F",
"name": {
"en": "Exempt based on article 148, section (f) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-148-G",
"name": {
"en": "Exempt based on article 148, section (g) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-151",
"name": {
"en": "Exempt based on article 151 of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-151-1A",
"name": {
"en": "Exempt based on article 151, section 1 (a) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-151-1AA",
"name": {
"en": "Exempt based on article 151, section 1 (aa) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-151-1B",
"name": {
"en": "Exempt based on article 151, section 1 (b) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-151-1C",
"name": {
"en": "Exempt based on article 151, section 1 (c) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-151-1D",
"name": {
"en": "Exempt based on article 151, section 1 (d) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-151-1E",
"name": {
"en": "Exempt based on article 151, section 1 (e) of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-309",
"name": {
"en": "Exempt based on article 309 of Council Directive 2006/112/EC"
}
},
{
"code": "VATEX-EU-AE",
"name": {
"en": "Reverse charge"
}
},
{
"code": "VATEX-EU-D",
"name": {
"en": "Travel agents VAT scheme."
}
},
{
"code": "VATEX-EU-F",
"name": {
"en": "Second hand goods VAT scheme."
}
},
{
"code": "VATEX-EU-G",
"name": {
"en": "Export outside the EU"
}
},
{
"code": "VATEX-EU-I",
"name": {
"en": "Works of art VAT scheme."
}
},
{
"code": "VATEX-EU-IC",
"name": {
"en": "Intra-community supply"
}
},
{
"code": "VATEX-EU-J",
"name": {
"en": "Collectors items and antiques VAT scheme."
}
},
{
"code": "VATEX-EU-O",
"name": {
"en": "Not subject to VAT"
}
},
{
"code": "VATEX-FR-FRANCHISE",
"name": {
"en": "France domestic VAT franchise in base"
}
},
{
"code": "VATEX-FR-CNWVAT",
"name": {
"en": "France domestic Credit Notes without VAT, due to supplier forfeit of VAT for discount"
}
},
{
"code": "VATEX-SA-29",
"name": {
"en": "Financial services mentioned in Article 29 of the VAT Regulations"
}
},
{
"code": "VATEX-SA-29-7",
"name": {
"en": "Life insurance services mentioned in Article 29 of the VAT Regulations"
}
},
{
"code": "VATEX-SA-30",
"name": {
"en": "Real estate transactions mentioned in Article 30 of the VAT Regulations"
}
},
{
"code": "VATEX-SA-32",
"name": {
"en": "Export of goods"
}
},
{
"code": "VATEX-SA-33",
"name": {
"en": "Export of services"
}
},
{
"code": "VATEX-SA-34-1",
"name": {
"en": "The international transport of goods"
}
},
{
"code": "VATEX-SA-34-2",
"name": {
"en": "International transport of passengers"
}
},
{
"code": "VATEX-SA-34-3",
"name": {
"en": "Services directly connected and incidental to a supply of international passenger transport"
}
},
{
"code": "VATEX-SA-34-4",
"name": {
"en": "Supply of a qualifying means of transport"
}
},
{
"code": "VATEX-SA-34-5",
"name": {
"en": "Any services relating to goods or passenger transportation, as defined in Article 25 of the VAT Regulations"
}
},
{
"code": "VATEX-SA-35",
"name": {
"en": "Medicines and medical equipment"
}
},
{
"code": "VATEX-SA-36",
"name": {
"en": "Qualifying metals"
}
},
{
"code": "VATEX-SA-EDU",
"name": {
"en": "Private education to citizen"
}
},
{
"code": "VATEX-SA-HEA",
"name": {
"en": "Private healthcare to citizen"
}
},
{
"code": "VATEX-SA-MLTRY",
"name": {
"en": "Supply of qualified military goods"
}
},
{
"code": "VATEX-SA-OOS",
"name": {
"en": "Reason is free text, to be provided by the taxpayer on a case-by-case basis"
}
}
]
"pattern": "^VATEX-[A-Z]{2}(-[A-Z0-9]+)+$"
@alvarolivie
alvarolivie marked this pull request as ready for review July 29, 2026 16:34
Copilot AI review requested due to automatic review settings July 29, 2026 16:34

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Copilot reviewed 4 out of 4 changed files in this pull request and generated no new comments.

Comments suppressed due to low confidence (1)

addons/eu/en16931/tax_combo_test.go:154

  • This subtest name claims it verifies that a country-specific VATEX code "passes the catalogue pattern", but it only asserts that rules.Validate returns no error. The EN16931 tax combo rules currently don't validate cef-vatex values against the catalogue definition, so this test would pass even if the pattern were missing/incorrect. Add an explicit assertion that the cef-vatex extension value matches the registered definition (e.g. via tax.ExtensionHasValidCode("cef-vatex")).
		norm.Normalize(c, tax.AddonContext(en16931.V2017))
		err := rules.Validate(c, tax.AddonContext(en16931.V2017))
		assert.NoError(t, err)
	})

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants