sepa_rator 0.16.0 → 1.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (86) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +134 -46
  3. data/lib/schema/at/pain.001.001.03.at.004.xsd +1942 -0
  4. data/lib/schema/at/pain.001.001.03.xsd +921 -0
  5. data/lib/schema/at/pain.001.001.09.at.005.xsd +2094 -0
  6. data/lib/schema/at/pain.001.codelists.xsd +4680 -0
  7. data/lib/schema/at/pain.001_codelists.xsd +6314 -0
  8. data/lib/schema/at/pain.008.001.02.at.004.xsd +2204 -0
  9. data/lib/schema/at/pain.008.001.02.xsd +879 -0
  10. data/lib/schema/at/pain.008.001.08.at.004.xsd +2185 -0
  11. data/lib/schema/at/pain.008.codelists.xsd +3111 -0
  12. data/lib/schema/at/pain.008_codelists.xsd +6275 -0
  13. data/lib/schema/dk/pain.001.001.03_GBIC_3.xsd +499 -0
  14. data/lib/schema/dk/pain.001.001.09_GBIC_5.xsd +2411 -0
  15. data/lib/schema/dk/pain.008.001.02_GBIC_3.xsd +625 -0
  16. data/lib/schema/dk/pain.008.001.08_GBIC_5.xsd +2690 -0
  17. data/lib/schema/iso/pain.001.001.09.xsd +1114 -0
  18. data/lib/schema/iso/pain.008.001.08.xsd +1106 -0
  19. data/lib/schema/sps/pain.001.001.09.ch.03.xsd +1733 -0
  20. data/lib/schema/sps/pain.008.001.02.chsdd.02.xsd +1056 -0
  21. data/lib/sepa_rator/account/address.rb +11 -0
  22. data/lib/sepa_rator/account/creditor_account.rb +2 -2
  23. data/lib/sepa_rator/account/debtor_account.rb +4 -3
  24. data/lib/sepa_rator/account.rb +11 -10
  25. data/lib/sepa_rator/builders/credit_transfer/group_header.rb +40 -0
  26. data/lib/sepa_rator/builders/credit_transfer/payment_information.rb +85 -0
  27. data/lib/sepa_rator/builders/credit_transfer/transaction/amount.rb +20 -0
  28. data/lib/sepa_rator/builders/credit_transfer/transaction/credit_transfer_mandate.rb +24 -0
  29. data/lib/sepa_rator/builders/credit_transfer/transaction/creditor.rb +19 -0
  30. data/lib/sepa_rator/builders/credit_transfer/transaction/creditor_account.rb +15 -0
  31. data/lib/sepa_rator/builders/credit_transfer/transaction/creditor_agent.rb +22 -0
  32. data/lib/sepa_rator/builders/credit_transfer/transaction/instructions_for_creditor_agent.rb +26 -0
  33. data/lib/sepa_rator/builders/credit_transfer/transaction/payment_id.rb +19 -0
  34. data/lib/sepa_rator/builders/credit_transfer/transaction/purpose.rb +15 -0
  35. data/lib/sepa_rator/builders/credit_transfer/transaction/regulatory_reporting.rb +87 -0
  36. data/lib/sepa_rator/builders/credit_transfer/transaction/remittance_information.rb +15 -0
  37. data/lib/sepa_rator/builders/credit_transfer/transaction/txn_instruction_for_debtor_agent.rb +35 -0
  38. data/lib/sepa_rator/builders/credit_transfer/transaction/ultimate_creditor.rb +19 -0
  39. data/lib/sepa_rator/builders/credit_transfer/transaction/ultimate_debtor.rb +19 -0
  40. data/lib/sepa_rator/builders/direct_debit/group_header.rb +23 -0
  41. data/lib/sepa_rator/builders/direct_debit/payment_information.rb +80 -0
  42. data/lib/sepa_rator/builders/direct_debit/transaction/amount.rb +18 -0
  43. data/lib/sepa_rator/builders/direct_debit/transaction/debtor.rb +19 -0
  44. data/lib/sepa_rator/builders/direct_debit/transaction/debtor_account.rb +15 -0
  45. data/lib/sepa_rator/builders/direct_debit/transaction/debtor_agent.rb +20 -0
  46. data/lib/sepa_rator/builders/direct_debit/transaction/direct_debit_info.rb +61 -0
  47. data/lib/sepa_rator/builders/direct_debit/transaction/payment_id.rb +19 -0
  48. data/lib/sepa_rator/builders/direct_debit/transaction/purpose.rb +15 -0
  49. data/lib/sepa_rator/builders/direct_debit/transaction/remittance_information.rb +15 -0
  50. data/lib/sepa_rator/builders/direct_debit/transaction/ultimate_creditor.rb +19 -0
  51. data/lib/sepa_rator/builders/direct_debit/transaction/ultimate_debtor.rb +19 -0
  52. data/lib/sepa_rator/builders/stage.rb +31 -0
  53. data/lib/sepa_rator/concerns/schema_validation.rb +29 -17
  54. data/lib/sepa_rator/concerns/xml_builder.rb +49 -21
  55. data/lib/sepa_rator/error.rb +36 -0
  56. data/lib/sepa_rator/message/credit_transfer.rb +12 -198
  57. data/lib/sepa_rator/message/direct_debit.rb +12 -126
  58. data/lib/sepa_rator/message.rb +180 -176
  59. data/lib/sepa_rator/profile.rb +269 -0
  60. data/lib/sepa_rator/profiles/at.rb +65 -0
  61. data/lib/sepa_rator/profiles/cfonb.rb +45 -0
  62. data/lib/sepa_rator/profiles/country_defaults.rb +144 -0
  63. data/lib/sepa_rator/profiles/dk.rb +57 -0
  64. data/lib/sepa_rator/profiles/epc.rb +50 -0
  65. data/lib/sepa_rator/profiles/gb.rb +70 -0
  66. data/lib/sepa_rator/profiles/iso.rb +233 -0
  67. data/lib/sepa_rator/profiles/sps.rb +80 -0
  68. data/lib/sepa_rator/transaction/credit_transfer_transaction.rb +71 -77
  69. data/lib/sepa_rator/transaction/direct_debit_transaction.rb +8 -33
  70. data/lib/sepa_rator/transaction.rb +14 -0
  71. data/lib/sepa_rator/validators/dk/min_amount.rb +12 -0
  72. data/lib/sepa_rator/validators/min_amount.rb +22 -0
  73. data/lib/sepa_rator/version.rb +1 -1
  74. data/lib/sepa_rator.rb +50 -0
  75. metadata +68 -12
  76. data/lib/schema/pain.001.001.03.ch.02.xsd +0 -1212
  77. /data/lib/schema/{pain.001.001.09.xsd → at/pain.001.001.09.xsd} +0 -0
  78. /data/lib/schema/{pain.008.001.08.xsd → at/pain.008.001.08.xsd} +0 -0
  79. /data/lib/schema/{pain.001.001.03.xsd → iso/pain.001.001.03.xsd} +0 -0
  80. /data/lib/schema/{pain.001.001.13.xsd → iso/pain.001.001.13.xsd} +0 -0
  81. /data/lib/schema/{pain.001.002.03.xsd → iso/pain.001.002.03.xsd} +0 -0
  82. /data/lib/schema/{pain.001.003.03.xsd → iso/pain.001.003.03.xsd} +0 -0
  83. /data/lib/schema/{pain.008.001.02.xsd → iso/pain.008.001.02.xsd} +0 -0
  84. /data/lib/schema/{pain.008.001.12.xsd → iso/pain.008.001.12.xsd} +0 -0
  85. /data/lib/schema/{pain.008.002.02.xsd → iso/pain.008.002.02.xsd} +0 -0
  86. /data/lib/schema/{pain.008.003.02.xsd → iso/pain.008.003.02.xsd} +0 -0
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 83ba8734459eaf10832606aa2c4c894cad0fde36f221a88e4664d55ec929d1d6
4
- data.tar.gz: 54c0ad9c0f54bcfa88b2912cd1f93b5fd2574d15581574dd5bd2760941adef10
3
+ metadata.gz: 142a5f6d6bff2b0355c10149b9654e20f2754b73db9ba049191c00dd5571e370
4
+ data.tar.gz: 34979be8d246b1e4dbcbb4ac8e0e9d6852a7b5406b76bd171838bb4a16f55b5f
5
5
  SHA512:
6
- metadata.gz: 2570e0b6dc02a36accc1d6caeeeb19b064f6da7395f43a1d13af1629de401f67b94d07fcbd45dd82b5e6bc473860ede0c8a6e41f811eca5e66f1fda15398444c
7
- data.tar.gz: eb2e7d4a6b6809f4a4eeec006de9816773407845c3a74a002fe082d7fb4190052389ea007b7357bf65651638d83c9cbafbc15135faba6decf145de16d0f48558
6
+ metadata.gz: ee2885d89f417ff31bf9ee8ebe692ba5aaddd5533cc129b995d039f2727447e47f4e62ad7867ad1d34f53a5f8f4a4c5f61c3168f5050cd0c194ec435c6b68d05
7
+ data.tar.gz: 4f0cd2f5f693efbbb91decb08384d54b6e9b97580ba01f9921a5ff8513c199a44445f7365e91cd1dd80f28c50280a394b8f8638b493a7b86d7e5d8f6ea31c483
data/README.md CHANGED
@@ -3,97 +3,181 @@
3
3
  [![Build Status](https://github.com/AdVitam/sepa_rator/workflows/Test/badge.svg?branch=master)](https://github.com/AdVitam/sepa_rator/actions)
4
4
 
5
5
  Successor to [salesking/sepa_king](https://github.com/salesking/sepa_king) (unmaintained since 2022).
6
- Adds support for newer SEPA schemas (`pain.001.001.09`, `pain.001.001.13`,
7
- `pain.008.001.08`, `pain.008.001.12`) with extensive code quality
8
- and security improvements.
6
+ Adds support for newer SEPA schemas and a **profile-based architecture** that makes
7
+ national variants (CFONB for France, DK/DFÜ for Germany, …) first-class.
9
8
 
10
9
  ## Features
11
10
 
12
- * **Credit Transfer** (`pain.001`) schemas `.001.13`, `.001.09`, `.003.03`, `.002.03`, `.001.03`, `.001.03.ch.02`
13
- * **Direct Debit** (`pain.008`)schemas `.001.12`, `.001.08`, `.003.02`, `.002.02`, `.001.02`
14
- * Full XSD validation on every generated XML
15
- * Postal addresses, contact details, LEI, regulatory reporting
16
- * Flexible charge bearer (SLEV, DEBT, CRED, SHAR)
17
- * Mandate amendment support (original mandate ID, debtor account, creditor scheme)
11
+ - **Credit Transfer** (`pain.001`) and **Direct Debit** (`pain.008`) across 7 profile families (see table below)
12
+ - Resolves the right profile from a simple `country: :fr` hint falls back to generic EPC for unlisted countries
13
+ - Full XSD validation on every generated XML
14
+ - Postal addresses, contact details, LEI, regulatory reporting
15
+ - Flexible charge bearer (SLEV, DEBT, CRED, SHAR)
16
+ - Mandate amendment support (original mandate ID, debtor account, creditor scheme)
18
17
 
19
18
  **pain** = **Pa**yment **In**itiation (ISO 20022).
20
19
 
20
+ ## Supported schemas & profiles
21
+
22
+ | Family | Namespace | Country hint | Credit Transfer (pain.001) | Direct Debit (pain.008) |
23
+ |---|---|---|---|---|
24
+ | ISO (raw XSD) | `Profiles::ISO` | — | `SCT_03`, `SCT_09`, `SCT_13`, `SCT_EPC_002_03`, `SCT_EPC_003_03` | `SDD_02`, `SDD_08`, `SDD_12`, `SDD_EPC_002_02`, `SDD_EPC_003_02` |
25
+ | EPC SEPA | `Profiles::EPC` | _(SEPA fallback)_ | `SCT_03`, `SCT_09`, `SCT_13` | `SDD_02`, `SDD_08`, `SDD_12` |
26
+ | CFONB 🇫🇷 | `Profiles::CFONB` | `country: :fr` | `SCT_03`, `SCT_09`, `SCT_13` | `SDD_02`, `SDD_08`, `SDD_12` |
27
+ | DK / DFÜ 🇩🇪 | `Profiles::DK` | `country: :de` | `SCT_03_GBIC3`, `SCT_09_GBIC5`, `SCT_13_GBIC5` | `SDD_02_GBIC3`, `SDD_08_GBIC5`, `SDD_12_GBIC5` |
28
+ | SPS 🇨🇭 | `Profiles::SPS` | `country: :ch` | `SCT_03`, `SCT_09`, `SCT_13` | `SDD_02`, `SDD_08`, `SDD_12` |
29
+ | GB 🇬🇧 | `Profiles::GB` | `country: :gb` | `SCT_03`, `SCT_09`, `SCT_13` | `SDD_02`, `SDD_08`, `SDD_12` |
30
+ | AT / PSA 🇦🇹 | `Profiles::AT` | `country: :at` | `SCT_03`, `SCT_09`, `SCT_13` | `SDD_02`, `SDD_08`, `SDD_12` |
31
+
32
+ For the full per-profile detail (XSD, constraints, capabilities), see [DOCUMENTATION.md](DOCUMENTATION.md#supported-profiles-and-schemas). Adding a new country is a single file in `lib/sepa_rator/profiles/` plus entries in `lib/sepa_rator/profiles/country_defaults.rb`.
33
+
21
34
  ## Requirements
22
35
 
23
- * Ruby 3.1+
24
- * ActiveModel 7.0+ (including 8.1)
36
+ - Ruby 3.2+
37
+ - ActiveModel 7.0+ (tested up to 8.1)
25
38
 
26
39
  ## Installation
27
40
 
28
41
  ```ruby
29
- gem 'sepa_rator'
42
+ gem 'sepa_rator', '~> 1.0'
30
43
  ```
31
44
 
32
45
  ## Quick start
33
46
 
34
- ### Credit Transfer
47
+ ### The simplest possible Credit Transfer
48
+
49
+ No profile, no country, no schema name — defaults to the latest EPC SEPA profile:
35
50
 
36
51
  ```ruby
37
52
  sct = SEPA::CreditTransfer.new(
38
- name: 'Debtor Inc.',
39
- bic: 'BANKDEFFXXX',
40
- iban: 'DE87200500001234567890'
53
+ name: 'Acme Ltd',
54
+ bic: 'BNPAFRPPXXX',
55
+ iban: 'FR7612345678901234567890123'
41
56
  )
42
57
 
43
58
  sct.add_transaction(
44
- name: 'Creditor AG',
45
- bic: 'PBNKDEFF370',
46
- iban: 'DE37112589611964645802',
59
+ name: 'Supplier GmbH',
60
+ iban: 'DE21500500009876543210',
47
61
  amount: 102.50,
48
- reference: 'XYZ-1234/123',
62
+ reference: 'INV-123',
49
63
  remittance_information: 'Invoice 123'
50
64
  )
51
65
 
52
- xml = sct.to_xml # pain.001.001.03 (default)
53
- xml = sct.to_xml('pain.001.001.09') # newer schema
54
- xml = sct.to_xml('pain.001.001.13') # latest schema
66
+ xml = sct.to_xml
55
67
  ```
56
68
 
57
- ### Direct Debit
69
+ ### The simplest possible Direct Debit
58
70
 
59
71
  ```ruby
60
72
  sdd = SEPA::DirectDebit.new(
61
- name: 'Creditor Inc.',
62
- bic: 'BANKDEFFXXX',
63
- iban: 'DE87200500001234567890',
64
- creditor_identifier: 'DE98ZZZ09999999999'
73
+ name: 'Acme Ltd',
74
+ bic: 'BNPAFRPPXXX',
75
+ iban: 'FR7612345678901234567890123',
76
+ creditor_identifier: 'FR72ZZZ123456'
65
77
  )
66
78
 
67
79
  sdd.add_transaction(
68
- name: 'Debtor Corp.',
69
- bic: 'SPUEDE2UXXX',
80
+ name: 'Customer SA',
70
81
  iban: 'DE21500500009876543210',
71
82
  amount: 39.99,
72
- reference: 'XYZ/2013-08-ABO/6789',
73
- mandate_id: 'K-02-2011-12345',
74
- mandate_date_of_signature: Date.new(2011, 1, 25),
75
- sequence_type: 'OOFF'
83
+ reference: 'SUB/2025-08/001',
84
+ mandate_id: 'MND-2025-001',
85
+ mandate_date_of_signature: Date.new(2025, 1, 15)
76
86
  )
77
87
 
78
- xml = sdd.to_xml # pain.008.001.02 (default)
79
- xml = sdd.to_xml('pain.008.001.08') # newer schema
80
- xml = sdd.to_xml('pain.008.001.12') # latest schema
88
+ xml = sdd.to_xml
89
+ ```
90
+
91
+ ## The 4-level public API
92
+
93
+ `sepa_rator` exposes a progressive API: the simpler path covers 90 % of use
94
+ cases; the explicit path is there when you need it.
95
+
96
+ ### Level 0 — defaults (generic SEPA)
97
+
98
+ Do nothing special and get the latest EPC SEPA profile
99
+ (`pain.001.001.13` for credit transfer, `pain.008.001.12` for direct debit):
100
+
101
+ ```ruby
102
+ SEPA::CreditTransfer.new(name: ..., iban: ..., bic: ...)
103
+ SEPA::DirectDebit.new(name: ..., iban: ..., bic: ..., creditor_identifier: ...)
104
+ ```
105
+
106
+ ### Level 1 — hint by country
107
+
108
+ The country code is **the country of the bank that will receive and process
109
+ your XML file** — your own bank for credit transfers, the creditor's bank for
110
+ direct debits. It is **not** the country of the beneficiary.
111
+
112
+ > Example: a company with a French bank pays Italian and German suppliers.
113
+ > The file goes to the French bank, so write `country: :fr`. The suppliers'
114
+ > IBANs can be from any SEPA country.
115
+
116
+ ```ruby
117
+ SEPA::CreditTransfer.new(country: :fr, name: ..., iban: ..., bic: ...)
118
+ # → SEPA::Profiles::CFONB::SCT_13
119
+
120
+ SEPA::DirectDebit.new(country: :de, name: ..., iban: ..., bic: ...,
121
+ creditor_identifier: ...)
122
+ # → SEPA::Profiles::DK::SDD_12_GBIC5
123
+ ```
124
+
125
+ Countries without a dedicated profile (e.g. `:it`, `:es`, `:be`) fall back
126
+ to the generic EPC profile automatically.
127
+
128
+ ### Level 2 — country + version
129
+
130
+ If your bank hasn't upgraded to the latest ISO version yet, pin the version:
131
+
132
+ ```ruby
133
+ SEPA::CreditTransfer.new(country: :fr, version: :v09, ...)
134
+ # → SEPA::Profiles::CFONB::SCT_09
135
+ ```
136
+
137
+ Supported version symbols:
138
+
139
+ | Family | Versions |
140
+ |-----------------|-------------------------|
141
+ | `credit_transfer` | `:v09`, `:v13`, `:latest` |
142
+ | `direct_debit` | `:v08`, `:v12`, `:latest` |
143
+
144
+ Requesting an unknown version raises `SEPA::UnsupportedVersionError` with
145
+ the list of available versions.
146
+
147
+ The older EPC AOS schemas (`pain.001.002.03`, `pain.001.003.03`,
148
+ `pain.008.002.02`, `pain.008.003.02`) are not exposed through the
149
+ `country:` / `version:` API — use Level 3 (explicit
150
+ `SEPA::Profiles::ISO::*` constants) if you need them.
151
+
152
+ ### Level 3 — explicit profile (power user)
153
+
154
+ Pass a `SEPA::Profile` constant directly when you need a specific variant:
155
+
156
+ ```ruby
157
+ SEPA::CreditTransfer.new(
158
+ profile: SEPA::Profiles::DK::SCT_09_GBIC5,
159
+ name: ..., iban: ..., bic: ...
160
+ )
81
161
  ```
82
162
 
83
- ### Validators
163
+ `profile:` is mutually exclusive with `country:` / `version:` — passing
164
+ both raises `ArgumentError`.
84
165
 
85
- Reuse SEPA validators in your own models:
166
+ ## Reusing validators
86
167
 
87
168
  ```ruby
88
169
  class BankAccount < ActiveRecord::Base
89
170
  validates_with SEPA::IBANValidator, field_name: :iban
90
171
  validates_with SEPA::BICValidator, field_name: :bic
172
+ validates_with SEPA::LEIValidator, field_name: :agent_lei
91
173
  end
92
174
  ```
93
175
 
94
176
  ## Documentation
95
177
 
96
- For the full list of options (addresses, charge bearer, amendment info, batch booking, service level, etc.), see [DOCUMENTATION.md](DOCUMENTATION.md).
178
+ For the full list of options (addresses, charge bearer, amendment info,
179
+ regulatory reporting, LEI, contact details, etc.), see
180
+ [DOCUMENTATION.md](DOCUMENTATION.md).
97
181
 
98
182
  ## Changelog
99
183
 
@@ -101,17 +185,21 @@ See [CHANGELOG.md](CHANGELOG.md).
101
185
 
102
186
  ## Contributors
103
187
 
104
- * [Original contributors](https://github.com/salesking/sepa_king/graphs/contributors) (salesking/sepa_king)
105
- * [sepa_rator contributors](https://github.com/AdVitam/sepa_rator/graphs/contributors)
188
+ - [Original contributors](https://github.com/salesking/sepa_king/graphs/contributors) (salesking/sepa_king)
189
+ - [sepa_rator contributors](https://github.com/AdVitam/sepa_rator/graphs/contributors)
106
190
 
107
191
  ## Resources
108
192
 
109
- * [ISO 20022 message definitions](https://www.iso20022.org/iso-20022-message-definitions)
110
- * <https://www.ebics.de/de/datenformate>
193
+ - [ISO 20022 message definitions](https://www.iso20022.org/iso-20022-message-definitions)
194
+ - [EPC rulebooks](https://www.europeanpaymentscouncil.eu/document-library)
195
+ - [CFONB guides](https://www.cfonb.org/espaces-telechargements/documents)
196
+ - [EBICS / DK data formats](https://www.ebics.de/de/datenformate)
197
+ - [Swiss Payment Standards (SIX)](https://www.six-group.com/en/products-services/banking-services/payment-standardization/standards/iso-20022.html)
198
+ - [Bank of England ISO 20022 handbook](https://www.bankofengland.co.uk/payment-and-settlement/rtgs-renewal-programme/iso-20022-handbook)
111
199
 
112
200
  ## License
113
201
 
114
202
  Released under the [MIT License](LICENSE.txt).
115
203
 
116
- Originally copyright (c) 2013-2022 Georg Leciejewski (SalesKing), Georg Ledermann.
117
- Copyright (c) 2025-2026 AdVitam.
204
+ - Originally copyright (c) 2013-2022 Georg Leciejewski (SalesKing), Georg Ledermann.
205
+ - Copyright (c) 2025-2026 Advitam — fork, maintenance, profile-based architecture.