Skip to main content
3D Secure (3DS) is an authentication protocol used by Visa, Mastercard, and other networks to verify the cardholder during online card payments. When a merchant requests a 3DS check, the issuer must confirm the person making the purchase is really the cardholder. This protects against card-not-present fraud and is required by regulators like PSD2 in many regions. Reap handles 3DS for you. The only choice you need to make is how the cardholder proves their identity when a challenge is raised.

Verification methods

Each card carries a 3dsChallengeMethod setting that determines how challenges are resolved. You can switch the method per card at any time.
MethodWho verifies the cardholderIntegration work
SMS (default)Reap sends a one-time code to the cardholder’s phone and verifies the response.None.
WEBHOOKReap forwards the challenge to your backend. You authenticate the cardholder in your app (biometric, in-app PIN, push approval) and call back.Subscribe to a webhook and respond within 5 minutes.
Use SMS if you want zero integration. Use WEBHOOK if you want to drive the verification step yourself, typically because your app already has a strong, in-app authentication flow you would rather reuse.

Configuring the method

Set 3dsChallengeMethod when creating a card. If omitted, the card defaults to SMS. Switch later by calling Update 3DS challenge method. The change takes effect for subsequent transactions. The current setting is exposed on the card resource as 3dsChallengeMethod.

SMS flow

When a merchant triggers a 3DS check:
  1. The card network requests authentication from Reap.
  2. Reap sends a one-time code to the cardholder’s phone number on file.
  3. The cardholder enters the code on the merchant’s 3DS page.
  4. Reap verifies the code and confirms (or denies) the authentication with the network.
You receive a CARD_TRANSACTION_CREATED webhook for the resulting authorization, with channel: ECOMMERCE. There are no extra integration steps.
The phone number used for SMS comes from the user record. Keep it up to date so challenges reach the cardholder. A wrong or stale number means the cardholder cannot complete the OTP step and the transaction is declined.

Webhook flow

Use the WEBHOOK method when you want to authenticate the cardholder in your own app instead of relying on SMS OTP.
1

Subscribe to the webhook

Listen for CARD_3DS_CHALLENGE_CREATED. The payload includes the challenge ID, card ID, merchant name and country, transaction amount and currency, and an expiresAt timestamp.
2

Authenticate the cardholder

Show the merchant name and amount in your app and verify the cardholder using your preferred method (biometric, PIN, push approval, etc.). Surface the time remaining so the cardholder knows the window is finite.
3

Respond to the challenge

Call Respond to 3DS challenge with approve: true to approve, or approve: false to reject. You must respond within 5 minutes of the challenge being created. Missing the window expires the challenge and the transaction is declined.
4

Receive the transaction

The card network completes (or declines) the transaction based on your response. You receive a CARD_TRANSACTION_CREATED webhook for the authorization.

Challenge status

A challenge moves through one of four states. Use Get 3DS challenge to fetch the latest state by ID at any time.
StatusMeaning
PENDINGAwaiting your response
APPROVEDYou approved the challenge
REJECTEDYou rejected the challenge
EXPIREDNo response was received within the 5-minute window. The transaction was declined

Best practices

  • Show context to the cardholder. Surface the merchant name, country, and amount from the challenge payload. This helps the cardholder spot fraudulent purchases before approving.
  • Respect the 5-minute window. Treat expiresAt as authoritative. If your authentication step might block (push notification, deep link, app cold start), make sure the cardholder can complete it well before the timeout.
  • Start with SMS. Cards default to SMS, so 3DS works out of the box. Switch individual cards to WEBHOOK once your in-app authentication flow is ready.
  • Handle declines. A rejected or expired challenge causes the transaction to be declined. Tell the cardholder so they can retry the purchase if needed.