Most Asterisk call centers start monitoring too late. They install Asterisk, configure queues, hire agents, and then six months in somebody asks: "Why are 15% of our callers hanging up?"
By then, the problem has been costing money for months.
I have worked with Asterisk deployments ranging from 5 agents to 200+. The pattern is consistent: teams that set up monitoring from day one make better staffing decisions, catch problems before customers complain, and pay less per resolved call.
This guide covers what to monitor, how to set it up on Asterisk, and which tools actually work in production. No theory - specific configs, SQL queries, and real numbers.
What Asterisk Exposes (and What It Hides)
Asterisk generates a lot of data. The challenge is not collection - it is knowing which data matters and how to connect the pieces.
Three Data Sources You Need
1. AMI (Asterisk Manager Interface) - Real-Time Events
AMI streams events as they happen: calls entering queues, agents answering, callers abandoning, agents pausing. This is your real-time monitoring backbone.
; /etc/asterisk/manager.conf
[monitoring]
secret = generate_a_strong_password_here
deny = 0.0.0.0/0.0.0.0
permit = 10.0.0.0/255.255.255.0
read = system,call,log,agent,reporting
write = system,call,agent,reporting
writetimeout = 5000AMI gives you sub-second visibility into queue state. Every external monitoring tool connects through AMI for real-time data.
2. queue_log - Historical Queue Events
This file records every queue interaction: who called, which agent answered, how long they waited, why they disconnected.
# Verify queue_log is being written
tail -5 /var/log/asterisk/queue_log
# Expected format:
# 1774000000|1774000001|sales|ENTERQUEUE||2125551234|1
# 1774000005|1774000001|sales|CONNECT|5|SIP/200|1774000005.42
# 1774000120|1774000001|sales|COMPLETECALLER|5|115||1The fields: timestamp, unique ID, queue name, event, and event-specific data. The data1/data2/data3 fields change meaning depending on the event type - this trips up most custom reporting projects.
Critical: Enable full queue logging in every queue:
; /etc/asterisk/queues.conf (per queue)
[sales]
eventwhencalled = yes
eventmemberstatus = yes
queue-callswaiting = yesWithout eventwhencalled = yes, you lose agent-level granularity. Without eventmemberstatus, you cannot track agent state transitions.
3. CDR (Call Detail Records) - Call-Level Data
CDR captures start time, answer time, end time, duration, disposition. It operates at the call level, not the queue level.
Common mistake: CDR duration includes ring time. CDR billsec is closer to talk time but includes IVR navigation. Neither represents actual agent-customer conversation time. For accurate talk time, use queue_log CONNECT/COMPLETE events.
The Metrics That Actually Matter
I have seen dashboards with 40 metrics where nobody looks at 35 of them. Start with these seven. Add more only when you have a specific question they answer.
Tier 1: Watch These Every Hour
1. Calls Waiting (Real-Time)
How many callers are in queue right now. If this number exceeds 3x your available agents, you have a staffing problem happening now - not tomorrow, now.
# Quick check from CLI
asterisk -rx "queue show sales" | grep -E "^ [0-9]+ has"2. Service Level (SLA)
Percentage of calls answered within your target time. The industry default is "80/20" (80% answered within 20 seconds), but your target should match your queue type:
| Queue Type | SLA Target | Why |
|---|---|---|
| Sales/Inbound | 80% in 15s | Callers with purchase intent leave fast |
| Technical Support | 80% in 30s | Callers with problems wait longer |
| VIP/Enterprise | 90% in 10s | Premium customers, premium SLA |
| General Inquiry | 70% in 45s | Lower urgency, higher tolerance |
-- Calculate rolling SLA by queue (last 24 hours)
SELECT
queuename,
COUNT(CASE WHEN event = 'CONNECT' AND CAST(data1 AS UNSIGNED) <= 20 THEN 1 END) AS within_sla,
COUNT(CASE WHEN event = 'CONNECT' THEN 1 END) AS total_answered,
ROUND(100.0 * COUNT(CASE WHEN event = 'CONNECT' AND CAST(data1 AS UNSIGNED) <= 20 THEN 1 END) /
NULLIF(COUNT(CASE WHEN event = 'CONNECT' THEN 1 END), 0), 1) AS sla_pct
FROM queue_log
WHERE time > UNIX_TIMESTAMP(NOW() - INTERVAL 24 HOUR)
GROUP BY queuename
ORDER BY sla_pct ASC;3. Abandon Rate
Percentage of callers who hang up before reaching an agent. Below 5% is healthy. Above 10% is a revenue problem.
-- Abandon rate by hour (find your problem hours)
SELECT
HOUR(FROM_UNIXTIME(time)) AS hour_of_day,
COUNT(CASE WHEN event = 'ABANDON' THEN 1 END) AS abandoned,
COUNT(CASE WHEN event IN ('CONNECT','ABANDON') THEN 1 END) AS total_attempts,
ROUND(100.0 * COUNT(CASE WHEN event = 'ABANDON' THEN 1 END) /
NULLIF(COUNT(CASE WHEN event IN ('CONNECT','ABANDON') THEN 1 END), 0), 1) AS abandon_pct
FROM queue_log
WHERE time > UNIX_TIMESTAMP(NOW() - INTERVAL 7 DAY)
GROUP BY HOUR(FROM_UNIXTIME(time))
ORDER BY abandon_pct DESC;Run this query once. You will find 2-3 hours where abandon rate spikes. Those are your understaffed windows.
Tier 2: Review Daily
4. Average Handle Time (AHT) by Agent
AHT varies wildly between agents. The question is whether the variation indicates a problem or a difference in call complexity.
-- AHT by agent with call count (last 7 days)
SELECT
agent,
COUNT(*) AS calls,
ROUND(AVG(CAST(data2 AS UNSIGNED))) AS avg_talk_sec,
ROUND(AVG(CAST(data1 AS UNSIGNED))) AS avg_hold_sec,
ROUND(AVG(CAST(data2 AS UNSIGNED) + CAST(data1 AS UNSIGNED))) AS avg_total_sec
FROM queue_log
WHERE event IN ('COMPLETECALLER', 'COMPLETEAGENT')
AND time > UNIX_TIMESTAMP(NOW() - INTERVAL 7 DAY)
AND agent != 'NONE'
GROUP BY agent
HAVING calls >= 10
ORDER BY avg_total_sec DESC;An agent with 180s AHT handling 50 calls/day is not necessarily worse than one with 120s handling 40 calls. Check first call resolution rates before assuming faster means better.
5. Agent Occupancy
Time spent handling calls as a percentage of logged-in time. The healthy range is 70-85%.
Below 70%: overstaffed or agents avoiding queue. Above 85%: heading toward agent burnout. ACW quality drops, error rates increase, turnover follows.
6. Wait Time Distribution (Not Average)
Average wait time is misleading. A queue with 15-second average might have 80% of calls answered in 5 seconds and 20% waiting 3+ minutes. The experience is terrible for that 20%.
-- Wait time distribution (percentiles)
SELECT
queuename,
COUNT(*) AS total_calls,
ROUND(AVG(CAST(data1 AS UNSIGNED))) AS avg_wait,
-- Approximate percentiles using conditional aggregation
MAX(CASE WHEN rn <= total * 0.50 THEN wait_sec END) AS p50_wait,
MAX(CASE WHEN rn <= total * 0.90 THEN wait_sec END) AS p90_wait,
MAX(CASE WHEN rn <= total * 0.95 THEN wait_sec END) AS p95_wait
FROM (
SELECT
queuename,
CAST(data1 AS UNSIGNED) AS wait_sec,
ROW_NUMBER() OVER (PARTITION BY queuename ORDER BY CAST(data1 AS UNSIGNED)) AS rn,
COUNT(*) OVER (PARTITION BY queuename) AS total
FROM queue_log
WHERE event = 'CONNECT'
AND time > UNIX_TIMESTAMP(NOW() - INTERVAL 7 DAY)
) sub
GROUP BY queuename;If P50 is 8 seconds but P95 is 180 seconds, you have a bimodal distribution. The fix is usually staffing at peak hours, not adding agents across all shifts.
Tier 3: Review Weekly
7. Trunk Utilization
How close are your SIP trunks to capacity? Stay below 80% peak utilization. Above that, callers get busy signals during spikes.
-- Peak concurrent calls per trunk (last 7 days)
SELECT
DATE(calldate) AS day,
HOUR(calldate) AS peak_hour,
SUBSTRING_INDEX(channel, '/', 2) AS trunk,
COUNT(*) AS concurrent_calls
FROM cdr
WHERE calldate > DATE_SUB(NOW(), INTERVAL 7 DAY)
AND disposition = 'ANSWERED'
GROUP BY DATE(calldate), HOUR(calldate), SUBSTRING_INDEX(channel, '/', 2)
ORDER BY concurrent_calls DESC
LIMIT 10;Setting Up Monitoring: Three Approaches
Approach 1: CLI Scripts (Free, Limited)
Good for ad-hoc checks. Not a monitoring solution.
#!/bin/bash
# quick-queue-status.sh - run via cron every 5 minutes
QUEUES=$(asterisk -rx "queue show" | grep "^[a-zA-Z]" | awk '{print $1}')
for Q in $QUEUES; do
WAITING=$(asterisk -rx "queue show $Q" | grep "has [0-9]* calls" | awk '{print $3}')
AGENTS=$(asterisk -rx "queue show $Q" | grep -c "SIP/")
if [ "$WAITING" -gt 5 ] && [ "$AGENTS" -gt 0 ]; then
RATIO=$((WAITING / AGENTS))
if [ "$RATIO" -gt 3 ]; then
echo "ALERT: Queue $Q has $WAITING calls waiting with $AGENTS agents (ratio: $RATIO:1)"
# Send alert via email, Slack, etc.
fi
fi
doneThis gives you basic alerting. But it checks every 5 minutes - a lot can go wrong in 5 minutes. And it tells you nothing about trends, patterns, or individual agent performance.
Approach 2: Grafana + Custom Pipeline (Free, 40-80 Hours)
For teams with DevOps capability and time:
- —Install Grafana + PostgreSQL (or TimescaleDB for time-series optimization)
- —Write a queue_log parser that loads events into the database
- —Build an AMI listener for real-time events
- —Create dashboards for each metric above
- —Configure alerting rules
Realistic assessment: The initial build takes 40-80 hours depending on your SQL/Grafana experience. The dashboard looks great. Then:
- —Agent joins/leaves/pauses require dashboard updates
- —Queue configuration changes break queries
- —Someone needs to maintain the AMI listener (it disconnects, Asterisk restarts, network blips)
- —Historical data retention needs management
Most Grafana-on-Asterisk projects I have seen get abandoned within 6-12 months when the engineer who built them moves on. The 80% that breaks is not the dashboard - it is the data pipeline maintenance.
Read our complete Grafana vs Astervis comparison for a detailed assessment.
Approach 3: Astervis (Purpose-Built, 10 Minutes)
Astervis is built specifically for Asterisk call center monitoring. It handles the AMI connection, queue_log parsing, real-time dashboards, agent management, and alerting out of the box.
# Install on your Asterisk server or a separate machine
curl -fsSL https://api.astervis.io/api/releases/install.sh | bashThen in the dashboard:
- —Add your Asterisk server (AMI credentials)
- —Queues auto-discovered
- —Start monitoring
What you get:
- —30+ charts including heatmaps, trend comparisons, and queue analytics
- —Real-time dashboards (sub-second AMI event processing)
- —Agent performance tracking with KPIs and leaderboards
- —SLA monitoring with configurable thresholds per queue
- —Shift scheduling and operator management
- —Call recording playback from the dashboard
- —CRM integration (Bitrix24, AmoCRM)
- —Self-hosted - your data stays on your network
Pricing: From $119/month, unlimited operators. 14-day free trial, no credit card.
Works with FreePBX, Sangoma, Issabel, VitalPBX - anything running Asterisk underneath.
Asterisk Configuration for Monitoring
Tired of guessing what's happening in your queues?
Astervis gives you 30+ real-time charts, operator KPIs, and CRM integration for your Asterisk PBX. Self-hosted. Install in 5 minutes. From $119/mo flat — unlimited operators.
Enable Full Event Logging
Most Asterisk installations have incomplete logging. Fix this first:
; /etc/asterisk/queues.conf - add to EACH queue section
[sales]
; ... your existing config ...
eventwhencalled = yes ; Log which agent was offered the call
eventmemberstatus = yes ; Log agent state changes (pause, unpause, login)
monitor-type = MixMonitor ; Enable call recording
queue-callswaiting = yes ; Announce position to callers
queue-thankyou = beep ; Confirmation sound when connected
; Performance tuning
wrapuptime = 30 ; 30s between calls (prevents burnout, improves ACW tracking)
timeout = 15 ; Ring agent for 15s before trying next
retry = 5 ; Wait 5s between agent attemptsMy take on wrapuptime: The default is 0, which means agents get the next call immediately after hanging up. This is terrible for three reasons: (1) agents cannot complete after-call work, so they do it during the next call, inflating AHT; (2) it causes burnout - read our burnout prevention guide; (3) your AHT numbers become meaningless because wrap-up time is hidden inside talk time.
Set wrapuptime to 15-30 seconds minimum. Your AHT will look higher initially but your actual productivity will improve.
Configure AMI for External Tools
; /etc/asterisk/manager.conf
[general]
enabled = yes
port = 5038
bindaddr = 0.0.0.0
[monitoring]
secret = use_a_strong_32_char_password
deny = 0.0.0.0/0.0.0.0
permit = 10.0.0.100/255.255.255.255 ; Your monitoring server IP only
read = system,call,log,agent,reporting
write = system,call,agent,reporting
writetimeout = 5000Security: Never use permit = 0.0.0.0/0.0.0.0 in production. AMI has full control over your PBX. Restrict to specific IPs.
After changes:
asterisk -rx "manager reload"
# Test: telnet your-asterisk-server 5038Queue Strategy Selection
Your monitoring data is only as good as your queue strategy. Different strategies produce different patterns:
| Strategy | Behavior | Best For | Monitoring Pattern |
|---|---|---|---|
| ringall | Ring all agents | Small teams (<5) | Even distribution, high answer rate |
| leastrecent | Ring agent idle longest | Balanced workload | Uniform agent metrics |
| fewestcalls | Ring agent with fewest calls | Fair distribution | Similar call counts |
| rrmemory | Round-robin with memory | Predictable | Sequential agent patterns |
| random | Random agent | Large teams | Statistical distribution |
| linear | Fixed order priority | Skills-based | Top agents overloaded |
linear gives the most predictable quality but burns out your best agents. leastrecent is the best general-purpose strategy - it naturally balances workload, which makes your monitoring data more meaningful.
Common Monitoring Mistakes
Mistake 1: Monitoring Averages Instead of Distributions
Average wait time of 25 seconds sounds acceptable. But the distribution might be:
- —60% of calls: answered in under 10 seconds
- —25% of calls: answered in 30-60 seconds
- —15% of calls: waiting 2-5 minutes
That 15% is your churn risk. Use P90 and P95 percentiles instead of averages. The SQL queries above calculate both.
Mistake 2: Not Separating Queue Types
Mixing sales queue metrics with support queue metrics makes both useless. A 30-second wait in a sales queue costs revenue. A 30-second wait in a callback queue is expected. Configure separate SLA targets per queue.
Mistake 3: Treating CDR as Queue Analytics
CDR records calls. Queue_log records queue interactions. They are different data sources that answer different questions.
CDR tells you: "This call lasted 3 minutes." Queue_log tells you: "This caller waited 45 seconds, agent SIP/200 answered, talk time was 2 minutes 15 seconds, caller hung up first."
If you are building reports from CDR data only, you are missing the queue context. See our CDR reporting guide for how to combine both sources effectively.
Mistake 4: Alert Fatigue
Setting alerts for every minor threshold creates noise. Agents learn to ignore all alerts, including critical ones.
Start with three alerts only:
- —Queue overflow: More than 10 callers waiting for more than 2 minutes
- —SLA breach: Service level drops below 60% for 15+ minutes
- —Trunk capacity: Concurrent calls exceed 80% of trunk capacity
Add more alerts only when you have proven you act on these three consistently.
Mistake 5: No Historical Baseline
Real-time dashboards are useless without context. "47 calls in queue" means nothing if you do not know that Tuesday at 2 PM normally has 50. You need at least 30 days of historical data before your real-time dashboard becomes actionable.
Monitoring Checklist
Use this checklist to verify your Asterisk monitoring setup is complete:
Data Collection:
- — AMI enabled with monitoring user
- — queue_log writing all events (eventwhencalled, eventmemberstatus)
- — CDR recording to database (not just flat file)
- — wrapuptime set per queue (not 0)
- — Call recording enabled (MixMonitor)
Dashboards:
- — Real-time queue status (calls waiting, agents available)
- — SLA gauge per queue (with correct threshold)
- — Abandon rate by hour (heatmap)
- — Agent performance table (AHT, calls, FCR)
- — Trunk utilization chart
Alerting:
- — Queue overflow alert configured
- — SLA breach alert configured
- — Trunk capacity alert configured
- — Alert delivery tested (email, Slack, webhook)
Reporting:
- — Daily summary automated
- — Weekly trend report configured
- — Monthly capacity report scheduled
What Changes with Real-Time Monitoring
The teams that get monitoring right see consistent improvements:
- —Abandon rate drops 30-50% in the first month (because you see problems as they happen, not next week)
- —Agent idle time decreases 15-20% (better real-time staffing decisions)
- —SLA compliance improves 10-25% (threshold alerts prevent sustained breaches)
- —Staffing costs decrease 5-10% over 3 months (heatmaps reveal overstaffing windows)
These are not hypothetical. They are patterns I see repeatedly when teams move from "check the CLI occasionally" to continuous monitoring.
The gap between a well-monitored Asterisk call center and an unmonitored one is not technical sophistication. It is visibility. You cannot fix what you cannot see.
Running an Asterisk call center without real-time monitoring? Start your free 14-day Astervis trial and get 30+ dashboards in 10 minutes.
Already monitoring with Grafana or scripts? See how Astervis compares in our monitoring tools comparison.
Stop guessing. Start monitoring.
See your Asterisk call center's real performance — queue wait times, agent activity, trunk usage, and 30+ charts. Self-hosted on your server. Install in 5 minutes. No credit card required.
From $119/mo flat. Unlimited operators. 14-day free trial.
