Skip to content

Verify a document

Use a standalone Document when you need a result for one file without evaluating a worker’s complete compliance case. This is the smallest complete Dockt workflow and a good way to validate your integration before adding Assessments.

By the end of this guide, your backend will upload a file, wait for asynchronous processing, distinguish processing failure from an invalid result, and read the structured details behind the result.

  1. Your backend uploads one PDF or image and receives a Document ID.
  2. Dockt processes the file after the upload request has returned.
  3. Your backend waits for completed, failed, or withdrawn by polling or receiving a webhook.
  4. For a completed Document, your product branches on document_result and uses the accompanying details to explain or review it.

The Document ID connects every step. Store it as soon as the upload succeeds.

You need a workspace credential with documents:create and documents:read. Export its bearer token and the API base URL:

Terminal window
export DOCKT_API_BASE_URL='https://api.dockt.com'
export DOCKT_API_TOKEN='REPLACE_WITH_BEARER_TOKEN'

Prepare one non-empty supported file no larger than 10 MB. This guide uses ./document.pdf. See Document uploads and evidence for accepted file formats.

The API call must come from your backend. Don’t send the Dockt bearer token to a browser or mobile client, and don’t place document bytes in application logs.

Send one file part and an idempotency key that identifies this upload in your system:

Terminal window
document_response="$(
curl --fail-with-body --silent --show-error \
-X POST "$DOCKT_API_BASE_URL/v1/documents" \
-H "Authorization: Bearer $DOCKT_API_TOKEN" \
-H 'Idempotency-Key: document-case-1042-primary' \
-F 'file=@./document.pdf;type=application/pdf'
)"
export DOCKT_DOCUMENT_ID="$(printf '%s' "$document_response" | jq -r '.data.id')"
printf '%s' "$document_response" | jq '.data | {id, status, filename}'

Dockt returns 202 Accepted with the new Document in a single-resource response envelope. Store data.id; it is the canonical Document ID for polling, webhook reconciliation, and later reads.

The initial status is normally uploaded or processing. There is no document_result to act on until the status becomes completed.

The response fields become useful at different points in the lifecycle:

FieldBefore completionAfter completed
statusuploaded or processingcompleted
document_resultnullvalid, review_required, or invalid
classified_as and evidence detailsCan be null or emptyContain the available result details
completed_atnullCompletion date and time

The Create document response shows the complete accepted-upload shape. The Get document response shows the canonical read shape.

Poll the Document with backoff while status is uploaded or processing:

Terminal window
while true; do
document_response="$(
curl --fail-with-body --silent --show-error \
-H "Authorization: Bearer $DOCKT_API_TOKEN" \
"$DOCKT_API_BASE_URL/v1/documents/$DOCKT_DOCUMENT_ID"
)"
document_status="$(printf '%s' "$document_response" | jq -r '.data.status')"
printf 'Document status: %s\n' "$document_status"
case "$document_status" in
completed|failed|withdrawn) break ;;
uploaded|processing) sleep 5 ;;
*) printf 'Unexpected status: %s\n' "$document_status" >&2; exit 1 ;;
esac
done

For production workloads, prefer the document.completed and document.failed webhooks and use polling as recovery. A webhook is a notification that state changed, so fetch the Document by ID before applying an important action.

Stop polling when your application’s own waiting deadline expires. Keep the Document unresolved and reconcile it later; elapsed time does not change the Document to failed.

If status is failed, processing didn’t produce a document verdict. Inspect issues, retain the response x-request-id, and decide whether to ask for a clearer file, retry the upload as a new logical operation, or send the case to manual review.

Don’t treat failed as invalid. A processing failure isn’t a conclusion about the document’s validity.

For a completed Document, inspect the result and actionable fields:

Terminal window
printf '%s' "$document_response" | jq '.data | {
document_result,
classified_as,
facts,
verifications,
enrichment,
credential_assertions,
issues,
fraud_signals,
findings
}'

Use document_result as the first branch in your application and handle every value:

  • valid: Continue the workflow, while still displaying relevant informational Findings.
  • review_required: Route the Document to a reviewer and show its issues and Findings.
  • invalid: Stop or escalate the workflow according to your policy and show the reasons.

After choosing the branch, use findings, issues, and fraud_signals to explain why it was selected. classified_as and facts describe what Dockt detected and extracted. verifications, enrichment, and credential_assertions provide additional supporting detail when applicable.

Not every Document produces every detail. Empty optional collections are normal and shouldn’t be treated as processing errors.

An unsupported document type completes as review_required with a type_unknown issue. Ask for another document or route the case to review.

Treat enrichment.status and its checks separately from document_result. Enrichment warnings provide additional context and don’t automatically override an intrinsic valid result.

Store at least:

  • Your source record ID.
  • data.id as the Dockt Document ID.
  • The latest status and document_result.
  • The x-request-id for failed API requests.

Keep the full response when your retention policy permits it. Don’t store or log the bearer token with the result.

If your product acts automatically, also store the result and response version it acted on. For a review workflow, keep the Document ID so the reviewer can fetch the current canonical response rather than relying on a webhook payload.

With documents:delete, withdraw a Document that should no longer participate in active use:

Terminal window
curl --fail-with-body --silent --show-error \
-X DELETE \
-H "Authorization: Bearer $DOCKT_API_TOKEN" \
"$DOCKT_API_BASE_URL/v1/documents/$DOCKT_DOCUMENT_ID" | jq

The response confirms deleted: true. Earlier Assessment Decisions, if any, remain immutable.