> ## Documentation Index
> Fetch the complete documentation index at: https://docs.telleo.ai/llms.txt
> Use this file to discover all available pages before exploring further.

# Counsellors

> Add the people who take your human calls, keep their details current, and deactivate them when they leave.

A **counsellor** is a person in your Telleo account who takes [human calls](/concepts/human-calls) and works leads in the dashboard. With a key that has the `counsellors:manage` [scope](/authentication#scopes) your HR system, CRM or onboarding tool can manage them directly:

| Request | What it does |
| - | - |
| `POST /v1/counsellors` | Adds a counsellor: a dashboard login with the Counsellor role in your account. |
| `GET /v1/counsellors` | Lists your active counsellors and admins (also with `human_calls:read`). |
| `GET /v1/counsellors/{id}` | One counsellor or admin, active or deactivated (also with `human_calls:read`). |
| `PATCH /v1/counsellors/{id}` | Changes their name, mobile number, Airtel extension, or turns them on and off. |
| `DELETE /v1/counsellors/{id}` | Deactivates them. |

The API only ever manages **counsellors**. It never gives anyone another role, and it never changes an admin, a teacher or any other member of your staff: those requests fail with `403 counsellor_not_manageable`. Manage them in the dashboard.

## Adding a counsellor

```bash theme={null}
curl https://api.telleo.ai/v1/counsellors \
  -H "X-API-Key: $TELLEO_API_KEY" \
  -H "Idempotency-Key: hr-emp-2291" \
  -H "Content-Type: application/json" \
  -d '{
    "name": "Asha Rao",
    "email": "asha@school.in",
    "mobile_number": "+919876543210"
  }'
```

```json theme={null}
{
  "id": "6b7e0c2a-1d3f-4e5a-8b9c-0d1e2f3a4b5c",
  "object": "counsellor",
  "name": "Asha Rao",
  "email": "asha@school.in",
  "roles": ["COUNSELLOR"],
  "status": "active",
  "can_call": true,
  "blocked_reason": null,
  "mobile_number": "919876543210",
  "airtel_extension": null,
  "manageable": true,
  "shared_account": false,
  "created": true,
  "existing_account": false,
  "welcome_email_sent": true,
  "warnings": []
}
```

What happens depends on whether the email already has a login on the platform:

| The email… | Result | Email sent |
| - | - | - |
| is new | A new login, **active at once**, with the Counsellor role in your account. | The welcome email with their username, password and the dashboard link (unless `send_welcome_email: false`). |
| already has a login that belongs to **another** account on the platform (or to no account) | `409 email_in_use_elsewhere`. The API never attaches someone else's login, because that would show your key their details. Use a different email, or have an admin add them from the dashboard. | None. |
| belonged to a person you removed from your account earlier (and to no other account) | The **same** login gets the Counsellor role back. Their name, mobile number and password stay exactly as they are (`warnings` says when what you sent was not applied). | None. They sign in with the login they already have. |
| is already a counsellor in your account | Nothing changes: `200` with `created: false`. | None. |
| is an admin, teacher or other member of your account | `409 account_has_other_role`. Give them the counsellor role in the dashboard if you mean to. | None. |
| belongs to a counsellor you deactivated | `409 counsellor_inactive`. [Reactivate](#reactivating) them instead. | None. |

* **`mobile_number`** is needed before they can take calls on Vacademy Voice and Exotel: their phone rings first. Without one the response carries a `mobile_number_missing` warning and `can_call` is `false`. It is stored as digits with the country code (`919876543210`).
* **`airtel_extension`** maps their Airtel IQ extension when your calling provider is Airtel. An extension can belong to one person in your account (`409 extension_taken` otherwise).
* Send an [`Idempotency-Key`](/platform/idempotency) so that a retried request never adds the person twice. Two requests for the same email at the same moment are handled one after the other; the second gets `409 request_in_progress` and should retry. If a request was cut off after the login was created, retrying it returns the counsellor (`created: false`) and sets the mobile number it carried if none was saved.
* `GET /v1/counsellors/{id}` shows a key with `counsellors:manage` the `mobile_number`, `airtel_extension`, `manageable` and `shared_account`. The mobile number is `null` when the login also belongs to another account (`shared_account: true`), and `GET /v1/counsellors` never includes phone numbers.

## Keeping details current

```bash theme={null}
curl -X PATCH https://api.telleo.ai/v1/counsellors/6b7e0c2a-1d3f-4e5a-8b9c-0d1e2f3a4b5c \
  -H "X-API-Key: $TELLEO_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{ "mobile_number": "+919812345678", "airtel_extension": "214" }'
```

Only the fields you send change. `airtel_extension: null` removes the mapping; a mobile number cannot be removed, only replaced.

### Shared logins

A person's email and mobile number are their **login everywhere on the platform**, not only in your account. When the login also belongs to another account (`shared_account: true`), changing the name or mobile number through your key would change them for that other account too, so it is refused with `409 shared_account`. The counsellor can change them in their own profile. Their Airtel extension and whether they are active in **your** account can always be changed.

## Deactivating

```bash theme={null}
curl -X DELETE https://api.telleo.ai/v1/counsellors/6b7e0c2a-1d3f-4e5a-8b9c-0d1e2f3a4b5c \
  -H "X-API-Key: $TELLEO_API_KEY"
```

Deactivating is what you do when someone leaves or stops taking leads. It never deletes the person or their history, and it only touches **your** account:

| | Effect |
| - | - |
| Sign-in | Their role in your account is disabled, so they can no longer open it from their next request (`effects.sessions_revoked: "this_account"`). They stay signed in to any other account they belong to. |
| Human calls | They drop out of `GET /v1/counsellors`; `POST /v1/human-calls` naming them fails with `counsellor_not_found`. |
| Lead pools | They are set **inactive in every lead pool** of your account, so new leads are no longer assigned to them. Leads already assigned to them **stay with them**; reassign those in the dashboard if needed. |
| IVR | They are taken out of every "ring these people" list in your IVR menus. A step left ringing nobody is flagged with `no_one_left: true`. |
| Inbound calls | A lead calling back is no longer routed to them as "the last counsellor who called". |

The response is the counsellor (`status: "inactive"`) with an `effects` object:

```json theme={null}
"effects": {
  "role_disabled": true,
  "sessions_revoked": "this_account",
  "pool_memberships_deactivated": 3,
  "ivr_dial_steps_updated": [
    { "menu_id": "m-1", "menu_name": "Main", "step_id": "n-4", "step_label": "Sales", "no_one_left": false }
  ],
  "leads_reassigned": 0
}
```

Deactivating again is harmless: it reports nothing more to change. `PATCH` with `{"active": false}` does the same.

### Reactivating

```bash theme={null}
curl -X PATCH https://api.telleo.ai/v1/counsellors/6b7e…4b5c \
  -H "X-API-Key: $TELLEO_API_KEY" -H "Content-Type: application/json" \
  -d '{ "active": true }'
```

This restores their role, so they can sign in and take human calls again. Their **lead pool memberships stay inactive** and they are **not put back** into IVR lists, because the API cannot tell which of those an admin had switched off on purpose before. Turn them back on in the dashboard where they should take leads and inbound calls again; the response's `effects.note` says so.

## Errors

| HTTP | Code | Meaning |
| - | - | - |
| 403 | `counsellor_not_manageable` | The person is an admin or other staff of your account. |
| 404 | `counsellor_not_found` | No counsellor or admin with this id in your account. |
| 409 | `account_has_other_role` | The email belongs to a member of your account with another role. |
| 409 | `email_in_use_elsewhere` | The email's login belongs to another account on the platform. Use another email, or add them in the dashboard. |
| 409 | `counsellor_inactive` | The email belongs to a deactivated counsellor; reactivate them. |
| 409 | `shared_account` | The login also belongs to another account; its name and mobile cannot be changed through the API. |
| 409 | `extension_taken` / `extension_managed_elsewhere` | The Airtel extension is already someone else's, or the person's extension is managed by another account. |
| 409 | `request_in_progress` | The same email is being added by another request right now. |
| 500 | `role_update_failed` | The role could not be disabled or restored, so nothing else was changed. Contact us with the `request_id`. |
| 503 | `temporarily_unavailable` | The user directory could not be reached. Retry; nothing was created. |


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.