pain.001 structured-address, before and after.

On November 14, 2026, the SWIFT MX/CBPR+ structured-address mandate makes the freeform <AdrLine> form of <PstlAdr> rejectable on cross-border MX. This page shows the exact XML change, the five required fields, and a working POST /v1/iso20022/pain.001 call.

The XML change

One block. Five fields.

The change applies to every party with a <PstlAdr> Dbtr, Cdtr, UltmtDbtr, UltmtCdtr, InitgPty. Note the town is ASCII-folded (Zürich → Zurich) for the SWIFT "x" Latin-only character set.

Before · freeform (post-mandate reject)

<!-- BEFORE — freeform <AdrLine> (rejected on/after 2026-11-14) -->
<Cdtr>
  <Nm>ACME Supplies GmbH</Nm>
  <PstlAdr>
    <AdrLine>Bahnhofstrasse 45</AdrLine>
    <AdrLine>8001 Zürich</AdrLine>
    <Ctry>CH</Ctry>
  </PstlAdr>
</Cdtr>

After · structured (mandate-compliant)

<!-- AFTER — structured <PstlAdr> (mandate-compliant) -->
<Cdtr>
  <Nm>ACME Supplies GmbH</Nm>
  <PstlAdr>
    <StrtNm>Bahnhofstrasse</StrtNm>   <!-- street, no number   -->
    <BldgNb>45</BldgNb>               <!-- house / building no  -->
    <PstCd>8001</PstCd>               <!-- postal code          -->
    <TwnNm>Zurich</TwnNm>             <!-- town (ASCII-folded)   -->
    <Ctry>CH</Ctry>                   <!-- ISO 3166-1 alpha-2    -->
  </PstlAdr>
</Cdtr>

The five mandate fields

Every one is required.

XML tagAPI fieldMeaning
<StrtNm>street_nameStreet name, without the house number.
<BldgNb>building_numberHouse / building number.
<PstCd>post_codePostal / ZIP code.
<TwnNm>town_nameTown or city name.
<Ctry>countryISO 3166-1 alpha-2 country code (uppercased at emission).

A missing country (or a non-ISO 3166-1 alpha-2 value) is rejected with INVALID_ADDRESS. The builder emits the fields in canonical ISO 20022 order: StrtNm, BldgNb, PstCd, TwnNm, Ctry.

Build it

POST /v1/iso20022/pain.001

Send structured addresses as JSON; the builder validates and emits the mandate-compliant XML. The Idempotency-Key deterministically derives the MsgId so the same logical request always yields the same id — bank-side dedup is safe.

curl -X POST https://api.iso-compliant.com/v1/iso20022/pain.001 \
  -H "Authorization: Bearer $ISO_COMPLIANT_API_KEY" \
  -H "Content-Type: application/json" \
  -H "Idempotency-Key: inv-2026-001234" \
  -d '{
    "debtor": {
      "name": "Willkommen Treasury AG",
      "iban": "CH9300762011623852957",
      "address": {
        "street_name": "Paradeplatz",
        "building_number": "8",
        "post_code": "8001",
        "town_name": "Zurich",
        "country": "CH"
      }
    },
    "creditor": {
      "name": "ACME Supplies GmbH",
      "iban": "DE89370400440532013000",
      "address": {
        "street_name": "Bahnhofstrasse",
        "building_number": "45",
        "post_code": "8001",
        "town_name": "Zurich",
        "country": "CH"
      }
    },
    "amount": "1250.00",
    "currency": "EUR",
    "end_to_end_id": "INV-2026-001234"
  }'

What happens if you send freeform

On a post-mandate ruleset, the legacy address_line field is rejected at validation — before any XML is serialised — so you catch it in your own pipeline, not at the bank.

// If you send the legacy freeform field on a post-mandate ruleset:
{
  "creditor": {
    "address": { "address_line": "Bahnhofstrasse 45, 8001 Zurich", "country": "CH" }
  }
}
// → 422  STRUCTURED_ADDRESS_REQUIRED
//   "creditor address uses legacy freeform 'address_line' which is rejected
//    by the SWIFT MX/CBPR+ structured-address mandate effective 2026-11-14"

Emit a mandate-compliant pain.001 today

100 documents/month free, no card. Point your existing SDK at api.iso-compliant.com.

Get an API key