Referência da API do Live ID

Endpoints do Live ID Validation — emita uma Chave de Identificação, crie uma sessão de captura, abra a página de captura hospedada, envie uma selfie, consulte o resultado e o payload do webhook de validação.

Três superfícies: gestão de chaves (autenticada pelo painel, para administradores), o ciclo de vida da sessão (autenticado por chave e por token de sessão, público) e o webhook. A URL base abaixo é o host da sua organização.

Os endpoints de sessão ficam em /api/kyc/public/live-id e não são autenticados por chave de API — eles são protegidos pela Chave de Identificação (na criação) ou pelo token de sessão de uso único (na validação e na consulta), e têm limite de requisições por IP.

Emitir uma Chave de Identificação

POST /api/kyc/live-id/:orgSlug/keys    Autenticação: sessão do painel (administrador/proprietário)

Emite uma chave por perfil. O token em texto puro é retornado uma única vez — guarde-o com segurança no seu backend; somente o hash dele é mantido.

Corpo da requisição

{ "applicantId": "app_…", "label": "mobile-app", "expiresInDays": 365 }
CampoTipoObrigatórioObservações
enrollmentIdstringum dos doisO id de cadastro do Live ID.
applicantIdstringum dos doisO id do solicitante de KYC (resolvido para o cadastro dele).
labelstringnãoRótulo de texto livre para a sua própria referência.
expiresInDaysintegernãoDe 1 a 3650. Omita para não expirar.

Resposta 201

{
  "id": "lik_…",
  "token": "livid_…",          // shown ONCE
  "keyVersion": 1,
  "label": "mobile-app",
  "expiresAt": null,
  "createdAt": "2026-06-18T12:00:00.000Z"
}

Endpoints relacionados: GET /api/kyc/live-id/:orgSlug/keys (lista, somente metadados), DELETE /api/kyc/live-id/:orgSlug/keys/:id (revoga) e GET /api/kyc/live-id/:orgSlug/enrollments (lista os perfis cadastrados).

Criar uma sessão

POST /api/kyc/public/live-id/sessions    Autenticação: Chave de Identificação (no corpo)

Chame este endpoint no servidor. Ele verifica a chave, aplica a checagem de faturamento e cria um token de sessão de uso único.

Corpo da requisição

{ "key": "livid_…", "deviceFingerprint": "optional", "captureMethod": "live_camera" }

Resposta 201

{
  "sessionId": "lis_…",
  "sessionToken": "…",
  "expiresAt": "2026-06-18T12:02:00.000Z",
  "captureUrl": "https://app.certivant.com/live-id/…",
  "nonce": "…"
}

Entregue o captureUrl ao dispositivo. O sessionToken também é retornado para que você possa consultar o status no servidor. O nonce é o valor de uso único da sessão — só é necessário se você criar sua própria interface de captura (veja Enviar uma selfie).

A criação é recusada com 429 enrollment_locked enquanto o perfil estiver bloqueado após repetidas validações com falha (5 falhas em 15 minutos bloqueiam o perfil por 30 minutos e disparam live_id.enrollment.locked).

Abrir a página de captura

GET /live-id/:sessionToken    Autenticação: token de sessão (no caminho)

A página de captura hospedada, otimizada para celular — abra-a no nível superior: em um pop-up, por meio de um redirecionamento ou em um WebView nativo. Ela é servida com frame-ancestors 'none', então não pode ser incorporada em iframe. Ela mostra a interface da câmera e da selfie quando a sessão está ativa, e um aviso claro quando a sessão expirou, é inválida ou já foi concluída.

Ao carregar, a página hospedada chama POST /api/kyc/public/live-id/sessions/:sessionToken/open. Esse passo registra o endereço IP do dispositivo e retorna o valor de uso único da sessão, que a página envia de volta junto com a selfie. A partir daí, uma selfie enviada sem o valor correto é recusada.

Abrir uma captura (apenas para interface de captura própria)

POST /api/kyc/public/live-id/sessions/:sessionToken/open    Autenticação: token de sessão (no caminho)

Chame isto a partir do dispositivo quando a sua própria tela de captura abrir. Resposta 200:

{ "nonce": "…", "expiresAt": "2026-06-18T12:02:00.000Z" }

Enviar uma selfie

POST /api/kyc/public/live-id/validate    Autenticação: token de sessão (no corpo)

A página hospedada chama este endpoint por você. Documente-o somente se você criar sua própria interface nativa de captura, em vez de usar a página hospedada.

Corpo da requisição

{ "sessionToken": "…", "selfieImage": "data:image/jpeg;base64,/9j/4AAQ…", "nonce": "…" }

selfieImage aceita uma string base64 ou uma URL data:. Mínimo de ~1 KB, máximo de 8 MB.

nonce é o valor de uso único da sessão (da resposta de criação ou de /open):

  • Um valor incorreto é sempre recusado (reason: "nonce_mismatch", matched: false).
  • Um valor ausente só é recusado quando a captura foi aberta com /open (a página hospedada sempre faz isso). Integrações servidor-a-servidor que nunca chamam /open continuam funcionando sem ele — mas enviá-lo é recomendado.

A mesma selfie nunca pode ser usada duas vezes: uma cópia exata da foto de referência cadastrada ou da selfie de uma sessão anterior é recusada (reason: "replayed_image"). Cópias quase idênticas são informadas em riskSignals no webhook.

Resposta 200

{
  "matched": true,
  "faceMatchScore": 0.94,
  "livenessScore": 0.98,
  "livePassed": true,
  "reason": "matched",
  "sessionId": "lis_…"
}

reason é um dos seguintes valores: matched, face_below_threshold, liveness_failed, face_and_liveness_failed, no_reference_image, nonce_mismatch, replayed_image, near_duplicate_image.

Consultar uma sessão

GET /api/kyc/public/live-id/sessions/:sessionToken    Autenticação: token de sessão (no caminho)

Resposta 200

{
  "sessionId": "lis_…",
  "status": "completed",
  "matched": true,
  "faceMatchScore": 0.94,
  "livenessScore": 0.98,
  "reason": "matched",
  "expiresAt": "2026-06-18T12:02:00.000Z"
}

status: pending → processing → completed (ou expired). Quando completed, matched é o veredito. Consulte a cada ~2 s; pare em completed ou expired.

Webhook — live_id.validation.completed

Disparado uma vez por validação concluída, para a URL de webhook da sua organização, assinado exatamente como os demais webhooks da Certivant (X-Certivant-Signature-V2: t=…,v1=…; o cabeçalho mais antigo X-KYC-Signature: sha256=… ainda é enviado).

{
  "event": "live_id.validation.completed",
  "organizationId": "org_…",
  "validationId": "liv_…",
  "sessionId": "lis_…",
  "enrollmentId": "lie_…",
  "applicantId": "app_…",
  "matched": true,
  "faceMatchScore": 0.94,
  "livenessScore": 0.98,
  "decisionReason": "matched",
  "riskSignals": {
    "nearDuplicateImage": false,
    "nearestImageDistance": 0.21,
    "nearestImageSource": "previous_session",
    "nonceVerified": true,
    "deviceIpChanged": false
  },
  "timestamp": "2026-06-18T12:02:00.000Z"
}

riskSignals servem para a sua própria decisão de risco — eles nunca alteram matched por conta própria. nonceVerified é verdadeiro quando a selfie continha o valor de uso único da sessão; deviceIpChanged é verdadeiro quando o IP do dispositivo mudou entre /open e a selfie (null quando não é possível comparar).

Webhook — live_id.enrollment.locked

Disparado quando um perfil é bloqueado após repetidas validações com falha.

{
  "event": "live_id.enrollment.locked",
  "organizationId": "org_…",
  "enrollmentId": "lie_…",
  "applicantId": "app_…",
  "failures": 5,
  "lockedUntil": "2026-06-18T12:32:00.000Z",
  "timestamp": "2026-06-18T12:02:00.000Z"
}

Veja Webhooks → Verificação de assinatura.

Erros

StatusCódigoSignificado
401invalid_key / unknown_key / key_mismatchA Chave de Identificação foi adulterada, não é reconhecida ou suas declarações não correspondem.
403key_revoked / key_expiredA chave foi revogada ou expirou.
403live_id_disabledO Live ID não está habilitado para a organização.
402verification_unavailableAcima da cota e o saldo da conta não cobre a cobrança PAYG (continuar sem crédito desativado). O corpo também traz error.organization (name, logoUrl); a mensagem nunca menciona faturamento, então pode ser exibida ao seu usuário.
409enrollment_inactiveO perfil não está cadastrado (ou não está mais).
429enrollment_lockedMuitas validações com falha — tente novamente após o fim do bloqueio.
404unknown_sessionNão há sessão para esse token.
409session_consumedA sessão já foi usada ou está em andamento.
410session_expiredO token de sessão expirou antes de a selfie chegar.
503biometric_unconfiguredO provedor biométrico da organização não está configurado.