> For the complete documentation index, see [llms.txt](https://docs.truecaller.com/truecaller-sdk/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://docs.truecaller.com/truecaller-sdk/mid-verification-sdk-api/flow-apis.md).

# Flow API's

A single call initiates exactly one verification flow. The flowType value determines which sub-flow runs; the other two are not processed.

| Field          | Type   | Required | Validation                                                                  | Description                                                   |
| -------------- | ------ | -------- | --------------------------------------------------------------------------- | ------------------------------------------------------------- |
| flowType       | String | Yes      | Exactly one of: `pos`, `pms`, `vms`. Case-sensitive. Returns 400 otherwise. | Selects the sub-flow. Only one flow is processed per request. |
| requestContent | Object | Yes      | Schema varies by `flowType`. See sections below.                            | Sub-flow specific payload.                                    |

{% hint style="info" %}
A single call initiates exactly one verification flow. The `flowType` value determines which sub-flow runs; the other two are not processed.
{% endhint %}

## Flow: POS — Point of Sale

Sends a Truecaller identity verification prompt to the user at a point-of-sale terminal.\
**flowType value:** `pos`

| Field            | Type   | Required | Validation                                                       | Description                                    |
| ---------------- | ------ | -------- | ---------------------------------------------------------------- | ---------------------------------------------- |
| requestNonce     | String | Yes      | Non-blank. Regex: `^[a-zA-Z0-9_-]{8,64}$` (URL-safe, 8–64 chars) | Unique session ID generated by partner.        |
| userNumber       | Long   | Yes      | E.164 without leading +. Returns 404 if not on Truecaller.       | Phone number of user to verify.                |
| partnerName      | String | Yes      | Non-blank.                                                       | Partner name shown in Truecaller notification. |
| privacyPolicyUrl | String | Yes      | Non-blank. Valid URI.                                            | Partner privacy policy URL shown to user.      |
| tosUrl           | String | Yes      | Non-blank. Valid URI.                                            | Partner terms of service URL shown to user.    |

```json
curl -X POST https://api4-noneu.truecaller.com/v1/apps/requests/mid-verification \
  -H "Authorization: Bearer <hmac-token>" \
  -H "appKey: <your-app-key>" \
  -H "Content-Type: application/json" \
  -d '{"flowType":"pos","requestContent":{"requestNonce":"abc123XY","userNumber":919876543210,"partnerName":"Acme Store","privacyPolicyUrl":"https://acme.com/privacy","tosUrl":"https://acme.com/tos"}}'
```

## Flow: PMS — Parking Management System

Sends a Truecaller notification to a vehicle owner to alert them their vehicle needs attention.\
**flowType value:** `pms`

| Field        | Type   | Required | Validation                                                       | Description                                                         |
| ------------ | ------ | -------- | ---------------------------------------------------------------- | ------------------------------------------------------------------- |
| requestNonce | String | Yes      | Non-blank. Regex: `^[a-zA-Z0-9_-]{8,64}$` (URL-safe, 8–64 chars) | Unique session ID generated by partner.                             |
| userNumber   | Long   | Yes      | E.164 without leading +. Returns 404 if not on Truecaller.       | Phone number of vehicle owner to contact.                           |
| url          | String | Yes      | Non-blank. Valid URI.                                            | Callback or deep-link URL sent as part of the parking notification. |

```json
curl -X POST https://api4-noneu.truecaller.com/v1/apps/requests/mid-verification \
  -H "Authorization: Bearer <hmac-token>" \
  -H "appKey: <your-app-key>" \
  -H "Content-Type: application/json" \
  -d '{"flowType":"pms","requestContent":{"requestNonce":"park99ZY-ab","userNumber":919876543210,"url":"https://parking.example.com/notify/abc123"}}'
```

## Flow: VMS — Visitor Management System

Sends a Truecaller identity prompt to a visitor arriving at a building or premises.

**flowType value:** `vms`

| Field            | Type   | Required | Text                                                             | Description                                                |
| ---------------- | ------ | -------- | ---------------------------------------------------------------- | ---------------------------------------------------------- |
| requestNonce     | String | Yes      | Non-blank. Regex: `^[a-zA-Z0-9_-]{8,64}$` (URL-safe, 8–64 chars) | Unique session ID generated by partner.                    |
| userNumber       | Long   | Yes      | E.164 without leading +. Returns 404 if not on Truecaller.       | Phone number of visitor to verify.                         |
| buildingName     | String | Yes      | Non-blank.                                                       | Building/premises name shown to visitor in Truecaller app. |
| tosUrl           | String | Yes      | Non-blank. Valid URI.                                            | Premises terms of service URL shown to visitor.            |
| privacyPolicyUrl | String | Yes      | Non-blank. Valid URI.                                            | Premises privacy policy URL shown to visitor.              |

```json
curl -X POST https://api4-noneu.truecaller.com/v1/apps/requests/mid-verification \
  -H "Authorization: Bearer <hmac-token>" \
  -H "appKey: <your-app-key>" \
  -H "Content-Type: application/json" \
  -d '{"flowType":"vms","requestContent":{"requestNonce":"vis-abc123XY","userNumber":919876543210,"buildingName":"TC HQ","tosUrl":"https://tcbuilding.com/tos","privacyPolicyUrl":"https://tcbuilding.com/privacy"}}'
```

## Responses

#### 200 OK — Success <a href="#id-200-ok-success" id="id-200-ok-success"></a>

Returned when the verification message is successfully dispatched to the user.

| Field        | Type   | Description                        |
| ------------ | ------ | ---------------------------------- |
| requestNonce | String | Echoes the nonce from the request. |
| status       | String | Always `message_sent` on success.  |

```json
{ "requestNonce": "abc123XY", "status": "message_sent" }
```

## Error Responses

| HTTP Status | Error Code | Message                                                                             | Cause                                                                            |
| ----------- | ---------- | ----------------------------------------------------------------------------------- | -------------------------------------------------------------------------------- |
| 400         | 4001       | Invalid request body                                                                | JSON malformed or required fields missing.                                       |
| 400         | 1005       | RequestNonce parameter should be minimum 8 and maximum 64 bytes URL safe character. | `requestNonce` is blank, out of length range, or contains disallowed characters. |
| 400         | 4005       | Url is invalid.                                                                     | `url`, `tosUrl`, or `privacyPolicyUrl` is not a valid URI.                       |
| 401         | 4011       | Unauthorized                                                                        | Authorization header missing, malformed, or HMAC mismatch.                       |
| 403         | 1009       | App type is forbidden                                                               | `appKey` does not belong to a `MID_SDK` app.                                     |
| 404         | 4044       | Phone number not found                                                              | `userNumber` is not registered on Truecaller.                                    |
| 429         | 429        | Too many calls                                                                      | Per-app rate limit exceeded.                                                     |
| 500         | —          | Failed to initiate the request                                                      | Internal error or downstream service failure.                                    |

## Field Validation Summary

| **Field**          | **Flows** | **Type** | **Rule**                                                                 |
| ------------------ | --------- | -------- | ------------------------------------------------------------------------ |
| `flowType`         | All       | String   | Enum: `pos` \| `pms` \| `vms`. Case-sensitive. One per request.          |
| `requestNonce`     | All       | String   | Non-blank. Regex: `^[a-zA-Z0-9_-]{8,64}$`                                |
| `userNumber`       | All       | Long     | E.164 without leading +. Must exist on Truecaller. Example: 919876543210 |
| `partnerName`      | POS only  | String   | Non-blank.                                                               |
| `url`              | PMS only  | String   | Non-blank. Valid URI.                                                    |
| `buildingName`     | VMS only  | String   | Non-blank.                                                               |
| `tosUrl`           | POS, VMS  | String   | Non-blank. Valid URI.                                                    |
| `privacyPolicyUrl` | POS, VMS  | String   | Non-blank. Valid URI                                                     |

{% hint style="info" %}

* Only `MID_SDK` apps are permitted. Other app group types are rejected with 403.
* Shopify apps are not supported on this endpoint.
* On success, a Truecaller in-app message is sent to `userNumber`. The partner callback URL fires asynchronously when the user responds.
* Rate limiting is enforced per `appId` via token bucket. Exceeding the limit returns 429.
  {% endhint %}

## Single-Click vs Double-Click Flow

The verification experience is controlled by the **"Additional user profiling with explicit user consent?"** toggle in the Truecaller Developer Portal under **Customisation Configuration** for the SDK app.<br>

| **Toggle state**   | **Flow type**    | **User experience**                                                               |
| ------------------ | ---------------- | --------------------------------------------------------------------------------- |
| Disabled (default) | **Single-click** | User taps once in Truecaller to verify — no separate consent screen.              |
| Enabled            | **Double-click** | User views a consent screen (partner privacy policy and terms) before confirming. |

{% hint style="warning" %}
**PMS is always single-click.** The Parking Management System flow is not affected by the "Additional user profiling with explicit user consent?" toggle. It always uses the single-click path regardless of the SDK app's Customisation Configuration setting.
{% endhint %}

## Webhook Payloads

All webhooks are sent as HTTP POST with `Content-Type: application/json` to the partner's registered callback URL. Delivery is asynchronous.

### Single-Click — Verification Successful

Sent when the user taps the one-tap button and verification completes (applies to POS, VMS, and PMS flows).

```json
{
  "requestId": "<requestNonce>",
  "status": "verified"
}
```

### Double-Click — Handshake (Flow Invoked)

Sent as soon as the user opens the consent screen in Truecaller, before they confirm. Partners can use this to show a loading state.

```json
{
  "requestId": "<requestNonce>",
  "status": "flow_invoked"
}
```

### Double-Click — Authorization Successful

Sent after the user confirms on the consent screen. Use `accessToken` with the Truecaller Profile API to fetch verified user details. The `endpoint` field is the Truecaller Profile API URL for this token.<br>

```json
{
  "requestId": "<requestNonce>",
  "accessToken": "<truecaller-access-token>",
  "endpoint": "<truecaller-profile-api-url>"
}
```

### Rejection Scenarios (Both Flows)

Sent when the user declines verification or opts for a different number:<br>

| **Scenario**                      | **Webhook payload**                                               |
| --------------------------------- | ----------------------------------------------------------------- |
| User rejects verification         | `{"requestId": "<requestNonce>", "status": "user_rejected"}`      |
| User selects "Use another number" | `{"requestId": "<requestNonce>", "status": "use_another_number"}` |

### Webhook Payload Summary by Flow and Scenario

| **Flow**                  | **Event**                    | **Key fields in webhook**                   |
| ------------------------- | ---------------------------- | ------------------------------------------- |
| Single-click (POS / VMS)  | User verifies                | `requestId`, `status: "verified"`           |
| PMS (always single-click) | User verifies                | `requestId`, `status: "verified"`           |
| Double-click (POS / VMS)  | User opens consent screen    | `requestId`, `status: "flow_invoked"`       |
| Double-click (POS / VMS)  | User consents and authorizes | `requestId`, `accessToken`, `endpoint`      |
| Any flow                  | User rejects                 | `requestId`, `status: "user_rejected"`      |
| Any flow                  | User selects another number  | `requestId`, `status: "use_another_number"` |
