Dashboard KPIs API Reference
Pull the same KPI bar shown on your Hermon dashboard for any date range.
Overview: This endpoint returns the exact metrics your Hermon dashboard shows — new leads, booked calls, close rates, cash collected, and more — for a date range you choose, alongside the same figures for the preceding period so you can track change over time. Values are computed by Hermon the same way the dashboard computes them, so numbers always line up with what you see in the app.
Get KPI Bar
Returns the KPI metrics for the requested period plus the comparison period. Provide a start and end date; both are calendar dates in your organization's timezone.
GET/api/external/dashboard/kpis
Query Parameters
| Parameter | Type | Required | Description |
|---|---|---|---|
| from | string (YYYY-MM-DD) | required | Start of the reporting period (inclusive). A calendar date interpreted in your organization’s timezone. |
| to | string (YYYY-MM-DD) | required | End of the reporting period (inclusive). A calendar date interpreted in your organization’s timezone. |
| user_scope | string (comma-separated user IDs) | optional | Restrict the metrics to specific team members. Each id is matched on the role that member holds (setter, closer, or triager). Omit to include the whole team. Use the Team Members endpoint to resolve ids. |
| call_category | string (enum) | optional | Limit the metrics to a single call category: SALES_CALL, COACHING_CALL, or TRIAGE_CALL. Omit to include all categories. |
Dates & the comparison period: from and toare whole calendar days in your organization's timezone — the range always covers the full to day. The comparison period (previous_value on each metric) is the equal-length range immediately before your selected period, chosen automatically.
Code Examples
curl -X GET "https://api.hermon.io/api/external/dashboard/kpis?from=2026-09-01&to=2026-09-30" \
-H "x-api-key: sk_live_your_key_here"Response Fields
| Field | Type | Description |
|---|---|---|
| metrics | array | The KPI values for the requested period. Each entry carries value, previous_value, and growth_percent (see Metric Object below). |
| available_metrics | array | Catalogue of every metric that can appear, with its key, label, description, type, and group ("kpi", "finance", or "meta"). |
| currency | string | null | ISO currency code for all monetary metrics (your organization’s currency). |
| current_period | object | The resolved { start_date, end_date } for the requested range. |
| previous_period | object | The { start_date, end_date } of the comparison period (the equal-length range immediately before current_period). |
| avg_growth_percent | number | Average growth across the returned metrics. |
| meta_setup_status | string | Whether Meta Ads is connected for the organization ("ok", "not_connected", or "no_selection"). Meta metrics are zero when not connected. |
| meta_setup_message | string | null | Human-readable note about the Meta Ads setup status, when relevant. |
Metric Object
Each entry in metrics (and the catalogue in available_metrics) has the following shape.
| Field | Type | Description |
|---|---|---|
| key | string | Stable identifier for the metric (e.g. "closing_rate_booked_percent", "cash_collected"). |
| label | string | Human-readable name as shown on the dashboard. |
| description | string | Plain-English definition of exactly how the metric is calculated. |
| value | number | null | The metric value for the selected period. null when it is not applicable (e.g. a rate with no denominator). |
| previous_value | number | null | The same metric for the immediately preceding period of equal length, for comparison. |
| growth_percent | number | null | Percentage change from previous_value to value. |
Response Example
Trimmed to a representative subset — the live response returns the full metric set.
json
{
"status": "success",
"message": "KPI bar fetched successfully",
"data": {
"available_metrics": [
{
"key": "calls_booked",
"label": "Booked Calls",
"description": "Unique leads with at least one appointment (any outcome) in the period, using their latest appointment.",
"type": "number",
"group": "kpi"
},
{
"key": "cash_collected",
"label": "Cash Collected",
"description": "Sum of PAID payments in the period minus any associated succeeded refunds.",
"type": "currency",
"group": "kpi"
}
],
"metrics": [
{
"key": "new_leads",
"label": "New Leads",
"description": "Total number of new leads created within the period, based on lead creation date.",
"value": 42,
"previous_value": 37,
"growth_percent": 13.51
},
{
"key": "calls_booked",
"label": "Booked Calls",
"description": "Unique leads with at least one appointment (any outcome) in the period, using their latest appointment.",
"value": 18,
"previous_value": 21,
"growth_percent": -14.29
},
{
"key": "contract_signed",
"label": "Contracts Signed",
"description": "Number of contracts with status SIGNED and signed_at within the period.",
"value": 6,
"previous_value": 4,
"growth_percent": 50
},
{
"key": "closing_rate_booked_percent",
"label": "Close Rate (Booked)",
"description": "Booked calls in the period that produced a signed contract ÷ booked calls in the period × 100.",
"value": 33.33,
"previous_value": 19.05,
"growth_percent": 74.96
},
{
"key": "cash_collected",
"label": "Cash Collected",
"description": "Sum of PAID payments in the period minus any associated succeeded refunds.",
"value": 12500,
"previous_value": 9800,
"growth_percent": 27.55
}
],
"avg_growth_percent": 30.25,
"currency": "usd",
"current_period": {
"start_date": "2026-09-01",
"end_date": "2026-09-30"
},
"previous_period": {
"start_date": "2026-08-01",
"end_date": "2026-08-31"
},
"meta_setup_status": "ok",
"meta_setup_message": null
}
}Scoping to Specific Team Members
Per-rep numbers: pass user_scopewith one or more team-member ids (comma-separated) to see the KPIs for just those people — for example a single closer's close rate and cash collected. Each id is matched on the role that member holds. Resolve ids with the GET /api/external/team-members endpoint. Omit user_scope for whole-team totals.
Error Responses
400Missing or invalid date parameters
json
{
"status": "error",
"message": "from must be a date in YYYY-MM-DD format"
}401Missing or invalid API key
json
{
"status": "error",
"message": "Invalid or revoked API key"
}429Rate limit exceeded
json
{
"status": "error",
"message": "Rate limit exceeded for this organization. Retry after the number of seconds in the Retry-After header."
}