Skip to content

Read Agent States

This guide explains how to read contact-center agent state change history from the Portal API — the same events the queues app writes when an agent becomes idle, on a call, in wrap-up, on DND, and so on.

Use this when you need a timeline of state transitions for one or more agents (compliance, workforce tooling, or custom dashboards).

flowchart LR
  QueuesApp[Queues app] -->|write fonouc_log| CouchDB[(Account month DB)]
  App[Your app] -->|GET activity/events| PortalAPI["Portal API :9443"]
  PortalAPI -->|all_agent_events view| CouchDB

Note

This endpoint returns historical state-change events, not the agent's live status on the softphone. For real-time updates, see Contact Center Websocket events.


Prerequisites

Requirement Notes
Account with Contact Center / queues enabled State logs are written when agents are active on queues
HTTPS access to the portal API (https://{{ domain }}:9443)
API key or admin JWT Same auth model as other /api/v2/reports/... endpoints
Agent user_id (optional) Needed only if you filter the response to one user

Authentication

Required headers:

X-API-Key: <your_api_key>
X-Account-ID: <your_account_id>

Base URL pattern:

https://{{ domain }}:9443/api/v2

See API Key authentication.


Endpoint

GET /api/v2/reports/callcenter/agents/activity/events

Reads CouchDB view _design/fonouc_logs/_view/all_agent_events for the account’s monthly databases in the requested time range.

Query parameters

Provide a date range using one of:

Params Description
timeRange Relative window, e.g. 1d, 1w, 1M
startDate + endDate Unix timestamps (seconds); maximum 31 days apart; endDate must be greater than startDate

Pagination:

Param Description
pageSize Page size (defaults to the server reports page size if omitted)
startKey Cursor from the previous response next_start_key (Unix timestamp string)

No server-side user filter

The API returns events for all agents in the account within the time window. Each event includes user_id — filter client-side for a specific user. A userID query parameter is accepted by the shared reports parser but is not applied by this handler.

Example request

curl -sS "https://{{ domain }}:9443/api/v2/reports/callcenter/agents/activity/events?startDate=1784515200&endDate=1784601600&pageSize=100" \
  -H "X-API-Key: YOUR_API_KEY" \
  -H "X-Account-ID: YOUR_ACCOUNT_ID"

Example: filter to one user (client-side)

USER_ID="a2ca7416253d92c8d849ea96f9e2ebe6"

curl -sS "https://{{ domain }}:9443/api/v2/reports/callcenter/agents/activity/events?timeRange=1d&pageSize=500" \
  -H "X-API-Key: YOUR_API_KEY" \
  -H "X-Account-ID: YOUR_ACCOUNT_ID" \
  | jq --arg uid "$USER_ID" '.events[] | select(.user_id == $uid)'

Response shape

{
  "events": [
    {
      "event": "agent_idle",
      "enabled": true,
      "user_id": "a2ca7416253d92c8d849ea96f9e2ebe6",
      "ext": "3349",
      "username": "Sebastian+2 Ripari",
      "state": "available",
      "Timestamp": 1784602047
    }
  ],
  "next_start_key": "1784602047"
}
Field Type Description
events array Page of agent state events (oldest → newest within the page)
events[].event string State event name (see Event types)
events[].enabled boolean true = entered this state; false = left this state
events[].user_id string Agent user ID
events[].ext string Agent extension
events[].username string Display name (first_name + last_name from the log)
events[].state string Extra state detail (custom unavailable label, wrap-up queue name, etc.)
events[].Timestamp number Event time as Unix seconds (from the CouchDB view key). JSON field name is capital Timestamp.
next_start_key string Pass as startKey on the next request; empty when there is no further page

Normalization applied by the API

If event is agent_idle and state is empty or "none", the API rewrites state to "available" before returning the event. Stored CouchDB documents may still show "state": "none".


Event types

These values are written by the queues app into fonouc_log documents with type: "agent", then exposed through this API.

event Meaning when enabled: true Typical state
agent_idle Agent is available / idle (ready for queue work) "available" in API responses ("none" in raw DB logs)
agent_on_call Agent is on an active call usually "none"
agent_hold Agent has a call on hold usually "none"
agent_wrap_up Agent is in wrap-up / ACW may be a queue name when wrap-up is anchored to a queue
agent_dnd Agent Do Not Disturb is on usually "none"
agent_reg Agent device/registration considered registered usually "none"
agent_not_avail_state Agent selected a “not available” / custom CC status custom status label or id string

When enabled is false, the agent left that state (for example wrap-up ended, DND cleared, call hung up).

How to interpret a timeline

Events are edge transitions, not a single “current status” field. To reconstruct status over time for one user_id:

  1. Sort that user’s events by Timestamp.
  2. Treat each enabled: true as entering the named state, and enabled: false as leaving it.
  3. Several flags can overlap in the underlying system (for example registration vs idle); product reports often treat agent_idle + enabled: true as available for queue routing.

What is stored in the database (raw log)

For debugging or when reading CouchDB directly, each change is a document like:

{
  "account_id": "5d5764bac102d5ad3b6e95ed19920295",
  "pvt_type": "fonouc_log",
  "timestamp": 1784602047.62461,
  "type": "agent",
  "user_id": "a2ca7416253d92c8d849ea96f9e2ebe6",
  "event": "agent_idle",
  "ext": "3349",
  "first_name": "Sebastian+2",
  "last_name": "Ripari",
  "email": "sebastian2@fonouc.com",
  "customer_callerid_name": "",
  "customer_callerid_number": "",
  "state": "none",
  "enabled": true,
  "_id": "3c75c19de32d0490b91cd40b800e761a",
  "_rev": "1-98acda265fdb7b7b31e0dce756537731"
}
Raw field API field
event event
enabled enabled
user_id user_id
ext ext
first_name + last_name username
state state (with idle/noneavailable rewrite)
timestamp (float) Timestamp (integer seconds from the view key)

The activity API does not return email, caller-id fields, _id, or _rev.


Pagination

  1. Call with startDate / endDate (or timeRange) and pageSize.
  2. If next_start_key is non-empty, call again with startKey=<next_start_key> and the same date range.
  3. Repeat until next_start_key is empty.

The server skips the duplicate boundary event when startKey is a numeric timestamp.


Endpoint Purpose
GET /api/v2/reports/callcenter/agents/activity/events Raw agent state-change log (this guide)
GET /api/v2/reports/callcenter/agents/stats Aggregated Agents Activity report
GET /api/v2/reports/callcenter/queues/agents/status/activity Login/logout session activity by queue
UCP GET /ucp/v2/callcenter/agent/state Current custom CC status for the logged-in agent
Contact Center Websocket events Live stream of CC events

See also