Skip to content

feat: map party electronic address via the endpoint object - #111

Open
alvarolivie wants to merge 3 commits into
mainfrom
party-endpoint-mapping
Open

feat: map party electronic address via the endpoint object#111
alvarolivie wants to merge 3 commits into
mainfrom
party-endpoint-mapping

Conversation

@alvarolivie

Copy link
Copy Markdown
Collaborator

What

Map the UBL cbc:EndpointID (BT-34 / BT-49, the party's electronic
address) to and from GOBL's org.Party.Endpoints — the org.Endpoint
URI — instead of the deprecated org.Party.Inboxes.

Mapping

GOBL endpoint URI UBL EndpointID
mailto:<address> schemeID="EM" value <address>
iso6523-actorid-upis::<scheme>:<code> schemeID="<scheme>" value <code>

This matches the URI convention GOBL's eu/en16931 addon uses when it
normalizes Peppol inboxes into endpoints, extended to email (mailto:).

  • Serialize: newEndpointID reads party.FirstEndpoint().
  • Parse: goblEndpoint writes the inverse as an org.Endpoint.

Test data

  • Convert goldens are unchanged (byte-identical XML). Each
    supplier/customer fixture gains an endpoint carrying exactly the
    value the old inbox-based serializer emitted, so switching the source
    is a no-op on the wire.
  • ⚠️ Four France fixtures (france-cius/{credit-note-fr,invoice-fr-cius},
    france-extended/invoice-fr-extended{,-detailed}) carried a stale
    endpoint schemeID="9957" that disagreed with both their inbox and
    the committed golden (schemeID="0225"). The 0225 value is newer —
    it arrived with the APP-546 French-validation work, after the 9957
    endpoints — so I reconciled the endpoints to 0225 to keep the
    reviewed output. Please confirm 0225 is the intended French EAS
    scheme
    ; if 9957 is correct instead, it's a one-line fixture change
    plus a golden regen.
  • Parse goldens are regenerated (second commit): parsed inboxes
    become endpoints, and the envelope head gains the from/to routing
    now derivable from the endpoints.

Notes

Depends on GOBL's endpoint model; new builds normalized through the
en16931 addon already carry endpoints. Paired with the equivalent
change in gobl.cii.

🤖 Generated with Claude Code

alvarolivie and others added 2 commits July 20, 2026 11:19
Read and write the UBL cbc:EndpointID from org.Party.Endpoints (the
org.Endpoint URI) instead of the deprecated org.Party.Inboxes.

- Serialize: newEndpointID reads the party's first endpoint and maps
  "mailto:<addr>"                       -> schemeID "EM", and
  "iso6523-actorid-upis::<scheme>:<code>" -> schemeID "<scheme>".
- Parse: goblEndpoint writes the inverse as an org.Endpoint URI.

Convert fixtures gain endpoints migrated from their inboxes so the
generated UBL stays byte-identical (no golden XML changes). Four France
fixtures carried stale endpoints (schemeID 9957) that disagreed with
both their inbox and the validated golden (schemeID 0225, added later
alongside the APP-546 French validation work); these are reconciled to
0225 to preserve the reviewed output.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Parsed party inboxes become endpoints, and the envelope head gains the
from/to routing now derivable from those endpoints. Mechanically
regenerated with `go test -run TestParseInvoice -update`.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Copilot AI review requested due to automatic review settings July 20, 2026 11:20

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 updates the UBL party electronic address mapping to use GOBL’s org.Party.Endpoints (URI-based) for UBL cbc:EndpointID serialization/parsing, replacing the legacy inbox-based approach and updating fixture expectations accordingly.

Changes:

  • Serialize UBL cbc:EndpointID from party.FirstEndpoint() (URI forms: mailto: and iso6523-actorid-upis::).
  • Parse UBL cbc:EndpointID into org.Party.Endpoints via a new goblEndpoint mapper.
  • Regenerate/adjust parse and convert fixtures to reflect endpoints and envelope head.from/head.to routing.

Reviewed changes

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

Show a summary per file
File Description
party.go Serialize cbc:EndpointID from the party’s first endpoint URI; adds endpoint URI scheme constants and parsing helper.
party_parse.go Parse cbc:EndpointID into org.Party.Endpoints (URI form) via goblEndpoint.
party_parse_test.go Updates party parsing assertions to validate endpoints URIs instead of inbox fields.
test/data/parse/peppol/out/vat-category-Z.json Updates parsed party addressing from inboxes to endpoints; adds envelope from/to.
test/data/parse/peppol/out/Vat-category-S.json Updates parsed party addressing from inboxes to endpoints; adds envelope from/to.
test/data/parse/peppol/out/vat-category-O.json Updates parsed party addressing from inboxes to endpoints; adds envelope from/to.
test/data/parse/peppol/out/vat-category-O-invalid-bytes.json Updates parsed party addressing from inboxes to endpoints; adds envelope from/to.
test/data/parse/peppol/out/vat-category-E.json Updates parsed party addressing from inboxes to endpoints; adds envelope from/to.
test/data/parse/peppol/out/sg-invoice.json Updates parsed party addressing from inboxes to endpoints; adds envelope from/to.
test/data/parse/peppol/out/self-billed-invoice.json Updates parsed party addressing from inboxes to endpoints; adds envelope from/to.
test/data/parse/peppol/out/self-billed-creditnote.json Updates parsed party addressing from inboxes to endpoints; adds envelope from/to.
test/data/parse/peppol/out/sales-order-example.json Updates parsed party addressing from inboxes to endpoints; adds envelope from/to.
test/data/parse/peppol/out/proforma-invoice.json Updates parsed party addressing from inboxes to endpoints; adds envelope from/to.
test/data/parse/peppol/out/partial-invoice.json Updates parsed party addressing from inboxes to endpoints; adds envelope from/to.
test/data/parse/peppol/out/nbio-stuck-ubl.json Updates parsed party addressing from inboxes to endpoints; adds envelope from/to.
test/data/parse/peppol/out/invoice-peppol.json Updates parsed party addressing from inboxes to endpoints; adds envelope from/to.
test/data/parse/peppol/out/example-encoding.json Updates parsed party addressing from inboxes to endpoints; adds envelope from/to.
test/data/parse/peppol/out/base-negative-inv-correction.json Updates parsed party addressing from inboxes to endpoints; adds envelope from/to.
test/data/parse/peppol/out/base-example.json Updates parsed party addressing from inboxes to endpoints; adds envelope from/to.
test/data/parse/peppol/out/base-creditnote-correction.json Updates parsed party addressing from inboxes to endpoints; adds envelope from/to.
test/data/parse/peppol/out/Allowance-example.json Updates parsed party addressing from inboxes to endpoints; adds envelope from/to.
test/data/parse/france-cius/out/b2b-reg.json Removes parsed inboxes in favor of endpoints (and aligns routing).
test/data/parse/en16931/out/ubl-example5.json Switches parsed email inboxes to mailto: endpoints; adds envelope routing.
test/data/parse/en16931/out/ubl-example2.json Switches parsed email inboxes to mailto: endpoints.
test/data/convert/xrechnung/invoice-xr-minimal.json Adds endpoint URIs to parties to keep wire output stable while moving off inboxes.
test/data/convert/xrechnung/invoice-due-date-with-notes.json Adds endpoint URIs to parties to keep wire output stable while moving off inboxes.
test/data/convert/xrechnung/credit-note-xr.json Adds endpoint URIs to parties to keep wire output stable while moving off inboxes.
test/data/convert/peppol/invoice-intra-comunity.json Adds Peppol participant endpoint URI to keep wire output stable while moving off inboxes.
test/data/convert/invoice-complete.json Adds mailto: endpoint URI to keep wire output stable while moving off inboxes.
test/data/convert/invoice-attachments.json Adds mailto: endpoint URI to keep wire output stable while moving off inboxes.
test/data/convert/france-extended/invoice-fr-extended.json Reconciles France endpoint scheme in endpoint URIs (and keeps inbox scheme aligned).
test/data/convert/france-extended/invoice-fr-extended-detailed.json Reconciles France endpoint scheme in endpoint URIs (and keeps inbox scheme aligned).
test/data/convert/france-cius/invoice-fr-cius.json Reconciles France endpoint scheme in endpoint URI (and keeps inbox scheme aligned).
test/data/convert/france-cius/credit-note-fr.json Reconciles France endpoint scheme in endpoint URI (and keeps inbox scheme aligned).
test/data/convert/en16931/invoice-complete.json Adds mailto: endpoint URI to keep wire output stable while moving off inboxes.
test/data/convert/en16931/invoice-attachments.json Adds mailto: endpoint URI to keep wire output stable while moving off inboxes.

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

Comment thread party_parse.go
Comment on lines +78 to +87
if eID == nil || eID.Value == "" || eID.SchemeID == "" {
return nil
}
var uri cbc.URI
switch eID.SchemeID {
case SchemeIDEmail: // email
uri = cbc.URI(mailtoScheme + ":" + eID.Value)
default:
uri = cbc.URI(peppolEndpointScheme + "::" + eID.SchemeID + ":" + eID.Value)
}
The envelope head from/to routing in the France fixtures still pointed
at the same participants via the stale schemeID 9957; move them to 0225
to match the reconciled party endpoints. No output change (goldens are
untouched).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Copilot AI review requested due to automatic review settings July 20, 2026 11:32
@codecov-commenter

Copy link
Copy Markdown

Codecov Report

❌ Patch coverage is 90.00000% with 3 lines in your changes missing coverage. Please review.
✅ Project coverage is 81.01%. Comparing base (44edd23) to head (6c92f2e).

Files with missing lines Patch % Lines
party.go 83.33% 2 Missing and 1 partial ⚠️
Additional details and impacted files
@@            Coverage Diff             @@
##             main     #111      +/-   ##
==========================================
- Coverage   81.05%   81.01%   -0.05%     
==========================================
  Files          28       28              
  Lines        2143     2154      +11     
==========================================
+ Hits         1737     1745       +8     
- Misses        268      270       +2     
- Partials      138      139       +1     

☔ 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.

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 15 out of 36 changed files in this pull request and generated 1 comment.

Comment thread party.go
Comment on lines +60 to +76
func newEndpointID(party *org.Party) *EndpointID {
ep := party.FirstEndpoint()
if ep == nil {
return nil
}
switch ep.URI.Scheme() {
case mailtoScheme:
if addr := ep.URI.Opaque(); addr != "" {
return &EndpointID{SchemeID: SchemeIDEmail, Value: addr}
}
case peppolEndpointScheme:
if scheme, code, ok := splitPeppolEndpoint(ep.URI.Opaque()); ok {
return &EndpointID{SchemeID: scheme, Value: code}
}
}
return nil
}
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.

3 participants