DFNS integration
Connect your DFNS workspace with Sumsub to exchange Travel Rule data for your transfers.
DFNS provides a wallets-as-a-service infrastructure with secure key management for digital assets.
Use the DFNS integration to exchange Travel Rule data with counterparty VASPs for transfers that you make through DFNS. DFNS handles the transfers, and Sumsub handles the Travel Rule data exchange.
Personal data stays end-to-end encrypted between you and Sumsub. You encrypt the IVMS 101 payload before you pass it to DFNS, and only Sumsub can decrypt it. DFNS forwards the encrypted payload but has no access to its content.
Before you start, make sure that:
- Travel Rule is enabled for your Sumsub account.
- Your DFNS workspace has Travel Rule enabled. For details, contact DFNS or see the DFNS documentation.
- You have the following permissions in the Sumsub Dashboard:
- Manage company settings: to connect DFNS on the DFNS card in Marketplace.
- Manage TM rules: to install the Travel Rule rules in the Rules library.
How DFNS integration works
Three parties take part in each transfer. You prepare the Travel Rule data, DFNS carries it together with the transfer, and Sumsub runs the Travel Rule exchange with the counterparty VASP. DFNS then uses the result to decide whether the transfer can proceed.
| Party | Responsibility |
|---|---|
| You | Collect the originator and beneficiary data, encrypt it, and attach it to the transfer in DFNS. |
| DFNS | Forwards the transfer details and the encrypted payload to Sumsub, and applies the Travel Rule result to the transfer according to your DFNS policies. |
| Sumsub | Decrypts the payload, identifies the counterparty VASP, runs the Travel Rule exchange and your Travel Rule rules, and returns the result. |
Outbound flow
The outbound flow applies when your customer sends a transfer from a DFNS wallet. You provide the Travel Rule data for the transfer, and Sumsub delivers it to the beneficiary VASP.
The outbound flow includes the following steps:
- You initiate a transfer in DFNS and attach the encrypted IVMS 101 payload.
- DFNS creates a Travel Rule message (TRM) in Sumsub.
- Sumsub identifies the beneficiary VASP and exchanges Travel Rule data with it.
- Sumsub returns the TRM status. DFNS applies it to the transfer according to your DFNS policies.
You can create the TRM before the transfer is broadcast, or after it is settled on-chain.
Inbound flow
The inbound flow applies when your customer receives a transfer to a DFNS wallet. You provide the beneficiary data, and Sumsub checks the transfer against your Travel Rule rules.
The inbound flow includes the following steps:
- You receive a transfer in DFNS.
- You provide the beneficiary data for the transfer, encrypted the same way as for outbound transfers.
- DFNS creates a TRM for the incoming transfer in Sumsub.
- Sumsub runs the Travel Rule exchange and your rules for the incoming transfer, and returns the result.
Respond to incoming Travel Rule requests
When a counterparty VASP sends a Travel Rule request that requires your action, the request is surfaced through DFNS. Respond to it as described in the DFNS documentation.
Get started with DFNS integration
To enable the integration, connect DFNS in the Sumsub Dashboard, set up Sumsub in DFNS, and configure your Travel Rule settings. You set this up once for each environment: live and Sandbox.
Step 1: Connect DFNS in the Sumsub Dashboard
In the Sumsub Dashboard, you get the credentials for DFNS and set up the keys that protect personal data.
- Open the Marketplace section. On the DFNS card, click Settings.
- In the Connect DFNS section, click Generate app token. Copy the app token and the secret key, and store them securely. You will not be able to view them again. You use them in Step 2.
- In the PII encryption keys section, set up your key pair. You sign the payloads that you send to Sumsub with the private key. Sumsub uses the public key to verify your signature and to encrypt the data that it returns to you. Choose one option:
- Generate in Sumsub. Select Generate key pair. Copy the public key, the private key, and the issuer, and store them securely. You will not be able to view the private key again. Sumsub keeps only the public key.
- Use your own public key. Enter your public key in JWK format and the public key issuer, and click Save keys.
- In the PII encryption keys section, copy the Sumsub public key. You use it to encrypt the data that you send to Sumsub. The
kidvalue in this key is the key ID of the Sumsub public key.
Leave the Travel Rule status webhook section empty for now. You set it up in the next step, after you get the webhook URL from DFNS.
Note
- Sumsub saves the app token and the generated key pair as soon as you generate them. You click Save keys only if you use your own public key. The Sumsub public key appears after you generate the app token.
- If you set up the integration before, the buttons are named Regenerate app token and Regenerate key pair. A new app token replaces the previous one, so update it in DFNS. If you replace your public key, Sumsub continues to accept payloads signed with the previous key, so you can rotate keys without downtime.
TipIf you have questions while you set up this step, click the Summy AI Copilot icon in the upper-right corner of the settings panel and start the conversation. For more information about Summy AI Copilot, refer to this article.
Step 2: Connect Sumsub in DFNS
In DFNS, you add the Sumsub credentials and get the webhook URL for status updates.
- Contact your DFNS representative to enable Travel Rule in DFNS and the Sumsub integration for your organization.
- In DFNS, set up Sumsub as your Travel Rule provider. Use the app token and the secret key from Step 1. For details, see the DFNS documentation.
To receive Travel Rule status updates in DFNS without polling, set up the status webhook. Sumsub sends updates for all Travel Rule transactions, incoming and outgoing.
- In your DFNS dashboard, copy the Travel Rule webhook URL.
- Open the Marketplace section. On the DFNS card, click Settings.
- In the Travel Rule status webhook section, paste the URL in Webhook URL, and click Save webhook URL.
- Click Generate webhook secret. Copy the secret and add it to the Sumsub integration settings in DFNS, where you added the app token and the secret key. DFNS uses it to verify the webhook signatures. You will not be able to view the secret again.
NoteSave webhook URL stays inactive until you enter a URL in the correct format: https://api.dfns.io/v2/policies/webhooks/travel-rule/sumsub/
Step 3: Configure Travel Rule settings and rules
- In the Sumsub Dashboard, go to Transactions and travel rule → Rules manager → Rules library, and open the Travel Rule tab.
- For each use case that applies to you, click the Install button on the right of the use case name, and confirm the installation. If the rules depend on other rules, these rules are installed too.
- Go to Rules manager → Installed rules, and make sure that the Travel Rule rules are active, not in Test mode. Rules in Test mode do not affect the transaction status.
- Go to Transactions and travel rule → Settings → Travel rule. Select the originator and beneficiary fields to share with counterparty VASPs, and set the confirmation timeout and the other settings that you need. For details, see the Integration settings section.
There are no separate Travel Rule settings for DFNS. Your Travel Rule settings and rules apply to all Travel Rule transfers, including the transfers that you make through DFNS.
Step 4: Encrypt data
The Travel Rule data is an IVMS 101 payload, signed with your private key and encrypted with the Sumsub public key:
IVMS 101 JSON → JWS (signed with your private key) → JWE (encrypted with the Sumsub public key)
Prepare the IVMS 101 payload
Use the IVMS 101.2023 format. The payload must meet these requirements:
Important
- Use the IVMS 101.2023 field names:
originatorPerson,beneficiaryPerson, andnaturalPersonNameIdentifierType. Sumsub ignores unknown fields, so a payload with IVMS 101.2020 field names arrives empty.- Set
payloadMetadata.payloadVersionto 101.2023.- Set
customerIdentificationfor your own customer: the originator for outbound transfers, and the beneficiary for inbound transfers. Sumsub uses it to link the transfer to the applicant.
Example of an IVMS 101 payload for an outbound transfer:
{
"Originator": {
"originatorPerson": [
{
"naturalPerson": {
"name": {
"nameIdentifier": [
{
"primaryIdentifier": "Doe",
"secondaryIdentifier": "John",
"naturalPersonNameIdentifierType": "LEGL"
}
]
},
"customerIdentification": "customer-123"
}
}
]
},
"Beneficiary": {
"beneficiaryPerson": [
{
"naturalPerson": {
"name": {
"nameIdentifier": [
{
"primaryIdentifier": "Smith",
"secondaryIdentifier": "Jane",
"naturalPersonNameIdentifierType": "LEGL"
}
]
}
}
}
]
},
"payloadMetadata": {
"payloadVersion": "101.2023"
}
}Sign the payload (JWS)
Create a signed JWT with your private key.
Field |
Value |
|---|---|
|
|
|
|
|
The |
Claim |
Value |
|---|---|
|
The issuer of your key from Step 1: the Issuer value that you copied when you generated the key pair, or the Public key issuer that you entered with your own key. |
|
Issue time, in seconds. It must not be more than 60 seconds in the future. |
|
Expiration time, in seconds. |
|
Required. A unique ID for the token. |
|
The IVMS 101 JSON, encoded as base64url without padding. |
Encrypt the signed payload (JWE)
Encrypt the signed JWT with the Sumsub public key.
| Field | Value |
|---|---|
alg | RSA-OAEP-256 |
enc | A256GCM |
kid | The kid value of the Sumsub public key that you copied in Step 1. |
cty | JWT |
Build the payload object
Pass the encrypted payload to DFNS in this object:
{
"version": "IVMS101.2023",
"data": "<JWE compact serialization>",
"filledFields": [
"Originator.originatorPerson[].naturalPerson.customerIdentification",
"...",
"payloadMetadata.payloadVersion"
]
}In filledFields, list the path of every field that has a value in the IVMS 101 payload. Separate the path parts with dots, and add [] after the name of an array. For the payload example above, filledFields contains these paths:
Originator.originatorPerson[].naturalPerson.customerIdentificationOriginator.originatorPerson[].naturalPerson.name.nameIdentifier[].primaryIdentifierOriginator.originatorPerson[].naturalPerson.name.nameIdentifier[].secondaryIdentifierOriginator.originatorPerson[].naturalPerson.name.nameIdentifier[].naturalPersonNameIdentifierTypeBeneficiary.beneficiaryPerson[].naturalPerson.name.nameIdentifier[].primaryIdentifierBeneficiary.beneficiaryPerson[].naturalPerson.name.nameIdentifier[].secondaryIdentifierBeneficiary.beneficiaryPerson[].naturalPerson.name.nameIdentifier[].naturalPersonNameIdentifierTypepayloadMetadata.payloadVersion
Decrypt data from Sumsub
The Travel Rule data that Sumsub returns, for example, the beneficiary data on an inbound transfer, is encrypted the same way: signed with the Sumsub private key and encrypted with your public key. To read it, do the following:
- Decrypt the JWE with your private key.
- Verify the JWS signature with the Sumsub public key.
- Decode the data claim from base64url to get the IVMS 101 JSON.
Step 5: Make transfer with Travel Rule data
Initiate the transfer through the DFNS Transfer Asset API, and add the travelRule object to the request. Travel Rule applies only to transfers made through the API. It does not apply to transfers from the DFNS dashboard or to transfers without the travelRule object.
To make a transfer with Travel Rule data:
- Create the
travelRuleobject:
| Field | Value |
|---|---|
kind | Sumsub |
ivms101 | The payload object from Step 4. |
beneficiaryVaspId | The Sumsub ID of the beneficiary VASP. Use it for a transfer to a hosted wallet. |
beneficiaryWalletType | unhosted. Use it for a transfer to a self-hosted wallet. |
- Set exactly one of
beneficiaryVaspIdandbeneficiaryWalletType. DFNS rejects a request with both fields or with neither of them. - Add the
travelRuleobject to the Transfer Asset request, and send the request:
{
"kind": "Native",
"to": "0x1234567890abcdef1234567890abcdef12345678",
"amount": "1000000000000000000",
"travelRule": {
"kind": "Sumsub",
"ivms101": {
"version": "IVMS101.2023",
"data": "<JWE compact serialization>",
"filledFields": ["..."]
},
"beneficiaryVaspId": "<Sumsub VASP ID>"
}
}DFNS forwards the Travel Rule data to Sumsub together with the transfer details. For details, see the DFNS documentation.
Step 6: View results
Sumsub returns the TRM status to DFNS. The status reflects the final decision on the transaction in Sumsub, after the Travel Rule exchange and your Travel Rule rules.
| Status | Description |
|---|---|
PENDING | The TRM is being processed, is waiting for the counterparty VASP, or is under manual review. The transfer must stay on hold. |
ACCEPTED | The Travel Rule exchange completed successfully. The transfer can proceed. |
REJECTED | The Travel Rule exchange was rejected. The transfer must not proceed. |
DFNS applies the status to the transfer according to your DFNS policies. You can also see each Travel Rule transaction and its details in the Sumsub Dashboard. For more information, refer to this article.
Troubleshooting
Sumsub returns these errors when it cannot process the Travel Rule data or the integration settings. Find your error in the table to see the cause and the fix.
| Error | Cause and fix |
|---|---|
Failed to decrypt IVMS101 payload | Sumsub cannot decrypt the payload or verify its signature. Check that the JWS kid matches the public key that you set up in Step 1, that you encrypt with the current Sumsub public key, and that iss matches the issuer of your key. Live and sandbox environments use separate keys. |
Failed to deserialize IVMS101 data from JSON | The payload is decrypted, but its content is not valid IVMS 101 JSON. Check the JSON that you put in the data claim, and check that you encode it as base64url without padding. |
Invalid IVMS version, IVMS101.2023 required | payloadMetadata.payloadVersion is missing or is not 101.2023. |
IVMS101 Originator customerIdentification is required: it is used as the applicant identifier for outbound transfers | The originator has no customerIdentification, or the payload uses IVMS 101.2020 field names and arrives empty. Use the IVMS 101.2023 field names. For inbound transfers, the same error refers to the beneficiary. |
VASP not found | Sumsub has no VASP with the beneficiaryVaspId that you set. Check the VASP ID. |
Beneficiary VASP ID is not allowed for unhosted wallets | The request has both beneficiaryVaspId and beneficiaryWalletType set to unhosted. Set only one of them. |
Malformed data provided in the request | A field has an invalid format. For example, a VASP ID must be a 24-character hexadecimal string. |
Use the full webhook URL from DFNS | The webhook URL in the Sumsub Dashboard has the wrong format. Copy the full Travel Rule webhook URL from DFNS. It looks like https://api.dfns.io/v2/policies/webhooks/travel-rule/sumsub/<organization ID>. |
Updated about 2 hours ago