IDP Sandbox

AI Tools

The Yoti Identity Profiles (IDP) Sandbox is an isolated testing environment for validating your integration with mock data and simulated verification outcomes.

What you can do

  • Test end-to-end flows without real user data

  • Simulate different verification outcomes (approvals, rejections, extractions)

  • Use standard Yoti backed SDKs (no separate sandbox SDK)

  • Manually test using the user view, or automate testing (via built-in agent) by bypassing the user view.

Key differences

Sandbox uses the same SDKs as production but requires:

  • Sandbox URL: https://api.yoti.com/sandbox/idverify/v1

  • Sandbox keys from Yoti Hub

  • Predefined successful responses by default

  • Optional response configuration


Before you start

Ensure you have submitted your Yoti Hub organisation for verification and have generated sandbox keys.

Sandbox keys


Install the SDK

Install the Yoti SDK using your language's package manager. The same SDK is used for both production and sandbox environments.

npm install -S -E yoti
// If you are using Maven, add the following dependency: <dependency> <groupId>com.yoti</groupId> <artifactId>yoti-sdk-api</artifactId> <version>3.12.0</version> </dependency> // If you are using Gradle, add the following dependency: implementation group: 'com.yoti', name: 'yoti-sdk-api', version: '3.12.0'
// Get the Yoti PHP SDK library via a Composer package composer require yoti/yoti-php-sdk
pip install yoti
// To install the Yoti NuGet package, enter the following command // from NuGet Package Manager Console in Visual Studio: Install-Package Yoti
// Add to go.mod: require github.com/getyoti/yoti-go-sdk/v3 // Or download via terminal: go get "github.com/getyoti/yoti-go-sdk/v3"

Step 1: Initialise the client

Initialise the Yoti client with your sandbox credentials and point it to the sandbox URL.

Sandbox URL: https://api.yoti.com/sandbox/idverify/v1

const { IDVClient } = require('yoti'); const fs = require('fs'); const SANDBOX_CLIENT_SDK_ID = 'YOUR_SANDBOX_SDK_ID'; const SANDBOX_PEM = fs.readFileSync('/path/to/your-sandbox-pem-file.pem', 'utf8'); // Initialise client with sandbox URL const idvClient = new IDVClient( SANDBOX_CLIENT_SDK_ID, SANDBOX_PEM, { apiUrl: 'https://api.yoti.com/sandbox/idverify/v1' } );
// Point the Doc Scan client at the sandbox by setting environment variable System.setProperty("yoti.docs.url", "https://api.yoti.com/sandbox/idverify/v1"); import com.yoti.api.client.ClassPathKeySource; import com.yoti.api.client.docs.DocScanClient; ... String SANDBOX_CLIENT_SDK_ID = "YOUR_SANDBOX_SDK_ID"; String SANDBOX_PEM_PATH = "/path/to/your-sandbox-pem-file.pem"; DocScanClient docScanClient = DocScanClient.builder() .withClientSdkId(SANDBOX_CLIENT_SDK_ID) .withKeyPairSource(ClassPathKeySource.fromClasspath(SANDBOX_PEM_PATH)) .build();
<?php use Yoti\DocScan\DocScanClient; $SANDBOX_CLIENT_SDK_ID = 'YOUR_SANDBOX_SDK_ID'; $SANDBOX_PEM_PATH = '/path/to/your-sandbox-pem-file.pem'; $docScanClient = new DocScanClient( $SANDBOX_CLIENT_SDK_ID, $SANDBOX_PEM_PATH, ['api.url' => 'https://api.yoti.com/sandbox/idverify/v1'] );
using System.IO; using System.Net.Http; using Yoti.Auth; using Yoti.Auth.DocScan; ... const string SANDBOX_CLIENT_SDK_ID = "YOUR_SANDBOX_SDK_ID"; const string SANDBOX_PEM_PATH = "/path/to/your-sandbox-pem-file.pem"; StreamReader privateKeyStream = System.IO.File.OpenText(SANDBOX_PEM_PATH); var key = CryptoEngine.LoadRsaKey(privateKeyStream); var docScanClient = new DocScanClient( SANDBOX_CLIENT_SDK_ID, key, new HttpClient(), new Uri("https://api.yoti.com/sandbox/idverify/v1") );
// Add to go.mod: require github.com/getyoti/yoti-go-sdk/v3 // Or download via terminal: go get "github.com/getyoti/yoti-go-sdk/v3"

Step 2: Create a session

Create an identity verification session exactly as you would in production. The session configuration determines what identity profile scheme is used.

const path = require('path'); const fs = require('fs'); const { IDVClient, AdvancedIdentityProfileSchemeBuilder, AdvancedIdentityProfileBuilder, AdvancedIdentityProfileRequirementsBuilder SessionSpecificationBuilder, SdkConfigBuilder, } = require('yoti'); const YOTI_CLIENT_SDK_ID = 'YOTI_CLIENT_SDK_ID'; const YOTI_PEM = fs.readFileSync(path.join(__dirname, '/path/to/pem')); const idvClient = new IDVClient(YOTI_CLIENT_SDK_ID, YOTI_PEM); const subject = { subject_id: 'subject_id_string', }; ] const advancedIdentityProfileScheme = new AdvancedIdentityProfileSchemeBuilder() .withType('DBS') .withObjective('STANDARD') .withLabel('DBS-EXAMPLE') .build(); const advancedIdentityProfile = new AdvancedIdentityProfileBuilder() .withTrustFramework('UK_TFIDA') .withScheme(advancedIdentityProfileScheme) .build(); const advancedIdentityProfileRequirements = new AdvancedIdentityProfileRequirementsBuilder() .withProfile(advancedIdentityProfile) .build(); const sdkConfig = new SdkConfigBuilder() .withAllowHandoff(true) .withSuccessUrl(`${APP_BASE_URL}/success`) .withErrorUrl(`${APP_BASE_URL}/error`) .build(); const sessionSpec = new SessionSpecificationBuilder() .withSubject(subject) .withAdvancedIdentityProfileRequirements(advancedIdentityProfileRequirements) .withSdkConfig(sdkConfig) .build(); const session = await idvClient.createSession(sessionSpec); const sessionId = session.getSessionId(); const clientSessionToken = session.getClientSessionToken();
import com.yoti.api.client.docs.session.create.CreateSessionResult; import com.yoti.api.client.docs.session.create.SdkConfig; import com.yoti.api.client.docs.session.create.SessionSpec; import com.yoti.api.client.docs.session.create.identityprofile.advanced.AdvancedIdentityProfilePayload; import com.yoti.api.client.docs.session.create.identityprofile.advanced.AdvancedIdentityProfileRequirementsPayload; import com.yoti.api.client.docs.session.create.identityprofile.advanced.AdvancedIdentityProfileSchemePayload; ... // Define checks DocScanClient docScanClient = DocScanClient.builder() .withClientSdkId("YOTI_CLIENT_SDK_ID") .withKeyPairSource(ClassPathKeySource.fromClasspath("/path/to/pem")) .build(); JSONObject subject = new JSONObject(); subject.put("subject_id", "subject_id_string"); AdvancedIdentityProfileSchemePayload scheme = AdvancedIdentityProfileSchemePayload.builder() .withType("DBS") .withObjective("STANDARD") .withLabel("DBS-EXAMPLE") .build(); AdvancedIdentityProfilePayload profile = AdvancedIdentityProfilePayload.builder() .withTrustFramework("UK_TFIDA") .withScheme(scheme) .build(); AdvancedIdentityProfileRequirementsPayload advancedIdentityProfileRequirements = AdvancedIdentityProfileRequirementsPayload.builder() .withProfile(profile) .build(); SdkConfig sdkConfig = SdkConfig.builder() .withAllowHandoff(true) .withSuccessUrl("https://localhost:8443/success") .withErrorUrl("https://localhost:8443/error") .build(); SessionSpec sessionSpec = SessionSpec.builder() .withSubject(subject) .withAdvancedIdentityProfileRequirements(advancedIdentityProfileRequirements) .withSdkConfig(sdkConfig) .build(); CreateSessionResult createSessionResult = docScanClient.createSession(sessionSpec); string sessionId = createSessionResult.getSessionId(); string clientSessionToken = createSessionResult.getClientSessionToken();
<?php use Yoti\DocScan\Session\Create\SessionSpecificationBuilder; use Yoti\DocScan\Session\Create\SdkConfigBuilder; // Define check $YOTI_CLIENT_SDK_ID = 'YOTI_CLIENT_SDK_ID'; $YOTI_PEM = '/path/to/pem'; $docScanClient = new DocScanClient($YOTI_CLIENT_SDK_ID, $YOTI_PEM); $subject = (object)[ 'subject_id' => 'subject_id_string', ]; $advancedIdentityProfileRequirements = (object)[ 'profiles' => [ (object)[ 'trust_framework' => 'UK_TFIDA', 'schemes' => [ (object)[ 'type' => 'DBS', 'objective' => 'STANDARD', 'label' => 'DBS-EXAMPLE', ], ], ] ] ]; $sdkConfig = (new SdkConfigBuilder()) ->withAllowHandoff(true) ->withSuccessUrl('https://localhost:8443/success') ->withErrorUrl('https://localhost:8443/error') ->build(); $sessionSpec = (new SessionSpecificationBuilder()) ->withSubject($subject) ->withAdvancedIdentityProfileRequirements($advancedIdentityProfileRequirements) ->withSdkConfig($sdkConfig) ->build(); // Create session $session = $docScanClient->createSession($sessionSpec); $sessionId = $session->getSessionId(); $clientSessionToken = $session->getClientSessionToken();
using Yoti.Auth.DocScan.Session.Create; using Yoti.Auth.DocScan.Session.Create.Check; using Yoti.Auth.DocScan.Session.Create.Task; ... // Define check const string YOTI_CLIENT_SDK_ID = "YOTI_CLIENT_SDK_ID"; const string PEM_PATH = "/path/to/pem"; StreamReader privateKeyStream = System.IO.File.OpenText(PEM_PATH); var key = CryptoEngine.LoadRsaKey(privateKeyStream); DocScanClient docScanClient = new DocScanClient(YOTI_CLIENT_SDK_ID, key, new HttpClient()); string subjectString = @"{ subject_id: 'subject_id_string', }"; JObject subject = JObject.Parse(subjectString); string advancedIdentityProfileRequirementsString = @"{ profiles: [ { trust_framework: 'UK_TFIDA', schemes: [ { type: 'DBS', objective: 'STANDARD', label: 'DBS_EXAMPLE' } ] } ] }"; JObject advancedIdentityProfileRequirements = JObject.Parse(advancedIdentityProfileRequirementsString); SdkConfig sdkConfig = new SDKConfigBuilder() .WithAllowHandoff(true) .WithSuccessUrl("https://localhost:8443/success") .WithErrorUrl("https://localhost:8443/error") .Build(); SessionSpecification sessionSpec = new SessionSpecificationBuilder() .WithSubject(subject) .WithAdvancedIdentityProfileRequirements(advancedIdentityProfileRequirements) .WithSdkConfig(sdkConfig) .Build(); // Create session CreateSessionResult createSessionResult = docScanClient.CreateSession(sessionSpec); string sessionId = createSessionResult.SessionId; string clientSessionToken = createSessionResult.ClientSessionToken;
sdkID := "YOTI_CLIENT_SDK_ID"; key, _ := ioutil.ReadFile("YOTI_KEY_FILE_PATH") client, err := docscan.NewClient(sdkId, key) if err != nil { return nil, err } advancedIdentityProfile := []byte(`{ profiles: [ { trust_framework: 'UK_TFIDA', schemes: [ { type: 'DBS', objective: 'STANDARD', label: 'DBS_EXAMPLE' } ] } ] }`) subject := []byte(`{ "subject_id": "subject-id-string" }`) var sdkConfig *create.SDKConfig sdkConfig, err = create.NewSdkConfigBuilder(). withAllowHandoff(true). WithSuccessUrl("https://localhost:8443/success"). WithErrorUrl("https://localhost:8443/error"). WithPrivacyPolicyUrl("https://localhost:8443/privacy-policy"). Build() if err != nil { return nil, err } sessionSpec, err = create.NewSessionSpecificationBuilder(). WithSDKConfig(sdkConfig). WithAdvancedIdentityProfileRequirements(advancedIdentityProfile). WithSubject(subject). Build() createSessionResult, err = client.CreateSession(sessionSpec) if err != nil { return nil, err } sessionId = createSessionResult.SessionID clientSessionToken = createSessionResult.ClientSessionToken
Info

More details on how to create a session can be found here

Trust Framework

Scheme Type

Objective

Description

UK_TFIDA

RTW

N/A

UK certified right to work verification.

UK_TFIDA

RTR

N/A

UK certified right to rent verification.

UK_TFIDA

DBS

BASIC, STANDARD, ENHANCED

UK certified digital method for verifying a person's identity for criminal record checks

YOTI_GLOBAL

IDENTITY

AL_L1, AL_M1

Yoti created Identity verification that can be set to a low assurance "L1" or a medium assurance "M1". The medium assurance adds a biometric face match.

YOTI_GLOBAL

IDENTITY_PLUS_ADDRESS

AL_L1, AL_M1

Yoti created Identity verification that can be set to a low assurance "L1" or a medium assurance "M1". The medium assurance adds a biometric face match. An address check will also be performed.

YOTI_GLOBAL

GBR_RTW_SHARECODE

N/A

Yoti created verification that will fetch a users share code details and compare them to details extracted from a users Id documents.

YOTI_GLOBAL

CAN_CRC

N/A

Yoti created Identity verification that will verify a document and perform a biometric face match. For the Canadian Criminal Record Check.


Step 3a: Launch the user view (manual testing)

Construct the following URL for manual testing, and render it inside an iFrame:

https://api.yoti.com/sandbox/idverify/v1/web/index.html?sessionID={sessionID}&sessionToken={clientSessionToken}

iFrame example

<iframe src="https://api.yoti.com/sandbox/idverify/v1/web/index.html?sessionID={sessionID}&sessionToken={clientSessionToken}" style="height:100vh; width:100%; border:none;" allow="camera"> </iframe>

Users can upload sample documents and selfies, and the sandbox returns predefined successful responses along with the uploaded image resources.


Step 3b: Use the agent endpoint (automated testing)

Info

The /agent endpoint bypasses the user view and completes sessions programmatically with sample data—ideal for CI/CD and automated tests.

Endpoint

POST https://api.yoti.com/sandbox/idverify/v1/sessions/{sessionId}/agent

Use Case

Benefit

Automated tests

Skip manual document upload

CI/CD pipelines

Integrate verification in build process

Payload structure

{ "session_id": "YOUR_SESSION_ID", "client_session_token": "YOUR_SESSION_TOKEN" }

Code examples

const { RequestBuilder, Payload } = require("yoti"); const payload = { session_id: sessionId, client_session_token: clientSessionToken }; const request = new RequestBuilder() .withBaseUrl("https://api.yoti.com/sandbox/idverify/v1") .withPemFilePath(SANDBOX_PEM_PATH) .withEndpoint("/agent") .withPayload(new Payload(payload)) .withMethod("POST") .withQueryParam("sdkId", SANDBOX_CLIENT_SDK_ID) .build(); // Execute request const response = await request.execute();
import com.yoti.api.client.spi.remote.call.SignedRequest; import com.yoti.api.client.spi.remote.call.SignedRequestBuilder; ... String payload = String.format( "{\"session_id\":\"%s\",\"client_session_token\":\"%s\"}", sessionId, clientSessionToken ); try { SignedRequest signedRequest = SignedRequestBuilder.newInstance() .withKeyPair(SANDBOX_PEM_PATH) .withBaseUrl("https://api.yoti.com/sandbox/idverify/v1") .withEndpoint("/agent") .withPayload(payload.getBytes()) .withHttpMethod("POST") .withQueryParameter("sdkId", SANDBOX_CLIENT_SDK_ID) .build(); Response response = signedRequest.execute(); } catch (Exception ex) { ex.printStackTrace(); }
<?php use Yoti\Http\RequestBuilder; use Yoti\Http\Payload; $payload = [ 'session_id' => $sessionId, 'client_session_token' => $clientSessionToken ]; $request = (new RequestBuilder()) ->withBaseUrl('https://api.yoti.com/sandbox/idverify/v1') ->withPemFilePath($SANDBOX_PEM_PATH) ->withEndpoint('/agent') ->withPayload(Payload::fromJsonData($payload)) ->withMethod('POST') ->withQueryParam('sdkId', $SANDBOX_CLIENT_SDK_ID) ->build() ->execute();
using System.IO; using System.Net.Http; using System.Text; using Yoti.Auth.Web; HttpClient httpClient = new HttpClient(); StreamReader privateKeyStream = System.IO.File.OpenText(SANDBOX_PEM_PATH); string payload = Newtonsoft.Json.JsonConvert.SerializeObject(new { session_id = sessionId, client_session_token = clientSessionToken }); byte[] payloadBytes = Encoding.UTF8.GetBytes(serializedRequest); Uri baseUrl = new UriBuilder("https", "api.yoti.com", 443, "sandbox/idverify/v1").Uri; Request agentRequest = new RequestBuilder() .WithStreamReader(privateKeyStream) .WithBaseUri(baseUrl) .WithEndpoint("/agent") .WithHttpMethod(HttpMethod.Post) .WithContent(payloadBytes) .WithQueryParam("sdkId", SANDBOX_CLIENT_SDK_ID) .Build(); HttpResponseMessage response = agentRequest.Execute(httpClient).Result;
import ( "encoding/json" "io/ioutil" "net/http" "github.com/getyoti/yoti-go-sdk/v3/requests" ) key, _ := ioutil.ReadFile(SANDBOX_PEM_PATH) payload := map[string]string{ "session_id": sessionID, "client_session_token": clientSessionToken, } payloadJSON, _ := json.Marshal(skipUI) request, _ := requests.SignedRequest{ HTTPMethod: http.MethodPost, BaseURL: "https://api.yoti.com/sandbox/idverify/v1", Endpoint: "/agent", Params: map[string]string{ "sdkId": SANDBOX_CLIENT_SDK_ID, }, Headers: map[string][]string{ "Content-Type": {"application/json"}, "Accept": {"application/json"}, }, Body: payloadJSON, }.WithPemFile(key).Request() response, _ := http.DefaultClient.Do(request)

Step 4: Retrieve session results

After the session is completed (either via user view or agent endpoint), retrieve the results to verify the outcome.

// Retrieve session result idvClient.getSession(sessionId).then(session => { // Session state const state = session.getState(); // Resources (documents, images) const resources = session.getResources(); const idDocuments = resources.getIdDocuments(); // Checks const authenticityChecks = session.getAuthenticityChecks(); const livenessChecks = session.getLivenessChecks(); const faceMatchChecks = session.getFaceMatchChecks(); // Tasks const textExtractionTasks = session.getTextDataChecks(); // Identity Profile const advancedIdentityProfile = sessionResult.getAdvancedIdentityProfile(); const report = advancedIdentityProfile.getIdentityProfileReport(); // Biometric consent const biometricConsent = session.getBiometricConsentTimestamp(); console.log('Session completed successfully'); }).catch(error => { console.error('Error retrieving session:', error); });
// Retrieve session result GetSessionResult sessionResult = docScanClient.getSession(sessionId); // Session state String state = sessionResult.getState(); // Resources (documents, images) ResourceContainer resources = sessionResult.getResources(); List<? extends IdDocumentResourceResponse> idDocuments = resources.getIdDocuments(); // Checks List<AuthenticityCheckResponse> authenticityChecks = sessionResult.getAuthenticityChecks(); List<LivenessCheckResponse> livenessChecks = sessionResult.getLivenessChecks(); List<FaceMatchCheckResponse> faceMatchChecks = sessionResult.getFaceMatchChecks(); // Tasks List<TextDataCheckResponse> textDataChecks = sessionResult.getTextDataChecks(); // Identity Profile AdvancedIdentityProfileReportResponse report = sessionResult.getAdvancedIdentityProfile().getIdentityProfileReport(); // Biometric consent String biometricConsent = sessionResult.getBiometricConsentTimestamp();
<?php // Retrieve session result $sessionResult = $docScanClient->getSession($sessionId); // Session state $state = $sessionResult->getState(); // Resources (documents, images) $resources = $sessionResult->getResources(); $idDocuments = $resources->getIdDocuments(); // Checks $authenticityChecks = $sessionResult->getAuthenticityChecks(); $livenessChecks = $sessionResult->getLivenessChecks(); $faceMatchChecks = $sessionResult->getFaceMatchChecks(); // Tasks $textDataChecks = $sessionResult->getTextDataChecks(); // Identity Profile $identityProfile = $sessionResult->getAdvancedIdentityProfile(); $identityProfileReport = $identityProfile->getIdentityProfileReport(); // Biometric consent $biometricConsent = $sessionResult->getBiometricConsentTimestamp();
// Retrieve session result GetSessionResult sessionResult = docScanClient.GetSession(sessionId); // Session state string state = sessionResult.State; // Resources (documents, images) ResourceContainer resources = sessionResult.Resources; List<IdDocumentResourceResponse> idDocuments = resources.GetIdDocuments(); // Checks List<AuthenticityCheckResponse> authenticityChecks = sessionResult.GetAuthenticityChecks(); List<LivenessCheckResponse> livenessChecks = sessionResult.GetLivenessChecks(); List<FaceMatchCheckResponse> faceMatchChecks = sessionResult.GetFaceMatchChecks(); // Tasks List<TextDataCheckResponse> textDataChecks = sessionResult.GetTextDataChecks(); // Identity Profile IdentityProfileResponse identityProfile = sessionResult.AdvancedIdentityProfile; // Biometric consent DateTime biometricConsent = sessionResult.BiometricConsentTimestamp();
// Returns a session result sessionResult, err := client.GetSession(sessionId) if err != nil { return nil, err } // Returns the session state state = sessionResult.State // Returns session resources resources = sessionResult.Resources // Identity Profile identityProfile = sessionResult.AdvancedIdentityProfileResponse identityProfileReport = identityProfile.Report
Info

More details on how to retrieve the results can be found here

Example sandbox response

Here is a sample JSON response from a finished sandbox session:

{ "client_session_token_ttl": 8889, "session_id": "09065a5e-ab48-4507-9d39-b061606def09", "state": "COMPLETED", "resources": { "id_documents": [ { "id": "3b92c849-4dfe-4163-a070-0c22bdba254d", "tasks": [ { "type": "ID_DOCUMENT_TEXT_DATA_EXTRACTION", "id": "1bb79ebb-0cd6-4667-8112-b47f5b22563a", "state": "DONE", "created": "2026-05-14T08:32:48Z", "last_updated": "2026-05-14T08:32:54Z", "generated_media": [ { "id": "b1e3381f-3707-4636-9361-ed81e8637b76", "type": "JSON" } ], "recommendation": { "value": "PROGRESS" }, "generated_checks": [] } ], "source": { "type": "END_USER" }, "created_at": "2026-05-14T08:32:48Z", "last_updated": "2026-05-14T08:32:54Z", "document_type": "NATIONAL_ID", "issuing_country": "AFG", "pages": [ { "capture_method": "CAMERA", "media": { "id": "f0e452cb-b5de-4c2f-aa25-d2ffc88722ba", "type": "IMAGE", "created": "2026-05-14T08:32:49Z", "last_updated": "2026-05-14T08:32:49Z" }, "frames": [ { "media": { "id": "227fc7f2-f05e-43f9-8308-bf17481b1b83", "type": "IMAGE", "created": "2026-05-14T08:32:50Z", "last_updated": "2026-05-14T08:32:50Z" } }, { "media": { "id": "d733fb00-0a50-4a78-a192-12442a47a4a1", "type": "IMAGE", "created": "2026-05-14T08:32:50Z", "last_updated": "2026-05-14T08:32:50Z" } } ], "extraction_image_ids": [] }, { "capture_method": "CAMERA", "media": { "id": "8d29b47e-d4d3-4ea1-bde0-aa631e230f7c", "type": "IMAGE", "created": "2026-05-14T08:32:51Z", "last_updated": "2026-05-14T08:32:51Z" }, "frames": [ { "media": { "id": "65b5bdd5-1484-4f5c-8c6d-ede273b1c9c3", "type": "IMAGE", "created": "2026-05-14T08:32:51Z", "last_updated": "2026-05-14T08:32:51Z" } }, { "media": { "id": "0769da39-a69b-4d27-92eb-5d7813295f65", "type": "IMAGE", "created": "2026-05-14T08:32:52Z", "last_updated": "2026-05-14T08:32:52Z" } } ], "extraction_image_ids": [] } ], "document_fields": { "media": { "id": "b1e3381f-3707-4636-9361-ed81e8637b76", "type": "JSON", "created": "2026-05-14T08:32:53Z", "last_updated": "2026-05-14T08:32:53Z" } }, "document_id_photo": { "media": { "id": "beeb009e-2331-4b8c-9859-f07206973819", "type": "IMAGE", "created": "2026-05-14T08:32:53Z", "last_updated": "2026-05-14T08:32:53Z" } } }, { "id": "dd504b1b-3a0f-461d-a1da-298a407b23b2", "tasks": [ { "type": "ID_DOCUMENT_TEXT_DATA_EXTRACTION", "id": "4d69d263-c7e0-44ef-8f79-e64b7ba48aee", "state": "DONE", "created": "2026-05-14T08:32:43Z", "last_updated": "2026-05-14T08:32:47Z", "generated_media": [ { "id": "5c1231ce-fd25-474b-8199-421687081831", "type": "JSON" } ], "recommendation": { "value": "PROGRESS" }, "generated_checks": [] } ], "source": { "type": "END_USER" }, "created_at": "2026-05-14T08:32:43Z", "last_updated": "2026-05-14T08:32:47Z", "document_type": "DRIVING_LICENCE", "issuing_country": "AFG", "pages": [ { "capture_method": "CAMERA", "media": { "id": "e61c5f33-b46d-45a3-b5d9-ac411e68addb", "type": "IMAGE", "created": "2026-05-14T08:32:43Z", "last_updated": "2026-05-14T08:32:43Z" }, "frames": [ { "media": { "id": "d9ed3bcb-7b1c-4b81-ac93-52fb8d6f64f3", "type": "IMAGE", "created": "2026-05-14T08:32:44Z", "last_updated": "2026-05-14T08:32:44Z" } }, { "media": { "id": "82c27d65-ec3f-4ab8-9fbe-0a821eac1dc5", "type": "IMAGE", "created": "2026-05-14T08:32:44Z", "last_updated": "2026-05-14T08:32:44Z" } } ], "extraction_image_ids": [] }, { "capture_method": "CAMERA", "media": { "id": "8db0aed6-1bd6-4c08-b3b7-fe674522c7e9", "type": "IMAGE", "created": "2026-05-14T08:32:45Z", "last_updated": "2026-05-14T08:32:45Z" }, "frames": [ { "media": { "id": "619f3406-4aa4-4e8b-87d7-403a995c0756", "type": "IMAGE", "created": "2026-05-14T08:32:45Z", "last_updated": "2026-05-14T08:32:45Z" } }, { "media": { "id": "06135ff4-373d-4b1a-bb43-c305e4afd05e", "type": "IMAGE", "created": "2026-05-14T08:32:46Z", "last_updated": "2026-05-14T08:32:46Z" } } ], "extraction_image_ids": [] } ], "document_fields": { "media": { "id": "5c1231ce-fd25-474b-8199-421687081831", "type": "JSON", "created": "2026-05-14T08:32:47Z", "last_updated": "2026-05-14T08:32:47Z" } }, "document_id_photo": { "media": { "id": "ce8e9446-1de0-45ba-a385-0321b114bba0", "type": "IMAGE", "created": "2026-05-14T08:32:47Z", "last_updated": "2026-05-14T08:32:47Z" } } }, { "id": "ae98a80f-4b6a-4c87-be98-50deef5e0f81", "tasks": [ { "type": "ID_DOCUMENT_TEXT_DATA_EXTRACTION", "id": "0c7663d2-05ba-42cc-80fd-818d7504ba1a", "state": "DONE", "created": "2026-05-14T08:32:36Z", "last_updated": "2026-05-14T08:32:40Z", "generated_media": [ { "id": "05f9a17c-0f8d-437b-a6a1-c06c68f37afd", "type": "JSON" } ], "recommendation": { "value": "PROGRESS" }, "generated_checks": [] } ], "source": { "type": "END_USER" }, "created_at": "2026-05-14T08:32:36Z", "last_updated": "2026-05-14T08:32:40Z", "document_type": "PASSPORT", "issuing_country": "AIA", "pages": [ { "capture_method": "CAMERA", "media": { "id": "b5c7d38c-dd25-4c4a-81c7-cb6a8f8c25a1", "type": "IMAGE", "created": "2026-05-14T08:32:36Z", "last_updated": "2026-05-14T08:32:36Z" }, "frames": [ { "media": { "id": "325be763-854a-4fb4-8b4a-5a64a9b18e69", "type": "IMAGE", "created": "2026-05-14T08:32:37Z", "last_updated": "2026-05-14T08:32:37Z" } }, { "media": { "id": "ca3a396d-ed18-4530-86e8-ec591dd8afca", "type": "IMAGE", "created": "2026-05-14T08:32:38Z", "last_updated": "2026-05-14T08:32:38Z" } }, { "media": { "id": "fd4dd759-b589-4bd1-a8d8-d71865fb0efe", "type": "IMAGE", "created": "2026-05-14T08:32:38Z", "last_updated": "2026-05-14T08:32:38Z" } } ], "extraction_image_ids": [] } ], "document_fields": { "media": { "id": "05f9a17c-0f8d-437b-a6a1-c06c68f37afd", "type": "JSON", "created": "2026-05-14T08:32:39Z", "last_updated": "2026-05-14T08:32:39Z" } }, "document_id_photo": { "media": { "id": "7672c9cb-d687-432b-b887-1ba3630f1b6b", "type": "IMAGE", "created": "2026-05-14T08:32:39Z", "last_updated": "2026-05-14T08:32:39Z" } } } ], "supplementary_documents": [], "liveness_capture": [ { "id": "cd3dfe34-b7b2-463c-9d17-96042b91270e", "tasks": [], "source": { "type": "END_USER" }, "created_at": "2026-05-14T08:32:57Z", "last_updated": "2026-05-14T08:33:00Z", "frames": [ { "media": { "id": "d781dfe4-848b-49d3-a0c8-1aad63213717", "type": "IMAGE", "created": "2026-05-14T08:32:58Z", "last_updated": "2026-05-14T08:32:58Z" } }, { "media": { "id": "3f4ad857-5293-4c14-9bb1-3d8a9dc70dfd", "type": "IMAGE", "created": "2026-05-14T08:32:58Z", "last_updated": "2026-05-14T08:32:58Z" } }, { "media": { "id": "a279a2d0-5786-4642-8970-5ce018f8c848", "type": "IMAGE", "created": "2026-05-14T08:32:59Z", "last_updated": "2026-05-14T08:32:59Z" } }, {}, {}, {}, {} ], "liveness_type": "ZOOM", "facemap": { "media": { "id": "03caf157-1cbe-4f8e-ab64-0c5d2e95744f", "type": "BINARY", "created": "2026-05-14T08:33:00Z", "last_updated": "2026-05-14T08:33:00Z" } } } ], "face_capture": [], "applicant_profiles": [ { "id": "6e1aa5ae-b972-487d-91d0-49e22b89a825", "tasks": [], "source": { "type": "END_USER" }, "created_at": "2026-05-14T08:32:55Z", "last_updated": "2026-05-14T08:32:55Z", "media": { "id": "61455a62-17c8-4a8f-b166-eadba3ca9d3b", "type": "JSON", "created": "2026-05-14T08:32:55Z", "last_updated": "2026-05-14T08:32:55Z" } }, { "id": "db213cdc-1f9c-4232-b4b6-5ff672907f3a", "tasks": [], "source": { "type": "END_USER" }, "created_at": "2026-05-14T08:32:41Z", "last_updated": "2026-05-14T08:32:41Z", "media": { "id": "36461bbc-691e-4f7a-8009-d3a30356e9d2", "type": "JSON", "created": "2026-05-14T08:32:41Z", "last_updated": "2026-05-14T08:32:41Z" } } ], "share_codes": [] }, "checks": [ { "type": "ID_DOCUMENT_AUTHENTICITY", "id": "5f9d2f2a-c8c2-491c-a12c-b5dcd4cb0ff1", "state": "DONE", "resources_used": [ "ae98a80f-4b6a-4c87-be98-50deef5e0f81", "cd3dfe34-b7b2-463c-9d17-96042b91270e" ], "generated_media": [], "report": { "recommendation": { "value": "APPROVE" }, "breakdown": [ { "sub_check": "document_in_date", "result": "PASS", "details": [], "process": "AUTOMATED" }, { "sub_check": "document_recognition", "result": "PASS", "details": [], "process": "AUTOMATED" }, { "sub_check": "fraud_list_check", "result": "PASS", "details": [], "process": "AUTOMATED" }, { "sub_check": "hologram", "result": "PASS", "details": [], "process": "EXPERT_REVIEW" }, { "sub_check": "hologram_movement", "result": "PASS", "details": [], "process": "EXPERT_REVIEW" }, { "sub_check": "mrz_validation", "result": "PASS", "details": [], "process": "AUTOMATED" }, { "sub_check": "no_sign_of_forgery", "result": "PASS", "details": [], "process": "EXPERT_REVIEW" }, { "sub_check": "no_sign_of_tampering", "result": "PASS", "details": [], "process": "EXPERT_REVIEW" }, { "sub_check": "ocr_mrz_comparison", "result": "PASS", "details": [ { "name": "date_of_birth", "value": "MATCH" }, { "name": "document_number", "value": "MATCH" }, { "name": "expiration_date", "value": "MATCH" }, { "name": "gender", "value": "MATCH" }, { "name": "issuing_country", "value": "MATCH" }, { "name": "name", "value": "MATCH" } ], "process": "AUTOMATED" }, { "sub_check": "other_security_features", "result": "PASS", "details": [], "process": "EXPERT_REVIEW" }, { "sub_check": "physical_document_captured", "result": "PASS", "details": [], "process": "EXPERT_REVIEW" }, { "sub_check": "portrait_integrity", "result": "PASS", "details": [ { "name": "portrait_substitution_trust_score", "value": "0.99" }, { "name": "portrait_substitution", "value": "VERY_UNLIKELY" } ], "process": "AUTOMATED" }, { "sub_check": "yoti_fraud_list_check", "result": "PASS", "details": [ { "name": "provider_org", "value": "Yoti Ltd" } ], "process": "AUTOMATED" } ] }, "created": "2026-05-14T08:33:15Z", "last_updated": "2026-05-14T08:33:18Z" }, { "type": "ID_DOCUMENT_AUTHENTICITY", "id": "5f98416f-3301-428e-8bb8-72482695d8ce", "state": "DONE", "resources_used": [ "3b92c849-4dfe-4163-a070-0c22bdba254d", "cd3dfe34-b7b2-463c-9d17-96042b91270e" ], "generated_media": [], "report": { "recommendation": { "value": "APPROVE" }, "breakdown": [ { "sub_check": "document_in_date", "result": "PASS", "details": [], "process": "AUTOMATED" }, { "sub_check": "document_recognition", "result": "PASS", "details": [], "process": "AUTOMATED" }, { "sub_check": "fraud_list_check", "result": "PASS", "details": [], "process": "AUTOMATED" }, { "sub_check": "hologram", "result": "PASS", "details": [], "process": "EXPERT_REVIEW" }, { "sub_check": "hologram_movement", "result": "PASS", "details": [], "process": "EXPERT_REVIEW" }, { "sub_check": "mrz_validation", "result": "PASS", "details": [], "process": "AUTOMATED" }, { "sub_check": "no_sign_of_forgery", "result": "PASS", "details": [], "process": "EXPERT_REVIEW" }, { "sub_check": "no_sign_of_tampering", "result": "PASS", "details": [], "process": "EXPERT_REVIEW" }, { "sub_check": "ocr_mrz_comparison", "result": "PASS", "details": [ { "name": "date_of_birth", "value": "MATCH" }, { "name": "document_number", "value": "MATCH" }, { "name": "expiration_date", "value": "MATCH" }, { "name": "gender", "value": "MATCH" }, { "name": "issuing_country", "value": "MATCH" }, { "name": "name", "value": "MATCH" } ], "process": "AUTOMATED" }, { "sub_check": "other_security_features", "result": "PASS", "details": [], "process": "EXPERT_REVIEW" }, { "sub_check": "physical_document_captured", "result": "PASS", "details": [], "process": "EXPERT_REVIEW" }, { "sub_check": "portrait_integrity", "result": "PASS", "details": [ { "name": "portrait_substitution_trust_score", "value": "0.99" }, { "name": "portrait_substitution", "value": "VERY_UNLIKELY" } ], "process": "AUTOMATED" }, { "sub_check": "yoti_fraud_list_check", "result": "PASS", "details": [ { "name": "provider_org", "value": "Yoti Ltd" } ], "process": "AUTOMATED" } ] }, "created": "2026-05-14T08:33:15Z", "last_updated": "2026-05-14T08:33:18Z" }, { "type": "LIVENESS", "id": "9a6ee622-51c3-488c-a664-86c2745fdfd0", "state": "DONE", "resources_used": [ "cd3dfe34-b7b2-463c-9d17-96042b91270e" ], "generated_media": [], "report": { "recommendation": { "value": "APPROVE" }, "breakdown": [ { "sub_check": "liveness_auth", "result": "PASS", "details": [], "process": "AUTOMATED" } ] }, "created": "2026-05-14T08:33:00Z", "last_updated": "2026-05-14T08:33:05Z" }, { "type": "ID_DOCUMENT_FACE_MATCH", "id": "12ca5a71-ab37-4072-acbd-879f1bb7ca5d", "state": "DONE", "resources_used": [ "ae98a80f-4b6a-4c87-be98-50deef5e0f81", "cd3dfe34-b7b2-463c-9d17-96042b91270e" ], "generated_media": [], "report": { "recommendation": { "value": "APPROVE" }, "breakdown": [ { "sub_check": "ai_face_match", "result": "PASS", "details": [ { "name": "confidence_score", "value": "0.95" } ], "process": "AUTOMATED" } ] }, "created": "2026-05-14T08:33:15Z", "last_updated": "2026-05-14T08:33:18Z" }, { "type": "ID_DOCUMENT_FACE_MATCH", "id": "70c44aee-6705-4fb9-9402-607f88080a45", "state": "DONE", "resources_used": [ "3b92c849-4dfe-4163-a070-0c22bdba254d", "cd3dfe34-b7b2-463c-9d17-96042b91270e" ], "generated_media": [], "report": { "recommendation": { "value": "APPROVE" }, "breakdown": [ { "sub_check": "ai_face_match", "result": "PASS", "details": [ { "name": "confidence_score", "value": "0.95" } ], "process": "AUTOMATED" } ] }, "created": "2026-05-14T08:33:15Z", "last_updated": "2026-05-14T08:33:19Z" }, { "type": "THIRD_PARTY_IDENTITY", "id": "6813a865-4026-43f8-83b2-4c050d67315c", "state": "DONE", "resources_used": [ "ae98a80f-4b6a-4c87-be98-50deef5e0f81", "3b92c849-4dfe-4163-a070-0c22bdba254d" ], "generated_media": [ { "id": "f602f65f-1ad5-414f-ad6b-4e290505dc40", "type": "JSON" } ], "report": { "recommendation": { "value": "APPROVE" }, "breakdown": [ { "sub_check": "address_match", "result": "PASS", "details": [ { "name": "provider_org", "value": "sandbox_verifier" } ], "process": "AUTOMATED" }, { "sub_check": "deceased", "result": "PASS", "details": [ { "name": "provider_org", "value": "sandbox_verifier" } ], "process": "AUTOMATED" }, { "sub_check": "dob_match", "result": "PASS", "details": [ { "name": "provider_org", "value": "sandbox_verifier" } ], "process": "AUTOMATED" }, { "sub_check": "electoral_roll", "result": "PASS", "details": [ { "name": "provider_org", "value": "sandbox_verifier" } ], "process": "AUTOMATED" }, { "sub_check": "multiple_sources_match", "result": "PASS", "details": [ { "name": "number_of_sources_matched", "value": "5" }, { "name": "provider_org", "value": "sandbox_verifier" } ], "process": "AUTOMATED" }, { "sub_check": "name_match", "result": "PASS", "details": [ { "name": "provider_org", "value": "sandbox_verifier" } ], "process": "AUTOMATED" }, { "sub_check": "pep_warning", "result": "PASS", "details": [ { "name": "provider_org", "value": "sandbox_verifier" } ], "process": "AUTOMATED" }, { "sub_check": "sanctions_warning", "result": "PASS", "details": [ { "name": "uk_sanctions_list", "value": "PASS" }, { "name": "ofac", "value": "PASS" }, { "name": "provider_org", "value": "sandbox_verifier" } ], "process": "AUTOMATED" } ] }, "created": "2026-05-14T08:33:12Z", "last_updated": "2026-05-14T08:33:14Z", "generated_profile": { "media": { "id": "f602f65f-1ad5-414f-ad6b-4e290505dc40", "type": "JSON", "created": "2026-05-14T08:33:14Z", "last_updated": "2026-05-14T08:33:14Z" } } }, { "type": "THIRD_PARTY_IDENTITY_FRAUD_1", "id": "d4e96718-646c-4f64-95ea-711110634524", "state": "DONE", "resources_used": [ "ae98a80f-4b6a-4c87-be98-50deef5e0f81", "3b92c849-4dfe-4163-a070-0c22bdba254d" ], "generated_media": [ { "id": "9d0cd898-cbbb-4abb-90e4-83c4a0a056d8", "type": "JSON" } ], "report": { "recommendation": { "value": "APPROVE" }, "breakdown": [ { "sub_check": "check_performed", "result": "PASS", "details": [ { "name": "provider_org", "value": "redacted/IDFP_1" } ], "process": "AUTOMATED" } ] }, "created": "2026-05-14T08:33:08Z", "last_updated": "2026-05-14T08:33:11Z", "generated_profile": { "media": { "id": "9d0cd898-cbbb-4abb-90e4-83c4a0a056d8", "type": "JSON", "created": "2026-05-14T08:33:11Z", "last_updated": "2026-05-14T08:33:11Z" } } } ], "advanced_identity_profile": { "result": "DONE", "identity_profile_report": { "compliance": [ { "trust_framework": "UK_TFIDA", "schemes_compliance": [ { "scheme": { "type": "DBS", "objective": "STANDARD", "label": "EXAMPLE1" }, "requirements_met": true } ] } ], "media": { "id": "ec38eed7-c71f-4215-b46d-cfbe0522a7be", "type": "JSON", "created": "2026-05-14T08:33:20Z", "last_updated": "2026-05-14T08:33:20Z" } } } }

Default responses

The sandbox automatically provides approved results for the checks using sample data which will result in an overall pass, for the configured scheme. for example:

  • Document authenticity: APPROVE

  • Liveness: APPROVE

  • Face match: APPROVE

  • Third party identity: APPROVE

  • Fraud check: APPORVE

  • DBS scheme: REQUIREMENTS MET

  • Resources: Sample images and text extraction (Document fields)

This lets you test result handling without configuration.


Step 5: (Optional) Configure custom responses

To simulate failures or custom scenarios, refer to the sandbox Configure response guide. This lets you provide mock data such as for text extraction and also simulate partial check approvals or rejections.

You can use the same production SDKs for this as well.


Troubleshooting

Session not completing? Verify you're using the sandbox URL: https://api.yoti.com/sandbox/idverify/v1

Authentication errors? Ensure you're using sandbox keys (not production) and haven't opened the PEM file manually.