Overview

In-house outbound and inbound dialer on Asterisk.

CRM pushes leads into dialer_master_data. Agents join a Socket.IO panel. One process claims rows, originates through AMI, and settles hangups. Mode is Progressive or Predictive from dialer_config. Inbound PSTN is always on.

Skill-only claim No master agent pin AMI originate Unlimited hold

How the pieces fit

HTTP APICRM upserts leads, closes tickets, schedules callbacks, unholds disposed rows. Does not originate.
Socket hubAgent ready/pause (picker reason required), dashboard snapshot, dialer phases, inbound ringing, redial.
EnginesProgressive: one call per idle agent. Predictive: customer first, then skill bridge.
AMI + inboundDevice state, originate, bridge, MOH. PSTN park and skill offer.

Roster is dialer_employee for module_id = in_house_operations. Skills JSON must include the lead form_type. AMI only tracks those extensions. Config reloads every 30 seconds; switching dialer_type waits until the floor is idle.

Life of a lead

  1. CRM POST /api/leads upserts by oli_id and mints a new data_id (returned on the 201). Status is Pending, or Callback if a callback priority has a time.
  2. An idle ready agent with matching skill claims the row: Calling, reserved. call_count does not increment here.
  3. Progressive originates the agent channel. Predictive originates the customer Local channel, then bridges a skilled agent on answer.
  4. Hangup settles master + a row on dialer_call_attempts (agent, call_type, and the master data_id at settle).
  5. Not Connected retries on dialer_config.retry_pattern (currently [4,4,3,2,1,1,1,1,1,1,1]) until max_tries (currently 20). Abandoned is not on that cycle — it keeps a future next_retry_at, otherwise waits retry_seconds (currently 3600). Received / Rejected / Disposed stop unless socket redial or CRM POST /api/unholdDialerData.

Master has no agent_id column. Sending it on the API is a 400. Connected agent is on dialer_call_attempts only.

Dial status

StatusMeaningClaimed again?
PendingIn the poolYes, skill + priority allowlist
CallbackWaiting on callback_scheduled_atWhen due, skill + priority allowlist
CallingReserved, originate in flightNo
ReceivedTalkedNo (unless redial)
Not ConnectedNo answer / busy / congestionAfter retry_pattern / retry_seconds
AbandonedCustomer left while waiting (predictive / inbound)After retry_seconds (or existing next_retry_at)
RejectedCancel / invalid / reject causeNo (unless redial)
DisposedNC cap or CRM CloseNo unless redial or unholdDialerData

Tables this process owns

TableRole
dialer_employeeRoster, skills, priority_ids, panel pause/active
dialer_configMode, wrap, ratio, retry, hours, isMaintainance
dialer_priorityQueue order, callback flags
dialer_master_dataLeads. No agent pin
dialer_master_push_logOne row per lead written by POST /api/leads / /api/master: oli_id, data_id, priority_id, pushed_date
dialer_call_attemptsEvery settle, with agent, hold seconds, master data_id snapshot, previous_dial_status (master at claim), and call_type (outgoing / incoming / redial)
dialer_agent_declinesSIP deny on a live hold (same call_type values)
dialer_agent_pausesPanel pause intervals
dialer_api_call_logHold / RNR / NC / remarks CRM posts
dialer_after_hours_callsAfter-hours DID misses (announce path only)

What this dialer does not do