# Get routing user status

> GET /v1/routing/statuses/{id} · Queues and routing API

Source: https://developer.kustomer.com/api/queues-and-routing/get-routing-user-status

```http
GET https://{orgname}.api.kustomerapp.com/v1/routing/statuses/{id}
Authorization: Bearer <API key>
```

## Authorization

Requires any one of these roles: `org.permission.routing_status.read`, `org.permission.routing.read`; or legacy `org.user.routing.read`. The API key or user must hold at least one of them. Legacy roles predate permission sets and still work.

Retrieves a routing status based on its unique ID.

## About Routing user statuses

A routing user status is one of the states an agent can be in for routing, such as "Available", "Lunch" or "Training". Admins define the list; each status has a type that decides whether routing sends the agent new work.

Agents pick their status from the routing status menu in the agent desktop, and supervisors can change it for them. The status an agent is in right now lives on their [work session](https://developer.kustomer.com/api/queues-and-routing#work-sessions), which points to one of these status records. Statuses are org-wide settings: admins create them in Kustomer's routing settings, and every team shares the same list.

Each org starts with built-in statuses, returned with `system: true`, such as the default available status and the busy status Kustomer sets for agents on a call or in wrap-up. Statuses you create sit alongside them, so an org can have several unavailable statuses ("Lunch", "Coaching", "Admin work") that routing treats the same way but that show up separately in utilization reporting.

#### Status types

`statusType` is what routing acts on. The name is only a label.

| `statusType` | Meaning |
| --- | --- |
| `available` | Ready for new work. The only type that can receive routed items, so it's the only type with `routable: true`. |
| `busy` | Occupied with work that isn't routed, such as a call. Counts toward queue staffing, but receives nothing new. |
| `unavailable` | Signed in but not taking work, such as on a break. |
| `offline` | Signed out. Switching to it ends the agent's work session. |

You can create statuses of type `available`, `unavailable` or `busy`; `offline` is built in. The type is fixed when the status is created, so to change it, create a new status and disable the old one.

#### Fields

- `name` is required, up to 150 characters, and must be unique in the org. It is stored lowercased and trimmed.
- `description` is free text for admins.
- `externalId` is your own identifier for the status, unique in the org, for keeping it in step with an outside system such as a phone or workforce management tool.
- `selectable` controls whether agents can choose the status themselves. It defaults to `false`, so set it to `true` for statuses agents should see in their menu.
- `enabled` retires a status without deleting it; there is no delete operation.
- `routable` and `system` are read-only.

#### Which endpoint to use

| To | Call |
| --- | --- |
| List the org's statuses | [`GET /v1/routing/statuses`](https://developer.kustomer.com/api/queues-and-routing/get-routing-user-statuses) |
| Read one status | [`GET /v1/routing/statuses/{id}`](https://developer.kustomer.com/api/queues-and-routing/get-routing-user-status) |
| Add a status | [`POST /v1/routing/statuses`](https://developer.kustomer.com/api/queues-and-routing/create-routing-user-status) |
| Rename, describe or disable a status | [`PUT /v1/routing/statuses/{id}`](https://developer.kustomer.com/api/queues-and-routing/update-routing-user-status) |
| Put an agent into a status | [`PUT /v1/routing/work-sessions/current`](https://developer.kustomer.com/api/queues-and-routing/update-current-work-session) for yourself, or [`PUT /v1/routing/work-sessions/{id}`](https://developer.kustomer.com/api/queues-and-routing/update-work-session-by-id) for another agent |

Changing a status record doesn't change anyone's status. To move an agent, update their work session with the status ID. If an agent rejects a routed item or doesn't accept it in time, Kustomer moves them to an unavailable status so routing stops offering them work until they return.

Related: [Work sessions](https://developer.kustomer.com/api/queues-and-routing#work-sessions), [Team routing settings](https://developer.kustomer.com/api/queues-and-routing#team-routing-settings), [Work items](https://developer.kustomer.com/api/queues-and-routing#work-items)

### Recipes

#### 1. Keep statuses in step with a workforce-management tool

Mirror the activity codes from a WFM or phone system as routing statuses, matched by your own `externalId`, so agent states line up in both systems.

**Step 1.** [`GET /v1/routing/statuses`](https://developer.kustomer.com/api/queues-and-routing/get-routing-user-statuses.md). List every status and index them by `externalId`. Built-in statuses (`system: true`) have none, so they never match.

```bash title="cURL"
curl "https://api.kustomerapp.com/v1/routing/statuses?pageSize=100" \
  --header "Authorization: Bearer $KUSTOMER_API_KEY"
```

```bash title="kusty"
kusty api GET /v1/routing/statuses --all \
  | jq -s 'map(select(.data.attributes.externalId) | {(.data.attributes.externalId): .data.id}) | add' > statuses-by-external-id.json
```

**Step 2.** [`POST /v1/routing/statuses`](https://developer.kustomer.com/api/queues-and-routing/create-routing-user-status.md). Create each code that has no match. `statusType` is required and fixed once created, so map each code to `unavailable`, `busy` or `available` up front. Send `selectable: true` if agents should be able to pick it themselves. A `name` or `externalId` that already exists in the org is rejected.

```bash title="cURL"
curl --request POST "https://api.kustomerapp.com/v1/routing/statuses" \
  --header "Authorization: Bearer $KUSTOMER_API_KEY" \
  --header "Content-Type: application/json" \
  --data '{"name": "Coaching", "statusType": "unavailable", "selectable": true, "externalId": "wfm-coaching"}'
```

```bash title="kusty"
kusty api POST /v1/routing/statuses \
  --data '{"name": "Coaching", "statusType": "unavailable", "selectable": true, "externalId": "wfm-coaching"}'
```

**Step 3.** [`PUT /v1/routing/statuses/{id}`](https://developer.kustomer.com/api/queues-and-routing/update-routing-user-status.md). Rename statuses whose codes changed, and send `enabled: false` for codes your tool no longer has. There's no delete, and you can't change `statusType` on update.

```bash title="cURL"
curl --request PUT "https://api.kustomerapp.com/v1/routing/statuses/$STATUS_ID" \
  --header "Authorization: Bearer $KUSTOMER_API_KEY" \
  --header "Content-Type: application/json" \
  --data '{"enabled": false}'
```

```bash title="kusty"
kusty api PUT /v1/routing/statuses/$STATUS_ID --field enabled:=false
```

> Names are stored lowercased, so "Coaching" comes back as `coaching`. Match on `externalId` rather than `name`.

#### 2. Report an agent's time in each status

Turn the status IDs on a work session into readable names, to show how a shift split between "Available", "Lunch", "Training" and the rest.

**Step 1.** [`GET /v1/routing/statuses`](https://developer.kustomer.com/api/queues-and-routing/get-routing-user-statuses.md). Build a map of status IDs to names. The list includes disabled statuses too, which older sessions can still reference.

```bash title="cURL"
curl "https://api.kustomerapp.com/v1/routing/statuses?pageSize=100" \
  --header "Authorization: Bearer $KUSTOMER_API_KEY"
```

```bash title="kusty"
kusty api GET /v1/routing/statuses --all \
  | jq -s 'map({(.data.id): .data.attributes.name}) | add' > status-names.json
```

**Step 2.** [`GET /v1/routing/users/{id}/work-sessions/current`](https://developer.kustomer.com/api/queues-and-routing/get-current-work-session-by-user-id.md). Read the agent's session. `totalTimeByStatus` is keyed by status ID, and each entry's `time` is milliseconds spent in that status. The status the agent is in now has only `statusAt` until they leave it, so add the time since then yourself.

```bash title="cURL"
curl "https://api.kustomerapp.com/v1/routing/users/$USER_ID/work-sessions/current" \
  --header "Authorization: Bearer $KUSTOMER_API_KEY"
```

```bash title="kusty"
kusty api GET /v1/routing/users/$USER_ID/work-sessions/current \
  | jq -r --slurpfile n status-names.json '.data.attributes.totalTimeByStatus | to_entries[]
      | [$n[0][.key] // .key, ((.value.time // 0) / 60000 | floor)] | @tsv'
```

> For past shifts, run the same mapping over each session from `GET /v1/routing/users/{id}/work-sessions`.

### Example object

A real record from [`GET /v1/routing/statuses/{id}`](https://developer.kustomer.com/api/queues-and-routing/get-routing-user-status.md):

```json
{
  "type": "statuses",
  "id": "5de895daf22a61001a97244b",
  "attributes": {
    "name": "bathroom break",
    "description": "Bathroom break status",
    "statusType": "unavailable",
    "selectable": true,
    "system": false,
    "enabled": true,
    "routable": false,
    "createdAt": "2019-12-05T05:30:02.653Z",
    "updatedAt": "2019-12-05T05:30:02.653Z"
  },
  "relationships": {
    "org": {
      "links": {
        "self": "/v1/orgs/57504f64d76808100089eb44"
      },
      "data": {
        "type": "org",
        "id": "57504f64d76808100089eb44"
      }
    },
    "createdBy": {
      "links": {
        "self": "/v1/users/57504f644c80120f00f3c378"
      },
      "data": {
        "type": "user",
        "id": "57504f644c80120f00f3c378"
      }
    }
  }
}
```

Fields:

- `attributes.name` (string): The label agents see, unique in the org and up to 150 characters. Kustomer stores it lowercased and trimmed, so compare names case-insensitively.
- `attributes.description` (string): Free text for admins, up to 1,024 characters.
- `attributes.statusType` (string): What routing does with agents in this status: `available`, `busy`, `unavailable` or `offline`. Set when the status is created and can't be changed.
- `attributes.selectable` (boolean): Whether agents can pick this status themselves. Defaults to `false` on create.
- `attributes.system` (boolean): `true` for the built-in statuses every org starts with. Read-only.
- `attributes.enabled` (boolean): Set it to `false` to retire a status; there's no delete.
- `attributes.routable` (boolean): Read-only. `true` only for statuses of type `available`, the one type routing sends new work to.

### Relationships

- Referenced by **Work sessions** via `relationships.status`

### Permissions

Fewest roles for a read-only integration: `org.permission.routing_status.read`. For every endpoint: `org.permission.routing_status.read`, `org.permission.routing_status.create`, `org.permission.routing_status.update`.

## Path parameters

| Name | Type | Required | Description |
| --- | --- | --- | --- |
| `id` | string | yes | Routing Status ID |

## Responses

### 200

OK

- `data` (object, required)
  - `type` (string, required)
  - `id` (string, required)
  - `attributes` (object, required)
    - `name` (string, required)
    - `description` (string, required)
    - `statusType` (string, required)
    - `selectable` (boolean, required)
    - `system` (boolean, required)
    - `enabled` (boolean, required)
    - `routable` (boolean, required)
    - `createdAt` (string, required)
    - `updatedAt` (string, required)
  - `relationships` (object, required)
    - `org` (object, required)
    - `createdBy` (object, required)

```json
{
  "data": {
    "type": "statuses",
    "id": "5de895daf22a61001a97244b",
    "attributes": {
      "name": "bathroom break",
      "description": "Bathroom break status",
      "statusType": "unavailable",
      "selectable": true,
      "system": false,
      "enabled": true,
      "routable": false,
      "createdAt": "2019-12-05T05:30:02.653Z",
      "updatedAt": "2019-12-05T05:30:02.653Z"
    },
    "relationships": {
      "org": {
        "links": {
          "self": "/v1/orgs/57504f64d76808100089eb44"
        },
        "data": {
          "type": "org",
          "id": "57504f64d76808100089eb44"
        }
      },
      "createdBy": {
        "links": {
          "self": "/v1/users/57504f644c80120f00f3c378"
        },
        "data": {
          "type": "user",
          "id": "57504f644c80120f00f3c378"
        }
      }
    }
  }
}
```

### 401

Unauthorized

### 403

Forbidden

### 404

Not Found

## Example request

```bash
curl --request GET \
  --url 'https://api.kustomerapp.com/v1/routing/statuses/5f184e74c61792001af42e49' \
  --header "Authorization: Bearer $KUSTOMER_API_KEY"
```
