Presence Verification integrates
Presence Verification helps confirm that a real, live, single human is present in the verification session and is completing it on their own. It uses a passive selfie video and device signals captured by Veriff's native SDKs to help keep bots, deepfakes, injected media, and sessions guided by a third party out of your sign-up and high-risk flows, without asking the end-user for an identity document.
Presence Verification is available in two tiers:
Presence Verification : assesses presence, uniqueness, and liveness from the selfie image and the full selfie video, together with device and network integrity signals.
Presence Verification : assesses presence, uniqueness, and liveness from the selfie image and the full selfie video, together with device and network integrity signals.
Presence Verification with Coercion Detection : includes everything above, and also analyses the session audio and video to flag signs that a third party is guiding the end-user during the session.
Presence Verification with Coercion Detection : includes everything above, and also analyses the session audio and video to flag signs that a third party is guiding the end-user during the session.
Presence Verification is available via native SDKs (iOS and Android) and web flow. Because the checks rely on the media and device signals that Veriff's SDK captures, Veriff strongly recommends using the solution via native SDKs.
You need a separate integration for this solution, meaning existing solution's integrations cannot be used. Presence Verification is used as a standalone solution on that integration.
All session-related info is returned via the decision webhook and can be polled from different API endpoints . The results of the verification can also be viewed in the Veriff Customer Portal , on the session's page.
your solutions engineer for info and configuration.
You have an integration set up with Veriff
You have an integration set up with Veriff
Presence Verification is configured for that integration by your Solutions Engineer , including which tier you use
Presence Verification is configured for that integration by your Solutions Engineer , including which tier you use
You have configured the decision webhook to get responses from Veriff (see the how-to in webhooks' Set up webhooks section)
You have configured the decision webhook to get responses from Veriff (see the how-to in webhooks' Set up webhooks section)
You have integrated a Veriff native SDK (iOS or Android), and your app can request camera access from the end-user, and microphone access if you use Presence Verification with Coercion Detection
You have integrated a Veriff native SDK (iOS or Android), and your app can request camera access from the end-user, and microphone access if you use Presence Verification with Coercion Detection
Your backend is ready to create sessions with POST /sessions using the API keys of your Presence Verification integration
Your backend is ready to create sessions with POST /sessions using the API keys of your Presence Verification integration
Veriff strongly recommends that you create and send us the endUserId or vendorData
Veriff strongly recommends that you create and send us the endUserId or vendorData
To use Presence Verification with Coercion Detection, the end-user must be 18 years or older. Presence Verification without Coercion Detection has no age requirement.
To use Presence Verification with Coercion Detection, the end-user must be 18 years or older. Presence Verification without Coercion Detection has no age requirement.
→ For more info how to integrate using Android or iOS SDKs, see the SDK Guides section.
Feeding pre-recorded, synthetic, or manipulated media into the session instead of a live camera feed
Assessment of whether the face in the capture belongs to a live person rather than a photo, screen, mask, or deepfake
Multiple parties present
A second person is visible in the session video
The end-user records a short selfie video without performing gestures or prompted actions
Presence Verification
Veriff solution that helps confirm that a real, live, single human is present and is completing the session on their own
Presence Verification with Coercion Detection
Higher tier that also analyses the session audio and video for signs of third-party guidance
Another person instructing, dictating to, or pressuring the end-user during the session, on or off camera
During the session, Veriff's SDK accesses the selfie image, the selfie video, device metadata, and sensor data. No identity document is captured.
Generate a verification session using the API keys and the baseURL of your Presence Verification integration (see the API Documentation and API Reference how to find these) Veriff strongly recommends you create and send the endUserId or vendorData Session creation bash example curl -X POST \ --url '/v1/sessions/' \ -H 'X-AUTH-CLIENT: your-api-key' \ -H 'Content-Type: application/json' \ -d '{ "verification": { "endUserId": "a1b2c35d-e8f7-6d5e-3cd2-a1b2c35db3d4", "vendorData": "12345678" } }' Session creation json example { "verification": { "endUserId": "a1b2c35d-e8f7-6d5e-3cd2-a1b2c35db3d4", "vendorData": "12345678" } }
Generate a verification session using the API keys and the baseURL of your Presence Verification integration (see the API Documentation and API Reference how to find these)
Veriff strongly recommends you create and send the endUserId or vendorData Session creation bash example
Veriff strongly recommends you create and send the endUserId or vendorData
Session creation bash example
Session creation json example
Capture the end-user's selfie video with Veriff's native SDK Launch the Veriff iOS or Android SDK in your app. You need the session URL generated in step 1 (found in response payload as verification.url ). The end-user grants camera access, and microphone access if you use Presence Verification with Coercion Detection The end-user records a short, passive selfie video
Capture the end-user's selfie video with Veriff's native SDK
Launch the Veriff iOS or Android SDK in your app. You need the session URL generated in step 1 (found in response payload as verification.url ).
Launch the Veriff iOS or Android SDK in your app. You need the session URL generated in step 1 (found in response payload as verification.url ).
The end-user grants camera access, and microphone access if you use Presence Verification with Coercion Detection
The end-user grants camera access, and microphone access if you use Presence Verification with Coercion Detection
The end-user records a short, passive selfie video
The end-user records a short, passive selfie video
Session will be submitted automatically once the end-user completes the capture
Session will be submitted automatically once the end-user completes the capture
Receive the results from Veriff via the decision webhook or poll them via GET /sessions/{sessionId}/decision endpoint If the decision is resubmission_requested , the end-user sees a retry prompt in the session, records the video again, and Veriff sends a new decision
Receive the results from Veriff via the decision webhook or poll them via GET /sessions/{sessionId}/decision endpoint
If the decision is resubmission_requested , the end-user sees a retry prompt in the session, records the video again, and Veriff sends a new decision
If the decision is resubmission_requested , the end-user sees a retry prompt in the session, records the video again, and Veriff sends a new decision
Session lifecycle flow diagram
Click to open SDK session lifecycle diagram
Your backend creates a session, your app opens it in the Veriff SDK, the end-user records a passive selfie video, the SDK submits the session, and Veriff sends the decision webhook to your backend. If the decision is resubmission_requested , the end-user retries in the session and Veriff sends a new decision. Your backend can also poll the decision endpoint.
You can get the data from three sources:
Receive the decision webhook (full example with placeholder values below )
Receive the decision webhook (full example with placeholder values below )
Query the results via GET /sessions/{sessionId}/decision (payload is identical to the webhook)
Query the results via GET /sessions/{sessionId}/decision (payload is identical to the webhook)
View the session in the Veriff Customer Portal
View the session in the Veriff Customer Portal
Solution-specific parameters
Presence Verification does not add a solution-specific object to the payload. The result is returned in the standard decision fields: verification.status and verification.code show the outcome, and for sessions that are not approved, verification.reason and verification.reasonCode show why.
Which reason codes you can receive depends on your configuration, for example whether you use Presence Verification with Coercion Detection and whether bot and velocity protection is enabled. See Status and reason codes below.
Note object and field visibility
All objects and fields listed in the payload examples below are mandatory and always present.
verification.person and verification.document are always returned, but every field in them is null , because Presence Verification does not use an identity document
verification.person and verification.document are always returned, but every field in them is null , because Presence Verification does not use an identity document
verification.additionalVerifiedData is returned as an empty object {}
verification.additionalVerifiedData is returned as an empty object {}
verification.reason and verification.reasonCode are null when the session is approved
verification.reason and verification.reasonCode are null when the session is approved
verification.vendorData and verification.endUserId are null if you did not send them
verification.vendorData and verification.endUserId are null if you did not send them
technicalData.ip can be null
technicalData.ip can be null
Note on session outcomes
An approved session is identified by a verification.status of approved . It means the selfie and video appear genuine, a live end-user was present, and no signs of manipulation, non-uniqueness, or, on Presence Verification with Coercion Detection, third-party guidance were detected.
A session can also end as:
declined : the inputs appear not genuine, the end-user does not appear to be present, a second person or third-party guidance was detected, or other fraudulent behaviour was detected
declined : the inputs appear not genuine, the end-user does not appear to be present, a second person or third-party guidance was detected, or other fraudulent behaviour was detected
resubmission_requested : expected input is missing or of poor quality, for example the face is missing or not clearly visible, or the video is missing. The third-party guidance check never leads to resubmission_requested .
resubmission_requested : expected input is missing or of poor quality, for example the face is missing or not clearly visible, or the video is missing. The third-party guidance check never leads to resubmission_requested .
expired or abandoned : standard meanings, as for any other session
expired or abandoned : standard meanings, as for any other session
Note on the decision fields
For an approved session:
verification.status is approved ,
verification.status is approved ,
verification.code is 9001 , and
verification.code is 9001 , and
verification.reason and verification.reasonCode are null .
verification.reason and verification.reasonCode are null .
For a declined Presence Verification with Coercion Detection session, for example:
verification.status is declined ,
verification.status is declined ,
verification.code is 9102 ,
verification.code is 9102 ,
verification.reason is "Signs of third-party guidance during the session", and
verification.reason is "Signs of third-party guidance during the session", and
verification.reasonCode is 589 .
verification.reasonCode is 589 .
The example below uses placeholder data to show all mandatory parameters and possible Presence Verification fields . While mandatory fields are always present, solution-specific keys are omitted if a feature is disabled or data extraction fails. Depending on your integration's configuration , your production payload may contain additional parameters . For other parameters you might see, check the decision webhook documentation.
Request properties explained
status : string Status of the response
status : string Status of the response
verification : object Verification request decision object. null if decision is not available yet. id : string UUID v4 which identifies the verification session attemptId : string UUID v4 of the attempt which received a status (as shown in verification.status field) vendorData : string | null The unique identifier that you created for your end-user. null if not specified. endUserId : string | null The UUID that you created for your end-user. null if not specified. status : string Verification status, one of approved , declined , resubmission_requested , expired , abandoned code : integer Verification session decision code, one of 9001 , 9102 , 9103 , 9104 . For more info, see the Verification session decision codes (table) . reason : string | null Reason why the verification failed reasonCode : integer | null Reason code of the failed verification. For more info, see the Granular reason codes (table) . decisionTime : string | null Timestamp of the decision, represented as UTC YYYY-MM-DDTHH:MM:SS.SSS+Timezone Offset (ISO 8601) acceptanceTime : string Timestamp of the session generation, represented as UTC YYYY-MM-DDTHH:MM:SS.SSS+Timezone Offset (ISO 8601) submissionTime : string Timestamp of when the session was submitted, represented as UTC YYYY-MM-DDTHH:MM:SS.SSSSSS+Timezone Offset (ISO 8601) person : object Data the verified person. For Presence Verification, every field in this object is null . firstName : string | null Person's first name as written on the document lastName : string | null Person's last name as written on the document dateOfBirth : string | null Person's date of birth, represented as YYYY-MM-DD gender : string | null Person's gender, represented as M, F or X, or null if not present nationality : string | null Person's nationality, represented as ISO 3166 alpha-2 or alpha-3 number idNumber : string | null National identification number yearOfBirth : string | null Person's year of birth, represented as YYYY placeOfBirth : string | null Person's place of birth pepSanctionMatch : string | null Legacy field, may return incorrect result, should be ignored citizenship : null Deprecated, always returns null document : object Verified document. For Presence Verification, every field in this object is null . number : string | null Document number, [a-zA-Z0-9] characters only type : string | null Document type, one of PASSPORT , ID_CARD , RESIDENCE_PERMIT , DRIVERS_LICENSE , VISA , OTHER country : string | null Document issuing country, represented as ISO 3166 alpha-2 code state : string | null Document issuing state, represented as ISO 3166 alpha-2 or alpha-3 code validFrom : string | null Document is valid from date validUntil : string | null Document is valid until date additionalVerifiedData : object Data that has been optionally verified for the session. Empty {} for Presence Verification. : array (Deprecated) Always returns empty []
verification : object Verification request decision object. null if decision is not available yet.
id : string UUID v4 which identifies the verification session
id : string UUID v4 which identifies the verification session
attemptId : string UUID v4 of the attempt which received a status (as shown in verification.status field)
attemptId : string UUID v4 of the attempt which received a status (as shown in verification.status field)
vendorData : string | null The unique identifier that you created for your end-user. null if not specified.
vendorData : string | null The unique identifier that you created for your end-user. null if not specified.
endUserId : string | null The UUID that you created for your end-user. null if not specified.
endUserId : string | null The UUID that you created for your end-user. null if not specified.
status : string Verification status, one of approved , declined , resubmission_requested , expired , abandoned
status : string Verification status, one of approved , declined , resubmission_requested , expired , abandoned
code : integer Verification session decision code, one of 9001 , 9102 , 9103 , 9104 . For more info, see the Verification session decision codes (table) .
code : integer Verification session decision code, one of 9001 , 9102 , 9103 , 9104 . For more info, see the Verification session decision codes (table) .
reason : string | null Reason why the verification failed
reason : string | null Reason why the verification failed
reasonCode : integer | null Reason code of the failed verification. For more info, see the Granular reason codes (table) .
reasonCode : integer | null Reason code of the failed verification. For more info, see the Granular reason codes (table) .
decisionTime : string | null Timestamp of the decision, represented as UTC YYYY-MM-DDTHH:MM:SS.SSS+Timezone Offset (ISO 8601)
decisionTime : string | null Timestamp of the decision, represented as UTC YYYY-MM-DDTHH:MM:SS.SSS+Timezone Offset (ISO 8601)
acceptanceTime : string Timestamp of the session generation, represented as UTC YYYY-MM-DDTHH:MM:SS.SSS+Timezone Offset (ISO 8601)
acceptanceTime : string Timestamp of the session generation, represented as UTC YYYY-MM-DDTHH:MM:SS.SSS+Timezone Offset (ISO 8601)
submissionTime : string Timestamp of when the session was submitted, represented as UTC YYYY-MM-DDTHH:MM:SS.SSSSSS+Timezone Offset (ISO 8601)
submissionTime : string Timestamp of when the session was submitted, represented as UTC YYYY-MM-DDTHH:MM:SS.SSSSSS+Timezone Offset (ISO 8601)
person : object Data the verified person. For Presence Verification, every field in this object is null . firstName : string | null Person's first name as written on the document lastName : string | null Person's last name as written on the document dateOfBirth : string | null Person's date of birth, represented as YYYY-MM-DD gender : string | null Person's gender, represented as M, F or X, or null if not present nationality : string | null Person's nationality, represented as ISO 3166 alpha-2 or alpha-3 number idNumber : string | null National identification number yearOfBirth : string | null Person's year of birth, represented as YYYY placeOfBirth : string | null Person's place of birth pepSanctionMatch : string | null Legacy field, may return incorrect result, should be ignored citizenship : null Deprecated, always returns null
person : object Data the verified person. For Presence Verification, every field in this object is null .
firstName : string | null Person's first name as written on the document
firstName : string | null Person's first name as written on the document
lastName : string | null Person's last name as written on the document
lastName : string | null Person's last name as written on the document
dateOfBirth : string | null Person's date of birth, represented as YYYY-MM-DD
dateOfBirth : string | null Person's date of birth, represented as YYYY-MM-DD
gender : string | null Person's gender, represented as M, F or X, or null if not present
gender : string | null Person's gender, represented as M, F or X, or null if not present
nationality : string | null Person's nationality, represented as ISO 3166 alpha-2 or alpha-3 number
nationality : string | null Person's nationality, represented as ISO 3166 alpha-2 or alpha-3 number
idNumber : string | null National identification number
idNumber : string | null National identification number
yearOfBirth : string | null Person's year of birth, represented as YYYY
yearOfBirth : string | null Person's year of birth, represented as YYYY
placeOfBirth : string | null Person's place of birth
placeOfBirth : string | null Person's place of birth
pepSanctionMatch : string | null Legacy field, may return incorrect result, should be ignored
pepSanctionMatch : string | null Legacy field, may return incorrect result, should be ignored
citizenship : null Deprecated, always returns null
citizenship : null Deprecated, always returns null
document : object Verified document. For Presence Verification, every field in this object is null . number : string | null Document number, [a-zA-Z0-9] characters only type : string | null Document type, one of PASSPORT , ID_CARD , RESIDENCE_PERMIT , DRIVERS_LICENSE , VISA , OTHER country : string | null Document issuing country, represented as ISO 3166 alpha-2 code state : string | null Document issuing state, represented as ISO 3166 alpha-2 or alpha-3 code validFrom : string | null Document is valid from date validUntil : string | null Document is valid until date
document : object Verified document. For Presence Verification, every field in this object is null .
number : string | null Document number, [a-zA-Z0-9] characters only
number : string | null Document number, [a-zA-Z0-9] characters only
type : string | null Document type, one of PASSPORT , ID_CARD , RESIDENCE_PERMIT , DRIVERS_LICENSE , VISA , OTHER
type : string | null Document type, one of PASSPORT , ID_CARD , RESIDENCE_PERMIT , DRIVERS_LICENSE , VISA , OTHER
country : string | null Document issuing country, represented as ISO 3166 alpha-2 code
country : string | null Document issuing country, represented as ISO 3166 alpha-2 code
state : string | null Document issuing state, represented as ISO 3166 alpha-2 or alpha-3 code
state : string | null Document issuing state, represented as ISO 3166 alpha-2 or alpha-3 code
validFrom : string | null Document is valid from date
validFrom : string | null Document is valid from date
validUntil : string | null Document is valid until date
validUntil : string | null Document is valid until date
additionalVerifiedData : object Data that has been optionally verified for the session. Empty {} for Presence Verification.
additionalVerifiedData : object Data that has been optionally verified for the session. Empty {} for Presence Verification.
: array (Deprecated) Always returns empty []
: array (Deprecated) Always returns empty []
technicalData : object Technical data object ip : string | null IP of the device from which the verification was made
technicalData : object Technical data object
ip : string | null IP of the device from which the verification was made
ip : string | null IP of the device from which the verification was made
The example below uses placeholder data to show all mandatory parameters and possible Presence Verification fields . While mandatory fields are always present, solution-specific keys are omitted if a feature is disabled or data extraction fails. Depending on your integration's configuration , your production payload may contain additional parameters . For other parameters you might see, check the GET /sessions/{sessionId}/decision documentation.
Click to open GET /decision response payload and field explanations
Response properties explained
status : string Status of the response
status : string Status of the response
verification : object Verification request decision object. null if decision is not available yet. id : string UUID v4 which identifies the verification session attemptId : string UUID v4 of the attempt which received a status (as shown in verification.status field) vendorData : string | null The unique identifier that you created for your end-user. null if not specified. endUserId : string | null The UUID that you created for your end-user. null if not specified. status : string Verification status, one of approved , declined , resubmission_requested , expired , abandoned code : integer Verification session decision code, one of 9001 , 9102 , 9103 , 9104 . For more info, see the Verification session decision codes (table) . reason : string | null Reason why the verification failed reasonCode : integer | null Reason code of the failed verification. For more info, see the Granular reason codes (table) . decisionTime : string | null Timestamp of the decision, represented as UTC YYYY-MM-DDTHH:MM:SS.SSS+Timezone Offset (ISO 8601) acceptanceTime : string Timestamp of the session generation, represented as UTC YYYY-MM-DDTHH:MM:SS.SSS+Timezone Offset (ISO 8601) submissionTime : string Timestamp of when the session was submitted, represented as UTC YYYY-MM-DDTHH:MM:SS.SSSSSS+Timezone Offset (ISO 8601) person : object Data the verified person. For Presence Verification, every field in this object is null . firstName : string | null Person's first name as written on the document lastName : string | null Person's last name as written on the document dateOfBirth : string | null Person's date of birth, represented as YYYY-MM-DD gender : string | null Person's gender, represented as M, F or X, or null if not present nationality : string | null Person's nationality, represented as ISO 3166 alpha-2 or alpha-3 number idNumber : string | null National identification number yearOfBirth : string | null Person's year of birth, represented as YYYY placeOfBirth : string | null Person's place of birth pepSanctionMatch : string | null Legacy field, may return incorrect result, should be ignored citizenship : null Deprecated, always returns null document : object Verified document. For Presence Verification, every field in this object is null . number : string | null Document number, [a-zA-Z0-9] characters only type : string | null Document type, one of PASSPORT , ID_CARD , RESIDENCE_PERMIT , DRIVERS_LICENSE , VISA , OTHER country : string | null Document issuing country, represented as ISO 3166 alpha-2 code state : string | null Document issuing state, represented as ISO 3166 alpha-2 or alpha-3 code validFrom : string | null Document is valid from date validUntil : string | null Document is valid until date additionalVerifiedData : object Data that has been optionally verified for the session. Empty {} for Presence Verification. : array (Deprecated) Always returns empty []
verification : object Verification request decision object. null if decision is not available yet.
id : string UUID v4 which identifies the verification session
id : string UUID v4 which identifies the verification session
attemptId : string UUID v4 of the attempt which received a status (as shown in verification.status field)
attemptId : string UUID v4 of the attempt which received a status (as shown in verification.status field)
vendorData : string | null The unique identifier that you created for your end-user. null if not specified.
vendorData : string | null The unique identifier that you created for your end-user. null if not specified.
endUserId : string | null The UUID that you created for your end-user. null if not specified.
endUserId : string | null The UUID that you created for your end-user. null if not specified.
status : string Verification status, one of approved , declined , resubmission_requested , expired , abandoned
status : string Verification status, one of approved , declined , resubmission_requested , expired , abandoned
code : integer Verification session decision code, one of 9001 , 9102 , 9103 , 9104 . For more info, see the Verification session decision codes (table) .
code : integer Verification session decision code, one of 9001 , 9102 , 9103 , 9104 . For more info, see the Verification session decision codes (table) .
reason : string | null Reason why the verification failed
reason : string | null Reason why the verification failed
reasonCode : integer | null Reason code of the failed verification. For more info, see the Granular reason codes (table) .
reasonCode : integer | null Reason code of the failed verification. For more info, see the Granular reason codes (table) .
decisionTime : string | null Timestamp of the decision, represented as UTC YYYY-MM-DDTHH:MM:SS.SSS+Timezone Offset (ISO 8601)
decisionTime : string | null Timestamp of the decision, represented as UTC YYYY-MM-DDTHH:MM:SS.SSS+Timezone Offset (ISO 8601)
acceptanceTime : string Timestamp of the session generation, represented as UTC YYYY-MM-DDTHH:MM:SS.SSS+Timezone Offset (ISO 8601)
acceptanceTime : string Timestamp of the session generation, represented as UTC YYYY-MM-DDTHH:MM:SS.SSS+Timezone Offset (ISO 8601)
submissionTime : string Timestamp of when the session was submitted, represented as UTC YYYY-MM-DDTHH:MM:SS.SSSSSS+Timezone Offset (ISO 8601)
submissionTime : string Timestamp of when the session was submitted, represented as UTC YYYY-MM-DDTHH:MM:SS.SSSSSS+Timezone Offset (ISO 8601)
person : object Data the verified person. For Presence Verification, every field in this object is null . firstName : string | null Person's first name as written on the document lastName : string | null Person's last name as written on the document dateOfBirth : string | null Person's date of birth, represented as YYYY-MM-DD gender : string | null Person's gender, represented as M, F or X, or null if not present nationality : string | null Person's nationality, represented as ISO 3166 alpha-2 or alpha-3 number idNumber : string | null National identification number yearOfBirth : string | null Person's year of birth, represented as YYYY placeOfBirth : string | null Person's place of birth pepSanctionMatch : string | null Legacy field, may return incorrect result, should be ignored citizenship : null Deprecated, always returns null
person : object Data the verified person. For Presence Verification, every field in this object is null .
firstName : string | null Person's first name as written on the document
firstName : string | null Person's first name as written on the document
lastName : string | null Person's last name as written on the document
lastName : string | null Person's last name as written on the document
dateOfBirth : string | null Person's date of birth, represented as YYYY-MM-DD
dateOfBirth : string | null Person's date of birth, represented as YYYY-MM-DD
gender : string | null Person's gender, represented as M, F or X, or null if not present
gender : string | null Person's gender, represented as M, F or X, or null if not present
nationality : string | null Person's nationality, represented as ISO 3166 alpha-2 or alpha-3 number
nationality : string | null Person's nationality, represented as ISO 3166 alpha-2 or alpha-3 number
idNumber : string | null National identification number
idNumber : string | null National identification number
yearOfBirth : string | null Person's year of birth, represented as YYYY
yearOfBirth : string | null Person's year of birth, represented as YYYY
placeOfBirth : string | null Person's place of birth
placeOfBirth : string | null Person's place of birth
pepSanctionMatch : string | null Legacy field, may return incorrect result, should be ignored
pepSanctionMatch : string | null Legacy field, may return incorrect result, should be ignored
citizenship : null Deprecated, always returns null
citizenship : null Deprecated, always returns null
document : object Verified document. For Presence Verification, every field in this object is null . number : string | null Document number, [a-zA-Z0-9] characters only type : string | null Document type, one of PASSPORT , ID_CARD , RESIDENCE_PERMIT , DRIVERS_LICENSE , VISA , OTHER country : string | null Document issuing country, represented as ISO 3166 alpha-2 code state : string | null Document issuing state, represented as ISO 3166 alpha-2 or alpha-3 code validFrom : string | null Document is valid from date validUntil : string | null Document is valid until date
document : object Verified document. For Presence Verification, every field in this object is null .
number : string | null Document number, [a-zA-Z0-9] characters only
number : string | null Document number, [a-zA-Z0-9] characters only
type : string | null Document type, one of PASSPORT , ID_CARD , RESIDENCE_PERMIT , DRIVERS_LICENSE , VISA , OTHER
type : string | null Document type, one of PASSPORT , ID_CARD , RESIDENCE_PERMIT , DRIVERS_LICENSE , VISA , OTHER
country : string | null Document issuing country, represented as ISO 3166 alpha-2 code
country : string | null Document issuing country, represented as ISO 3166 alpha-2 code
state : string | null Document issuing state, represented as ISO 3166 alpha-2 or alpha-3 code
state : string | null Document issuing state, represented as ISO 3166 alpha-2 or alpha-3 code
validFrom : string | null Document is valid from date
validFrom : string | null Document is valid from date
validUntil : string | null Document is valid until date
validUntil : string | null Document is valid until date
additionalVerifiedData : object Data that has been optionally verified for the session. Empty {} for Presence Verification.
additionalVerifiedData : object Data that has been optionally verified for the session. Empty {} for Presence Verification.
: array (Deprecated) Always returns empty []
: array (Deprecated) Always returns empty []
technicalData : object Technical data object ip : string | null IP of the device from which the verification was made
technicalData : object Technical data object
ip : string | null IP of the device from which the verification was made
ip : string | null IP of the device from which the verification was made
Veriff Customer Portal
You can find the verification session related info, including the decision, in the Veriff Customer Portal , under the session's Webhooks tab.
→ See Review verification in Veriff Customer Portal how to view the session info in the Veriff Customer portal
Status and reason codes
For an approved session, see:
verification.code verification session decision code, one of 9001 , 9102 , 9103 , 9104
verification.code verification session decision code, one of 9001 , 9102 , 9103 , 9104
verification.status verification status, one of approved , declined , resubmission_requested , expired , abandoned
verification.status verification status, one of approved , declined , resubmission_requested , expired , abandoned
If the Presence Verification session was declined or resubmission_requested , you can find additional information by checking:
verification.reason for the reason why the verification failed
verification.reason for the reason why the verification failed
verification.reasonCode for reason code of the failed verification and cross-reference it with Granular reason codes (table)
verification.reasonCode for reason code of the failed verification and cross-reference it with Granular reason codes (table)
verification.reasonCode
Signs of third-party guidance during the session
Signs were detected that another person guided the end-user during the session. Returned only with Presence Verification with Coercion Detection.
Multiple parties present in session
A second person was visible in the session video
The inputs appear not genuine
Attempted injection attack
Pre-recorded, synthetic, or manipulated media was fed into the session
Attempted deceit, photos streamed
Photos were streamed into the session instead of a live capture
Other fraudulent behaviour was detected
Velocity/abuse duplicated device
The device was already used in other sessions. Returned only if velocity protection is enabled.
Restricted IP location
The session came from a restricted IP location. Returned only if enabled for your integration.
resubmission_requested
The selfie video is missing. Ask the end-user to try again.
resubmission_requested
The face image is missing. Ask the end-user to try again.
resubmission_requested
Face is not clearly visible
The face is not clearly visible. Ask the end-user to try again in good lighting.
resubmission_requested
Face not clearly visible
The face is not clearly visible. Ask the end-user to try again in good lighting.
resubmission_requested
Multiple parties are present in the session
More than one face is present in the selfie. Ask the end-user to try again alone.
Depending on your configuration, you may also see other existing codes, for example 108 (duplicated end-user), 110 (duplicated ID), or 539 (resubmission limit exceeded).
The table above aims to list the most common reasons why you may see the decline reason for a Presence Verification session. However, the session may be declined due to a reason that is not inherently Presence Verification related. In that case, to find info the codes you are seeing, refer to:
Verification session status codes (table)
Verification session status codes (table)
Verification session decision codes (table)
Verification session decision codes (table)
Granular reason codes (table)
Granular reason codes (table)
Additional information
Use a native SDK : Veriff strongly recommends the iOS and Android SDKs over the web flow, because the checks rely on the media and device signals the SDK captures. The API alone cannot run this solution; it only creates the session.
Camera and microphone access : Make sure the end-user can grant camera access, and microphone access if you use Presence Verification with Coercion Detection, and explain in your app why they are needed. Without audio, the third-party guidance assessment cannot run. Adding Coercion Detection to an existing integration introduces a new runtime permission prompt and may require updating your app's privacy disclosures to cover audio capture.
Selfie image quality : ensure that end-user's selfie image is of good quality. This will reduce the possibility of session going to resubmission_requested .
Send an endUserId or vendorData : Create and send an endUserId or vendorData for every session.
Decision logic : Drive your logic from verification.code and verification.status . Treat verification.reasonCode as an open set that can gain new values, and handle unknown codes gracefully.
Third-party guidance declines : Treat 589 like other fraud-related declines in your risk handling.
Webhook first, polling as backup : Use the decision webhook as the primary channel, and GET /sessions/{sessionId}/decision as a fallback.
Error handling : Implement proper error handling for all possible validation results.
Webhook security : Secure your webhook endpoint and verify request signatures
User experience : Provide clear feedback to end-users validation results
Ensure Backwards compatible changes for webhooks and API connections
How is Presence Verification different from IDV and Biometric Authentication?
IDV answers "who is this person" using an identity document. Biometric Authentication answers "is this the same person as before" by matching against a session. Presence Verification uses no document and does no matching: it helps establish that a real person is present and acting on their own right now.
Can I use Presence Verification via the API or the web flow?
You cannot use the API alone: the API only creates the session. Web flow is supported, but Veriff strongly recommends native SDKs (iOS and Android) instead, because the checks rely on the media and device signals the SDK captures.
Does the third-party guidance check ever request a resubmission?
No. It results either in a pass or in a declined decision with reason code 589 .
What happens if the end-user denies microphone access or there is no audio?
The session is not declined for third-party guidance because audio is missing.
Can I retrieve the media the end-user submitted?
Yes, with the existing media endpoints: GET /v1/sessions/{sessionId}/media , GET /v1/attempts/{attemptId}/media , and GET /v1/media/{mediaId} . Data retention policies apply.
Which languages does the audio assessment support?
The audio assessment used in Presence Verification with Coercion Detection supports the following languages.
Documentation published
Veriff customer back-office, a dashboard where you can see your end-users' verification data.
Depending on your setup, you may be required to access the environment via station.veriff.com or hub.veriff.com. Always check your sign-up email and make sure that you log in via correct address .
A UUID-format unique identifier ([0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}) created by you for your end-user to link an end-user to their session(s). Cannot be resolved outside your environment.
Veriff stores it only for identity verification and returns it unchanged in webhooks/API responses or as null if not provided.
Strongly recommended if you already use UUID identifiers. Works as an alternative to vendorData in Biometric Authentication solution.
A custom unique identifier (max 1,000 characters) created by you, containing only non-semantic data that can't be resolved outside your systems.
Veriff returns it unchanged in webhooks/API responses or as null if not provided.
It's referred to as "unique identifier" in Customer Portal and cannot be changed once set.
Required for Fraud solutions (Cross Links check and Velocity Abuse check) and serves as an alternative to endUserId in Biometric Authentication when using non-UUID identifiers.
A session during which the end-user is verified. It starts when a session is created, it can contain several attempts (i.e. steps of uploading media, sending additional data etc.) and it ends when a conclusive decision (“approved”, “declined”, “expired”/”abandoned”) is granted.
Each verification session receives an unique ID, aka the session ID , which can be added to the API URL when making API requests.
This where the end-user is directed to go through the verification flow, and it is unique for each verification session .
It is a combination of the base URL and the sessionToken , created as soon as a verification session is created. You can find its value in the response payload of your POST /sessions call, as verification.url .
The data that you send when you make an API request, or that you receive when you get a response.
The full story
This article is one source in a clustered incident — the cluster page carries the summary, timeline and every other outlet covering it.
