Skip to content

Additional Steps

Collect Source of Funds / Source of Wealth documents and guided selfie evidence

Additional steps let you collect supporting evidence in the same customer journey as wallet ownership verification. CryptoSwift currently supports:

  • SOURCE_OF_FUNDS_WEALTH - a combined Source of Funds / Source of Wealth document request that requires manual review.
  • SELFIE - a guided selfie and liveness check that can be confirmed automatically when backend analysis passes, or left for manual review.

Each additional step has its own status. The wallet ownership result remains separate, so your application should evaluate the top-level wallet status and every required additional-step status before releasing funds or completing a withdrawal.

For a dashboard and customer-facing walkthrough, see Additional steps workflow.

Create a verification with additional steps

Add additionalSteps when you create the wallet verification:

curl --location 'https://api-dev.cryptoswift.eu/wallet-verification' \
--header 'X-Api-Key: $API_KEY' \
--header 'Content-Type: application/json' \
--data '{
  "asset": "ETH",
  "blockchain": "Ethereum",
  "address": "0x32Be343B94f860124dC4fEe278FDCBD38C102D88",
  "metadata": "customer-123",
  "allowedFlows": ["SIGNATURE_PROOF", "VISUAL_PROOF"],
  "origin": "https://app.example.com",
  "additionalSteps": [
    {
      "type": "SOURCE_OF_FUNDS_WEALTH",
      "settings": {
        "customerMessage": "Please provide bank statements covering the last three months."
      }
    },
    {
      "type": "SELFIE",
      "settings": { "autoConfirm": true }
    }
  ]
}'
Always double-check you are using the correct environment when integrating. Using the wrong base URL or API key will result in authentication errors.

Step types must be unique. Do not provide a step status, uploaded file paths, capture metadata, or selfie actions in the create request. CryptoSwift initializes each step as PENDING and generates the selfie action sequence on the server.

Additional-step settings are specific to their step type:

StepSettingDefaultBehavior
SOURCE_OF_FUNDS_WEALTHcustomerMessageOmittedOptional VASP-defined text, up to 2,000 characters, displayed in the widget before the document upload requirements.
SELFIEautoConfirmfalse through the APIWhen true, a passing backend liveness analysis changes the Selfie step to VERIFIED. When false, the evidence remains available for manual review.

In the Client Dashboard, selecting Source of Funds / Wealth reveals the customer-message field and selecting Selfie reveals Automatically approve the selfie. Automatic approval is enabled by default in the dashboard and can be turned off before creating the verification.

Example response excerpt:

{
  "id": "9f3dc458-a2be-4a34-bcb7-f1f677a0864c",
  "token": "eyJhbGciOiJIUzI1NiIs...",
  "url": "https://wallet-dev.cryptoswift.eu/?token=eyJhbGciOiJIUzI1NiIs...",
  "status": "PENDING",
  "additionalSteps": [
    {
      "type": "SOURCE_OF_FUNDS_WEALTH",
      "status": "PENDING",
      "settings": {
        "customerMessage": "Please provide bank statements covering the last three months."
      }
    },
    {
      "type": "SELFIE",
      "status": "PENDING",
      "settings": {
        "actions": ["TURN_LEFT", "BLINK", "LOOK_UP"],
        "autoConfirm": true
      }
    }
  ],
  "createdAt": "2026-09-11T09:00:00.000Z",
  "expiresAt": "2026-09-13T09:00:00.000Z"
}

For each Selfie step, CryptoSwift selects three distinct actions from TURN_LEFT, TURN_RIGHT, LOOK_UP, LOOK_DOWN, and BLINK. Your UI must use the returned sequence in order. Do not generate or replace these actions on the client.

Statuses

Every item in additionalSteps has an independent lifecycle:

StatusMeaning
PENDINGThe customer still needs to submit the requested evidence.
ACTION_REQUIREDEvidence was submitted and is available for review. For Selfie, backend analysis may also be running or may have completed without automatic confirmation.
VERIFIEDThe evidence was accepted manually, or a Selfie analysis passed while autoConfirm was enabled.
DECLINEDA reviewer rejected the submitted evidence.

Selfie analysis is returned separately in additionalStepResults.SELFIE:

Analysis statusMeaning
PENDINGAnalysis was scheduled.
PROCESSINGThe liveness service is analysing the submitted evidence.
PASSEDThe expected action sequence and liveness checks passed.
FAILEDThe evidence was processed but did not pass one or more checks. Review failureReasons and checks.
ERRORAnalysis could not be completed. Review errorCode and use your manual-review or retry policy.

The top-level status remains the wallet ownership result. For example, a wallet verification can have status: "VERIFIED", a Selfie step with status: "VERIFIED", and a Source of Funds / Source of Wealth step with status: "ACTION_REQUIRED".

Widget flow

The Wallet Verification Widget handles requested additional steps automatically:

  1. The customer completes wallet ownership verification using one of the allowed methods.
  2. The widget opens each additional step whose status is PENDING.
  3. For Source of Funds / Source of Wealth, the customer uploads documents. Submission changes the step to ACTION_REQUIRED for manual review.
  4. For Selfie, the widget asks for camera access and guides the customer through the server-selected actions. It captures an image for each action, a final selfie, and a short video without audio, then submits the evidence automatically.
  5. When Selfie automatic confirmation is enabled, the widget checks the analysis status and continues when processing finishes. A passing result verifies the step automatically. A failed analysis or processing error leaves the evidence for review.
  6. When no customer action remains, the widget shows either the standard success screen or a submitted-for-review screen, depending on the remaining step statuses.

If Selfie is the only additional step and automatic confirmation succeeds, the customer reaches the standard successful verification screen without VASP review. If automatic confirmation is disabled, or another step still requires review, the customer is told that the submitted evidence is under review.

Submit Source of Funds / Source of Wealth evidence

For a direct API integration, submit one or more files as repeated files fields in multipart/form-data:

POST {{apiBaseUrl}}/wallet-verification/{id}/additional-steps/SOURCE_OF_FUNDS_WEALTH
curl --location 'https://api-dev.cryptoswift.eu/wallet-verification/9f3dc458-a2be-4a34-bcb7-f1f677a0864c/additional-steps/SOURCE_OF_FUNDS_WEALTH' \
--header 'X-Api-Key: $API_KEY' \
--form 'files=@source-of-funds.pdf' \
--form 'files=@bank-statement.pdf'

SOURCE_OF_FUNDS_WEALTH accepts up to 10 documents of up to 50 MB each. Supported formats are pdf, doc, docx, xls, xlsx, ppt, pptx, txt, rtf, and csv.

The step must be PENDING. A successful submission changes it to ACTION_REQUIRED. Source of Funds / Source of Wealth evidence always requires a reviewer to accept or decline it.

Submit Selfie evidence

The widget is the recommended way to perform guided capture. If you build a custom UI, read the server-generated additionalSteps[].settings.actions, perform those actions in order, and submit the captured files with JSON-encoded metadata:

POST {{apiBaseUrl}}/wallet-verification/{id}/additional-steps/SELFIE
curl --location 'https://api-dev.cryptoswift.eu/wallet-verification/9f3dc458-a2be-4a34-bcb7-f1f677a0864c/additional-steps/SELFIE' \
--header 'X-Api-Key: $API_KEY' \
--form 'files=@turn-left.jpg' \
--form 'files=@blink.jpg' \
--form 'files=@look-up.jpg' \
--form 'files=@selfie.jpg' \
--form 'files=@liveness.webm' \
--form 'metadata={"captureStatus":"SUCCESS","libraryVersion":"1.0.0","startedAt":"2026-09-11T09:00:00Z","completedAt":"2026-09-11T09:00:10Z","actionResults":[{"action":"TURN_LEFT","status":"SUCCESS"},{"action":"BLINK","status":"SUCCESS"},{"action":"LOOK_UP","status":"SUCCESS"}]}'

A successful capture requires all three returned actions in the same order, with each action result set to SUCCESS. The endpoint accepts up to four images of up to 5 MB each and one video of up to 50 MB. A successful submission changes the step to ACTION_REQUIRED, creates additionalStepResults.SELFIE with status: "PENDING", and schedules backend analysis.

The capture metadata records what the client observed. Backend liveness analysis makes the authoritative liveness decision; the Selfie step does not perform identity matching against an identity document.

Read the wallet verification again to obtain the latest analysis:

GET {{apiBaseUrl}}/wallet-verification/{id}

When waiting synchronously in your own UI, poll at a modest interval until additionalStepResults.SELFIE.status is PASSED, FAILED, or ERROR. Continue to process configured webhook notifications for customer submissions and reviewer updates.

Retrieve submitted files

Retrieve short-lived signed URLs for either additional step:

GET {{apiBaseUrl}}/wallet-verification/{id}/additional-steps/{type}/signed-urls
curl --location 'https://api-dev.cryptoswift.eu/wallet-verification/9f3dc458-a2be-4a34-bcb7-f1f677a0864c/additional-steps/SELFIE/signed-urls' \
--header 'X-Api-Key: $API_KEY'

Example response:

{
  "urls": [
    "https://storage.googleapis.com/example/signed-evidence-url"
  ]
}

Raw storage object paths are not returned. In the Client Dashboard, images appear as labelled thumbnails and the liveness video can be opened and played. Selfie action images follow the server-generated sequence, followed by the final selfie and liveness video.

Manual review

The Client Dashboard shows wallet ownership, Source of Funds / Source of Wealth, and Selfie as separate checks. Reviewers can inspect:

  • uploaded Source of Funds / Source of Wealth documents
  • the Selfie liveness result, checks, and failure details
  • labelled action images, final selfie, and liveness video
  • capture and verification metadata

To accept or decline an additional step through the API:

PATCH {{apiBaseUrl}}/wallet-verification/{id}/additional-steps/{type}

Use one of these decision bodies:

{ "status": "VERIFIED" }
{ "status": "DECLINED" }

The endpoint returns the updated wallet verification. Changing an additional-step status does not change the top-level wallet ownership status.

Webhooks

Customer evidence submissions and reviewer status decisions emit wallet-verification notifications when a webhook URL is configured in CryptoSwift settings. Treat a notification as a signal to retrieve the latest wallet verification, then evaluate both the top-level status and additionalSteps.

See Webhooks and testing webhook notifications.

Next steps