MT940 File Support

CoreWallet supports MT940 out of the box. However, going through this documentation, you will be able to understand what MT940 is and what the system does and how and where you can configure the functionality.

What is MT940

MT940 is a type of Swift message format sent to non-financial institutions by a financial institution to show account statements. Below is sample format:

:20:D180320103
:25:70011110/0000998036
:28C:00023/001
:60F:C180320EUR000000011954,00
:61:1803200115CR000000000200,00NTRF0000551979735530//035519797/003553
:86:166?00SEPA GUTSCHRIFT BANK?20SVWZ+NOTPROVIDED?21SVWZ+CX-2XC24A3J4K5R2349YYYCL-CX?30COBADEHD001?31DE95200411330361579600?32TOB
IAS TESTER?34166
:61:1803200115CR000000000150,00NTRF0000551979773460//035519797/007346
:86:166?00SEPA GUTSCHRIFT BANK?20EREF+CX-2XC24A3J4K5SJNG63JKAR-CX?30HELADEF1TSK?31DE915125000
00008417130?32THOMAS TESTER?34166
:61:1803200115CR000000000400,00NTRF0000551979759640//035519797/015964
:86:166?00SEPA GUTSCHRIFT BANK?20SVWZ+NOTPROVIDED?21SVWZ+CX-2XC24A3J4K5R5MDRFGN6Z-CX?30WELADED1WIE?31DE28384524900000141986?32SIM
ON TEST?34166
:62F:C180320EUR000000012704,00

What does this system do

In summary, the system takes in an MT940 file and stores the content with the necessary information, then parses the content and categorizes it based on whether it is in a correct format or not. For those that are successfully parsed, they are picked for payment.

How is the MT940 module structured?

This implementation has three integral parts, the ingress, the parser and the payment. All these can work independently of each other but with a common table. The output of the ingress is the input of the parser, while the output of the parser is the input of the payment. See below diagram for illustration.

MT940 Ingress

Prerequisite for the ingress is an existing business contract. This must have been created in the system because;

  1. The business contract contains the path to look into when searching for MT940 file ( this is the case if the MT940FileReaderJob is used)
  2. The subsidiary of this business contract is used to create paymentData.

The MT940 ingress part allows for the creation of MT940 records into the system and the content is stored using the file transmission service (read more). The current implementation supports two types of ingress.

Job: MT940FileReaderJob 

Below describe how this job does is work:

  1. The job gets all the active business contracts using the contract qualifier, business Contract Status (BusinessContractStatus.Active), BusinessContractType(BusinessContractType.BankContract), and searches for available MT940 for each of this business contract.The current implementation hard code the contract qualifier which is SEPA. If this need to change in the future, you can go into the com.trimplement.wallet.server.payment.impl.mt940.MT940FileReaderImpl to change the contract qualifier to the intended one or change the logic to cater for different contract qualifiers.

Each of these business contracts has three directories configured for them; the input directory, the success directory and the failed directory:

i)  the input directory tells the job where to check for available MT940 file

ii) the successful directory tells the job where to move the MT940 file when the   record is created successfully and the content is saved as well.

iii) the failed directory provides the job the path to move files that were not successfully created.

  1. The MT940 Ingress has a default base directory (/MT940/) where all the directories described above are appended to. To change the default base directory, you can modify the trimplement.wallet.server.payment.impl.mt940.baseDirectory property
  2. Due to the possible size and number of MT940 files, this job will pick them in batches. The default batchSize is 100. However, to configure the batch size, you can modify trimplement.wallet.server.payment.impl.mt940.fileBatchSize to the desired number.
  3. The job then calls com.trimplement.wallet.server.payment.impl.mt940.MT940FileService#storeFile to create the MT940 file record in the database and save the content using the file transmission service

API: (/v2/admin/payment/mt940/files) 

The api is used to create an MT940 file in the system. This api expects the business contract id and the corresponding MT940 file. And it also makes sure that the caller has ADMIN permission to create the MT940. Then the  com.trimplement.wallet.server.payment.impl.mt940.MT940FileService#storeFile is called to create the MT940 file and save the content using the file transmission service

Furthermore, the ingress can be extended so long that the MT940 file is created.

What to take into consideration when extending the ingress:

  1. Make sure the MT940 record is created using the com.trimplement.wallet.server.payment.impl.storage.MT940FileDAO with the necessary information and make sure that you mark the record status as Created in order for this record to be picked for further processing.
  2. Save the content of the file in CW using fileTransmissionService as described above

MT940 Parser

The MT940 parser is the engine that reads the content of the MT940 and checks if the file is in the correct format. The parser is able to read a file containing several MT940 so long there is an empty space or hyphen (-) delimiter to mark the end of every MT940 in the file.

As the file content is stored using the file transmission service, the parser engine takes an object of com.trimplement.wallet.server.common.file.transmission.FileContentStream which contains the inputStream, the filename and the contentType, and returns a List of com.trimplement.wallet.server.payment.impl.mt940.MT940ParseResultSet which contain the necessary information extracted from the MT940 inputStream.

Below shows one properly formatted MT940 file and the other an incorrect MT940 file.

Correct MT940

:20:D180320103
:25:70011110/0000998036
:28C:00023/001
:60F:C180320EUR000000011954,00
:61:1803200115CR000000000200,00NTRF0000551979735530//035519797/003553
:86:166?00SEPA GUTSCHRIFT BANK?20SVWZ+NOTPROVIDED?21SVWZ+CX-2XC24A3J4K5R2349YYYCL-CX?30COBADEHD001?31DE95200411330361579600?32TOB
IAS TESTER?34166
:61:1803200115CR000000000150,00NTRF0000551979773460//035519797/007346
:86:166?00SEPA GUTSCHRIFT BANK?20EREF+CX-2XC24A3J4K5SJNG63JKAR-CX?30HELADEF1TSK?31DE915125000
00008417130?32THOMAS TESTER?34166
:61:1803200115CR000000000400,00NTRF0000551979759640//035519797/015964
:86:166?00SEPA GUTSCHRIFT BANK?20SVWZ+NOTPROVIDED?21SVWZ+CX-2XC24A3J4K5R5MDRFGN6Z-CX?30WELADED1WIE?31DE28384524900000141986?32SIM
ON TEST?34166
:62F:C180320EUR000000012704,00

The above example will be parsed successfully because it satisfies the MT940 specification. You can read more to understand this specification.  

Wrong MT940

:20:D180320103
:25:70011110/0000998036
:28C:00023/001
:60F:C180320EUR000000011954,00
:61:1803200115CR000000000200,00NTRF0000551979735530//035519797/003553
:86:166?00SEPA GUTSCHRIFT BANK?20SVWZ+NOTPROVIDED?21SVWZ+CX-2XC24A3J4K5R2349YYYCL-CX?30COBADEHD001?31DE95200411330361579600?32TOB
IAS TESTER?34166
:86:166?00SEPA GUTSCHRIFT BANK?20EREF+CX-2XC24A3J4K5SJNG63JKAR-CX?30HELADEF1TSK?31DE915125000
00008417130?32THOMAS TESTER?34166
:61:1803200115CR000000000400,00NTRF0000551979759640//035519797/015964
:86:166?00SEPA GUTSCHRIFT BANK?20SVWZ+NOTPROVIDED?21SVWZ+CX-2XC24A3J4K5R5MDRFGN6Z-CX?30WELADED1WIE?31DE28384524900000141986?32SIM
ON TEST?34166
:62F:C180320EUR000000012704,00

The above file will fail during parsing because it does not satisfy one of the rules of MT940 which is for every :86: tag line, there must be :61: tag line that precedes it.

MT940 Payment

The prerequisite of this part is that there should be some unprocessed MT940 file records whose status are marked as Created. The payment is the third part of this feature, it is where the actual payment is done using paymentService. And this is triggered by the MT940ParserProcessorJob.The current implementation support only a SEPA bank transfer hence before continuing with the payment, the implementation checks whether it is a SEPA bank transfer by checking that the MT940FileRecord;

  1. bankTransactionCode is not empty and is it is the same with the numeric value of MT940BusinessTransactionCode.SepaCreditTransferCredit enum (i.e. 166)
  2. debitCreditType is not empty and is of C (Credit) type.

If other type of payment need to be supported the implementation logic has to be added to com.trimplement.wallet.server.payment.impl.mt940.MT940FileRecordProcessorImpl#processFileRecord.

The process that happens during payment is as follows.

  • The business contract is used to get the subsidiary ID which in turn is used for the payment.
  • An external payment ID is generated using the concatenation of MT940 and currency, valuta and the payment record id in that order using ‘#’ as  the delimiter. Example of a typical externalPaymentId generated is MT940#EUR#140520#1.
  • The payment instrument (com.trimplement.wallet.server.payment.api.dom.PaymentInstrumentData)  is then created using the bankAccount.
  • Then paymentData (com.trimplement.wallet.server.payment.api.dom.PaymentData) is generated using the subsidiary Id and mt940 record.
  • The actual payment is done using the com.trimplement.wallet.server.payment.api.PaymentService#createExternalPayment service.

Payments reconciled from an MT940 account statement are deemed external payments as they may not have been triggered by a wallet-internal process. For example, the account may contain incoming payments for account top-up through bank transfer triggered from a 3rd party, like a consumer. Contrary to wallet-internal payments triggered through a payment gateway, which may go through several statuses, external payments are always considered successful. Once the external payment is created, the system's payment transaction listeners are invoked to account for the transaction.

MT940 Jobs

This module has three jobs:

  1. MT940FileReaderJob: As explained earlier, it helps to create an MT940 file record which then stores the content of the given file in a cloud bucket or computer file depending on the system configurations. This job is by default set to run every minute which can be modified based on the user's need using the property trimplement.wallet.server.payment.impl.mt940.readerRepeatInterval 
  1. MT940ParserProcessorJob: This job reads the content of an MT940 file which has been stored in a cloud or computer file and then parses it using MT940 parser. If it is successfully parsed, the MT940 file record is marked as “successfully parsed” and the appropriate MT940FileRecord database records are created. This job is by default set to run every minute which can be modified based on the user's need using the configuration trimplement.wallet.server.payment.impl.mt940.parserProcessorRepeatInterval in the property.
  1. MT940PaymentProcessorJob: This job retrieves the unprocessed MT940FileRecords that are due for payment from the database, and afterwards creates the actual transactions for them. This job is also configured by default to run every minute but this can be modified using the configuration trimplement.wallet.server.payment.impl.mt940.paymentProcessorRepeatInterval in the property

MT940 API

We have several APIs that are exposed in order to

  1. create an MT940 File
  2. get MT940 file details by unique ID
  3. get an MT940 files list based on some supplied criteria
  4. get MT940FileRecord details by unique ID
  5. get an MT940FileRecord list using the supplied criteria
  6. change the status of an MT940 File
  7. change the status of MT940FileRecord

You can refer to the Swagger for the appropriate APIs.

MT940 Configuration Summary

The summary below shows all the MT940 runtimes properties and their default value

Configure

Properties

Default value

Parser processor Job interval

trimplement.wallet.server.payment.impl.mt940.parserProcessorRepeatInterval

60000 (in milliseconds)

Payment processor Job interval

trimplement.wallet.server.payment.impl.mt940.paymentProcessorRepeatInterval

60000 (in milliseconds)

File Reader Job interval

trimplement.wallet.server.payment.impl.mt940.readerRepeatInterval

60000 (in milliseconds)

File Batch Size

trimplement.wallet.server.payment.impl.mt940.fileBatchSize

100

Base Directory

trimplement.wallet.server.payment.impl.mt940.baseDirectory

 /MT940/