Synchronizing
Architectural Primitives

Dynamic link verification

Use your backend to mint a short-lived hosted link that opens the Sentinel verification portal for a specific customer. Your frontend opens that link, the customer completes liveness, document capture, and review on the portal, and status changes come back to you by webhook or polling. Your client secret never reaches the browser.

Architecture at a glance

Four actors are involved.

  • Your backend holds clientUuid and clientSecret, calls POST /clients/encrypt/url, and forwards the returned URL to your frontend.
  • Your frontend receives the URL and opens it. It never sees the secret.
  • Sentinel validates your credentials, encrypts the payload, and serves the portal, the status endpoints, and webhook delivery.
  • The hosted portal is the verification flow the customer actually uses, themed for your tenant.

Create the link

Mint the link from your backend so clientSecret never touches the browser. Send a POST with your credentials and, optionally, the customer's contact details and a document scope.

http
POST https://api.sentinel.example.com/clients/encrypt/url
FieldTypeDescription
clientUuidrequiredstringYour client identifier, a UUID.
clientSecretrequiredstringYour client secret. Minimum 15 characters. Server-side only.
emailstringRequired if phoneNumber is absent. Valid email, 10 to 254 characters.
phoneNumberstringRequired if email is absent. Valid mobile number format.
documentsstring[]Optional. Restricts the document picker. See the documents enum below.

Example request:

request
{
  "clientUuid": "xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx",
  "clientSecret": "xxxxxxxxxxxxxxxx",
  "phoneNumber": "+971501234567",
  "email": "jane.doe@example.com",
  "documents": ["passport", "emiratesId"]
}

Response (200):

response
{
  "message": "Success",
  "data": "https://verify.sentinel.example.com?data=<encrypted-token>"
}
Use the returned URL verbatim
The host inside data can vary by client configuration. Always open the URL the API returns, exactly as given. Do not hardcode the portal host on your side.

Documents

The optional documents array restricts which identity documents the customer can upload.

  • passport: only passport upload is offered.
  • emiratesId: only Emirates ID upload is offered.
  • egyptNationalId: accepted by the API, but the portal does not render it yet.

Combinations are allowed, for example ["passport", "emiratesId"]. Omitting the field is equivalent to passing both passport and Emirates ID. You can also set a default document scope from your dashboard, so this field is optional for most integrations.

Wire up the flow

Expose a thin endpoint on your backend that calls Sentinel, then have your frontend call that endpoint and open the returned URL.

Your backend mints the URL on demand:

javascript
// Node / Express, using an HTTP client (for example axios)
app.post('/verification/link', async (req, res) => {
  const { phoneNumber, email } = req.body

  const response = await http.post(
    'https://api.sentinel.example.com/clients/encrypt/url',
    {
      clientUuid: process.env.SENTINEL_CLIENT_UUID,
      clientSecret: process.env.SENTINEL_CLIENT_SECRET,
      phoneNumber, // or email
    },
  )

  // The hosted link is in response.data.data
  res.json({ url: response.data.data })
})

Your frontend calls your backend, then opens the returned URL:

javascript
async function startVerification() {
  const { url } = await http.post('/verification/link', { phoneNumber })
  window.open(url, '_blank')
}

Redirect after completion

To send the customer somewhere after they finish, append &redirectUrl= with an absolute URL to the link your backend returned. HTTPS URLs and custom app schemes (deep links back into a mobile app) are both accepted. URL-encode the value if it carries query parameters of its own.

text
https://verify.sentinel.example.com?data=<encrypted-token>&redirectUrl=https://yourapp.example.com/verify/done

When the journey ends, the portal shows a brief confirmation for about five seconds, then performs a full-page navigation to your URL with a status query parameter appended. Query parameters already on your URL are preserved; a status parameter of your own would be overwritten.

text
https://yourapp.example.com/verify/done?status=success
yourapp://verify/done?status=failed
  • status=success: the customer completed and submitted a verification in this session.
  • status=failed: the journey ended without a new submission. This also covers an already-verified customer re-opening a link, so read it as "no new verification", not necessarily as a rejection.

The redirect target is remembered for the lifetime of the browser session, so it survives page reloads during the journey.

No parent-window message
The portal does not emit a postMessage to a parent window. If you open it in an iframe or popup and need a signal on the parent side, rely on the webhook or polling endpoints instead.
The redirect is not proof of verification
The redirect and its status parameter are a front-end convenience. status=success means a submission completed, not that screening passed. Always confirm the outcome through a webhook or result retrieval before granting access.

Per-client settings

The portal reads several settings on load and adapts. Some come from the encrypt request, others from your client configuration.

SettingSourceEffect
documentsEncrypt requestRestricts the document picker for this link.
theme.primaryClient configBrand color across buttons, accents, focus rings, and progress.
theme.backgroundPrimaryClient configBase background. Light or dark mode is derived from this value.
modifiableSignupIdentifiersClient configWhich of phoneNumber and email stay editable on the review screen when pre-filled. Identifiers not listed are locked.

Default documents and modifiable identifiers are managed from your dashboard. Brand theme colors are not yet self-serve, so contact the Sentinel team to set them for your tenant.

Notes

  • clientSecret is server-side only. Never embed it in frontend code, mobile app bundles, or query strings.
  • The theme comes from your client configuration. Do not assume a fixed palette.
  • Use the returned URL verbatim. The host can differ per client.
Next
Connect outcomes with Webhooks and callbacks, or read them on demand with Retrieving results.