We refreshed our doc site!

Bookmarked links may have changed

Read release notes

Web3 Services

Testing Guide

This guide helps developers test Circle’s Travel Rule APIs, designed to ensure compliance with the Travel Rule regulations. Below, you’ll find essential test cases to validate Travel Rule eligibility, required data, and the outcomes for different transaction flows.

API Endpoints for Testing

  • Eligibility Check: Verifies whether a transaction requires Travel Rule compliance.
  • Send PII: Sends the Travel Rule-compliant PII to the beneficiary VASP.
  • Receive PII: Retrieves received PII for inbound transfers.
  • Validity Check: Confirms the compliance of inbound PII.
  • Update Travel Rule Message: Updates the status of Travel Rule messages.

Note: For all test scenarios, use ETH-SEPOLIA on testnet.

Understanding Magic Values

Magic values are pre-configured test addresses that simulate various transaction outcomes. These values allow developers to test different conditions and responses without requiring actual VASP integration.

  • 0xd639717dec24f56770aad40ad5414f80fa7f8d2: Self-hosted wallet (Non-custodial wallet).
  • 0x774d7851bbda86ed5314823758baf3840166a9f5: Hosted wallet, VASP in the U.S.
  • 0x75658eea924fda66176a05ae7b328caccc907523: Hosted wallet, VASP in Singapore.

These addresses trigger specific API responses to help verify Travel Rule requirements, wallet types, and recommendations under different compliance scenarios.

Test Cases

1. Eligibility for Sending PII

1.1. Sending to a Self-hosted Wallet

Objective: Verify that the system blocks transactions to self-hosted wallets unless your customer has provided the wallet ownership proof.

Configuration:

  • Asset: ETH-SEPOLIA
  • Amount: 9.876 ETH
  • Destination Address: 0xd639717dec24f56770aad40ad5414f80fa7f8d2
  • Customer Jurisdiction: France (FR)

Request:

JSON
POST https://api.circle.com/v1/w3s/compliance/travelRule/eligibilityCheck
Authorization: Bearer <API_KEY>
{
  "transactionAsset": "ETH-SEPOLIA",
  "transactionAmount": "9876543210123456789",
  "destination": "0xd639717dec24f56770aad40ad5414f80fa7f8d2",
  "customerJurisdiction": "FR"
}

Expected Response: The API should recommend preventing the transaction, indicating that self-hosted wallets need ownership proof to achieve compliance. You can submit the evidence collected to the ownership proof API endpoint

Response

JSON
{
  "response": {
    "data": {
      "recommendation": "PREVENT_TRANSACTION",
      "reason": "NON_CUSTODIAL_WALLET",
      "beneficiaryAddressType": "UNKNOWN",
      "originatorVaspId": "originator-vasp-id",
      "matchedRules": []
    },
    "status": {
      "version": "1.0",
      "code": 0,
      "message": "Success"
    }
  }
}
1.1.1. Submit Ownership Proof for a self-hosted wallet

Objective: Verify that the system blocks transactions to self-hosted wallets due to unsupported compliance requirements.

Configuration:

  • Destination Address: 0xd639717dec24f56770aad40ad5414f80fa7f8d2
  • Customer Jurisdiction: France (FR)

Request:

JSON
POST https://api.circle.com/v1/w3s/compliance/travelRule/uploadownershipProof
Authorization: Bearer <API_KEY>
{
  "customerJurisdiction": "FR",
  "address": "0xd639717dec24f56770aad40ad5414f80fa7f8d2",
  "message": "I attest that this wallet is owned by John Doe [email protected]",
  "signature": "0x14f4b0527f06a380bdaccb5b36194c613c8b64859a6ac8c0b46f1489996e67734c85fd55e1ec0b7a2d14c1acfb811b86e4dffcd99d5e9932d1007534c1aa26421b",
  "proofType": "EIP_191"
}

Expected Response: The API should provide an ownership proof ID to indicate that your customer has successfully verified the ownership of the self-hosted wallet. You can store the ownership proof ID for future evidence. Future calls to the eligibility check API endpoint for the same address will acknowledge that the proof has already been validated, and the recommendation would be to allow the transaction to this address.

Response

JSON
{
  "response": {
    "data": {
      "proofId": "cadbbf87-344f-46d0-b05c-ef22d7ed1fbf"
    },
    "status": {
      "version": "1.0",
      "code": 0,
      "message": "Success"
    }
  }
}

1.2. Sending to a Hosted Wallet in the U.S

Objective: Confirm that transactions to compliant, hosted wallets in the U.S. proceed as expected under Travel Rule compliance.

Configuration:

  • Asset: ETH-SEPOLIA
  • Amount: 9.823 ETH
  • Destination Address: 0x774d7851bbda86ed5314823758baf3840166a9f5
  • Customer Jurisdiction: France (FR)

Request:

JSON
POST https://api.circle.com/v1/w3s/compliance/travelRule/eligibilityCheck
Authorization: Bearer <API_KEY>
{
  "transactionAsset": "ETH-SEPOLIA",
  "transactionAmount": "9823456789000000000",
  "destination": "0x774d7851bbda86ed5314823758baf3840166a9f5",
  "customerJurisdiction": "FR"
}

Expected Response: The API should return a recommendation to proceed, listing required PII data and identifying the wallet type and VASP details.

Response

JSON
{
  "response": {
    "data": {
      "recommendation": "PROCEED_WITH_TRANSACTION",
      "reason": "TRAVEL_RULE",
      "beneficiaryAddressType": "HOSTED",
      "beneficiaryVaspName": "UAT VASP US",
      "beneficiaryVaspId": "beneficiary-vasp-id",
      "requiredTravelRuleData": [
        "originatorName",
        "originatorGeographicAddress",
        "beneficiaryName",
        "originatorAccountNumber",
        "beneficiaryAccountNumber"
      ],
      "matchedRules": []
    },
    "status": {
      "version": "1.0",
      "code": 0,
      "message": "Success"
    }
  }
}

1.3. Sending to a Hosted Wallet in Singapore

Objective: Test a transaction to a hosted wallet in Singapore and verify required additional PII fields for compliance.

Configuration:

  • Asset: ETH-SEPOLIA
  • Amount: 0.005 ETH
  • Destination Address: 0x75658eea924fda66176a05ae7b328caccc907523
  • Customer Jurisdiction: France (FR)

Request:

JSON
POST https://api.circle.com/v1/w3s/compliance/travelRule/eligibilityCheck
Authorization: Bearer <API_KEY>
{
  "transactionAsset": "ETH-SEPOLIA",
  "transactionAmount": "5000",
  "destination": "0x75658eea924fda66176a05ae7b328caccc907523",
  "customerJurisdiction": "FR"
}

Expected Response: The response should indicate that the transaction can proceed, listing additional PII fields due to Singapore’s jurisdictional requirements.

Response

JSON
{
  "response": {
    "data": {
      "recommendation": "PROCEED_WITH_TRANSACTION",
      "reason": "TRAVEL_RULE",
      "beneficiaryAddressType": "HOSTED",
      "beneficiaryVaspName": "UAT VASP SG",
      "beneficiaryVaspId": "beneficiary-vasp-id",
      "requiredTravelRuleData": [
        "originatorName",
        "beneficiaryName",
        "originatorAccountNumber",
        "beneficiaryAccountNumber"
      ]
    },
    "status": {
      "version": "1.0",
      "code": 0,
      "message": "Success"
    }
  }
}

2. Sending PII

After confirming eligibility, use the Send PII endpoint to transfer the required PII to the beneficiary VASP.

Objective: Ensure PII data can be sent securely and validates all necessary fields.

Configuration:

  • Idempotency Key: Unique key for request retries
  • Asset: ETH-SEPOLIA
  • Transaction Amount: 9.576 ETH
  • Origin and Destination Addresses: Test values as per the eligibility response
  • Customer Jurisdiction: France (FR)

Request:

JSON
POST https://api.circle.com/v1/w3s/compliance/travelRule/sendPii
Authorization: Bearer <API_KEY>
{
  "idempotencyKey": "unique-key",
  "transactionAsset": "ETH-SEPOLIA",
  "transactionAmount": "9576574879897626508",
  "originatorVaspId": "originator-vasp-id",
  "beneficiaryVaspId": "beneficiary-vasp-id",
  "origin": "0x7a89424d980f1aff7fd4a239898e760eeb6aad7e",
  "destination": "0x75658eea924fda66176a05ae7b328caccc907523",
  "customerJurisdiction": "FR",
  "pii": {
    "originator": {
      "accountNumber": [
        "acc1234"
      ],
      "originatorPersons": [
        {
          "naturalPerson": {
            "name": [
              {
                "nameIdentifier": [
                  {
                    "primaryIdentifier": "Harry",
                    "secondaryIdentifier": "Potter"
                  }
                ]
              }
            ]
          }
        }
      ]
    },
    "beneficiary": {
      "accountNumber": [
        "ben1234"
      ],
      "beneficiaryPersons": [
        {
          "naturalPerson": {
            "name": [
              {
                "nameIdentifier": [
                  {
                    "primaryIdentifier": "Ron",
                    "secondaryIdentifier": "Weasley"
                  }
                ]
              }
            ]
          }
        }
      ]
    }
  }
}

Expected Response:

Response

JSON
{
  "response": {
    "data": {
      "travelRuleId": "unique-travel-rule-id",
      "travelRuleStatus": "CLAIMED",
      "beneficiaryVaspId": "beneficiary-vasp-id"
    },
    "status": {
      "version": "1.0",
      "code": 0,
      "message": "Success"
    }
  }
}

3. Receiving PII

Use the receivePii endpoint to validate the retrieval of inbound PII data transferred by a sending VASP. This endpoint helps confirm that the Travel Rule message has been correctly received and includes all necessary information for compliance checks.

Objective: Confirm the retrieval of PII data for an inbound transaction, validating that required information from the originator VASP is available for compliance purposes.

Configuration:

  • Asset: ETH-SEPOLIA
  • Travel Rule ID: Unique ID of the Travel Rule transfer.
  • Transaction ID (optional): Blockchain transaction UUID (alternative to travelRuleId).
  • Customer Jurisdiction: Jurisdiction of the receiving VASP.

Request:

Here’s a sample API request to retrieve the Travel Rule-compliant PII for an inbound transaction.

JSON
POST https://api.circle.com/v1/w3s/compliance/travelRule/receivePii
Authorization: Bearer <API_KEY>
{
  "travelRuleId": "unique-travel-rule-id",
  "customerJurisdiction": "US"
}

Expected Response:

The API response should provide a detailed view of the PII, including fields required under IVMS101 standards (name, address, account number, etc.). The response also includes information about the transaction’s origin and destination, VASP IDs, transaction status, and timestamps.

Response

JSON
{
  "response": {
    "data": {
      "id": "unique-travel-rule-id",
      "status": "CLAIMED",
      "token": "ETH_SEPOLIA",
      "transactionType": "INBOUND",
      "amount": "9.576574879897626508",
      "originatorVaspId": "originator-vasp-id",
      "beneficiaryVaspId": "beneficiary-vasp-id",
      "sourceAddress": "0x7a89424d980f1aff7fd4a239898e760eeb6aad7e",
      "destinationAddress": "0x75658eea924fda66176a05ae7b328caccc907523",
      "createDate": "2024-06-24T23:23:10.285Z",
      "updateDate": "2024-06-24T23:23:13.280Z",
      "ivms101": {
        "originator": {
          "originatorPersons": [
            {
              "naturalPerson": {
                "name": {
                  "nameIdentifier": [
                    {
                      "primaryIdentifier": "Harry",
                      "secondaryIdentifier": "Potter"
                    }
                  ]
                },
                "geographicAddress": [
                  {
                    "streetName": "main st",
                    "buildingNumber": "123",
                    "buildingName": "11A",
                    "townName": "NYC",
                    "countrySubDivision": "NY",
                    "country": "US",
                    "postCode": "12345"
                  }
                ],
                "dateAndPlaceOfBirth": {
                  "dateOfBirth": "010192",
                  "placeOfBirth": "NYC"
                }
              }
            }
          ],
          "accountNumber": [
            "acc1234"
          ]
        },
        "beneficiary": {
          "beneficiaryPersons": [
            {
              "naturalPerson": {
                "name": {
                  "nameIdentifier": [
                    {
                      "primaryIdentifier": "Ron",
                      "secondaryIdentifier": "Weasley"
                    }
                  ]
                },
                "geographicAddress": [
                  {
                    "streetName": "park",
                    "buildingNumber": "789",
                    "buildingName": "12A",
                    "townName": "SG",
                    "countrySubDivision": "SG",
                    "country": "SG",
                    "postCode": "12345"
                  }
                ]
              }
            }
          ],
          "accountNumber": [
            "ben1234"
          ]
        }
      }
    },
    "status": {
      "version": "1.0",
      "code": 0,
      "message": "Success"
    }
  }
}

This Receive PII test confirms:

  • PII Data Retrieval: All required fields under IVMS101 are included, such as names, addresses, and account numbers for both the originator and beneficiary.
  • Transaction Status: The current status of the Travel Rule transfer, ensuring compliance.
  • Details Verification: Information about VASP IDs, source and destination addresses, and transaction metadata (timestamps, amounts).

The receivePii endpoint provides critical information for validating compliance of inbound transactions in alignment with Travel Rule standards.

4. Eligibility for Receiving PII

Verifies that received PII data complies with jurisdiction-specific requirements.

Objective: Validate that received PII for an inbound transaction meets Travel Rule requirements for the customer’s jurisdiction.

Configuration:

  • Jurisdiction: Singapore (SG)
  • Travel Rule ID: Use travelRuleId from the previous response

Request:

JSON
POST https://api.circle.com/v1/w3s/compliance/travelRule/validityCheck
Authorization: Bearer <API_KEY>
{
  "customerJurisdiction": "SG",
  "travelRuleId": "unique-travel-rule-id"
}

Expected Response: The API should return a recommendation to prevent or allow the transaction based on configured compliance rules.

Response

JSON
{
  "response": {
    "data": {
      "recommendation": "PREVENT_TRANSACTION",
      "reason": "FAILED_RULES_EVALUATION",
      "originatorAddressType": "HOSTED",
      "originatorVaspName": "UAT VASP US",
      "originatorVaspId": "originator-vasp-id",
      "matchedRules": [
        {
          "precedence": -2,
          "name": "Rule 2: Block transaction to blocklisted jurisdiction."
        }
      ]
    },
    "status": {
      "version": "1.0",
      "code": 0,
      "message": "Success"
    }
  }
}

5. Updating Travel Rule Status

Update the status of an existing Travel Rule message as accepted or declined.

Objective: Ensure that developers can update Travel Rule message status.

Configuration:

  • Idempotency Key: Unique key for the request
  • Status: Set to "ACCEPTED" or "DECLINED"

Request:

JSON
PUT https://api.circle.com/v1/w3s/compliance/travelRule/unique-travel-rule-id
Authorization: Bearer <API_KEY>
{
  "idempotencyKey": "unique-key",
  "status": "ACCEPTED"
}

Expected Response:

JSON
{
  "response": {
    "data": {
      "status": "ACCEPTED",
      "travelRuleId": "unique-travel-rule-id"
    },
    "status": {
      "version": "1.0",
      "code": 0,
      "message": "Success"
    }
  }
}

Summary

This guide enables developers to test the Compliance Engine’s Travel Rule feature and validate that transactions meet jurisdictional Travel Rule requirements, ensuring compliance for all transaction types.

Did this page help you?
© 2023-2024 Circle Technology Services, LLC. All rights reserved.