Skip to main content
Skip table of contents

EFSwitch Dialer v1.1

Work In Progress

This document is a work in progress until details have been finalized.


To automate outbound communication with customers via interactive voice response (IVR) systems or agents.


  • The campaign information is specified in the user's campaign manager of choice(Mautic etc).
  • This campaign when started is sent to the scheduler which stores the contacts and sends them to CCM at their designated start times.
  • CCM feeds contacts one by one to the voice connector which stores them in its own database.
  • The dialer periodically runs a query to retrieve pending contacts from the database:
    • The total number of contacts to be retrieved depends on the current free call slots.
    • These contacts are distributed equally among all campaigns.
  • Appropriate action is taken for each contact based on whether its campaign time is AGENT or IVR.
  • In case of AGENT campaign call, a payload containing call information is sent to the voice connector which requests an agent from the CCM.
  • If an agent is received by the voice connector, the information is sent to the dialer and a call is made to the customer via Freeswitch ESL and bridged to the agent.
  • If an agent is not received then the dialer is notified and it sets the contact back to pending again.
  • one of the following flows will take place based on the dialing mode:
  • In case of IVR campaign call, a call is made to the customer and an IVR menu plays.
  • In either case, a post call script ensures that call results are saved in the database.


Proposed Solution

Contact Structure

The parameters for a campaign contact are set in the campaign manager e.g. Mautic and sent to the scheduler in a payload with the following format:

Campaign contact

    "id": "aba035c8-b9a9-4d9b-ae40-6fc9a9c02c07", //ID to identify contact
    "header": {
        "channelData": {
            "channelCustomerIdentifier": "1001", //Dialing number of customer
            "serviceIdentifier": "1218", //Service identifier of channel connector
            "additionalAttributes": []
        "customer": {
            "_id": "61c2b22725dadf1a1050c582"
        "shedulingMetaData": {
            "scheduledDatetime": "2023-04-10T22:55:00+03:00", //Scheduled dial time of this contact
            "campaignId": "123456789", //Unique ID for campaign
            "campaignType":"TYPE", //Can be AGENT or IVR
            "gatewayId": "4d995f13-f90a-4bc9-8045-23809a34f82e", //UUID of SIP gateway through which call will be routed to customer
            "campaignContactId": "contact-123", //not in use
            "startTime": "2023-04-10T09:00:01+03:00", //Start time for dialing this campaign
            "endTime": "2023-04-10T20:00:01+03:00", //End time for dialing this campaign
            "priority": "1", //Dialing priority of contact within a campaign
            "ivr": "6666", //Used for ivr campaigns, extension number of IVR menu 
            "dialingMode": "PROGRESSIVE", // Used for agent campaigns, can be PREDICTIVE, PREVIEW or PROGRESSIVE  
            "routingMode": "QUEUE", //Used for agent campaigns, can be AGENT or QUEUE  
            "resourceId": "7bn473-c34de35c-v54nv5u43-5dlh68c", //Used for agent campaigns, QUEUE or AGENT ID
            "queueName": "", //Used for agent campaigns, queue name i.e. voice queue 4
            "webhookId": "KL9DF2", //not in use
            "agent": null, //not in use
            "queue": null //not in use
    "body": {
        "type": "PLAIN",
        "markdownText": "Hello Customer"

These parameters are described in the following sections, along with other relevant information that the dialer stores in a database based on the state of the contact.

FieldDescriptionTypeProvided By
idUnique UUID identifier used to identify this contact and callVARCHAR(40)Campaign Manager
customer_numberThe number to be dialedVARCHAR(20)Campaign Manager
campaign_typeIVR or AGENTVARCHAR(20)Campaign Manager
gateway_idThe UUID of the Freeswitch gateway to be used to dial  customer numberVARCHAR(40)Campaign Manager
statuspending, agent_pending, dialed, ended, stopped or failedVARCHAR(20)Dialer
call_resultThe result of a call e.g. Normal clearing, User busy etcVARCHAR(40)Dialer
received_timeThe time at which the contact was received from CCMDateTimeDialer
dial_timeThe time at which the contact was sent by the dialer to Freeswitch to be dialedDateTimeDialer
campaign_contact_idThe id of the contact received in CCM message payloadVARCHAR(40)Campaign Manager
campaign_idThe campaign id received in CCM messageVARCHAR(40)Campaign Manager
start_timeThe contact cannot be dialed before this timeDateTimeCampaign Manager
end_timeThe contact cannot be dialed after this timeDateTimeCampaign Manager
priorityThe contact between 1-10IntegerCampaign Manager
IVR campaign

Can be provided in an IVR campaign. If not provided, the default value configured in the dialer is used.

FieldDescriptionTypeProvided By
ivrThe ivr to be selected, THE IVR number, if contact is IVR basedVARCHAR(20)Campaign Manager
Agent campaign

Mandatory for agent campaigns.

FieldDescriptionTypeProvided By
routing_modeAGENT or QUEUE, only for contacts with campaign_type = AGENTVARCHAR(20)Campaign Manager
resource_idQueue or AgentId based on routing_modeVARCHAR(40)Campaign Manager
queue_nameThe name of queue if routing_mode = QUEUE, optional if routing_mode = AGENT or if routing_mode = QUEUE and resource_id is setVARCHAR(20)Campaign Manager

Dialing Flow

  1. The dialer will periodically query the database and take note of all the campaigns and the number of their contacts present.
  2. It will also take note of the current free call slots.
  3. Based on this information, it will calculate the number of contacts to be retrieved for each campaign such that they are all treated equally.
  4. A set of queries is then run to retrieve the allotted number of 'pending contacts for each campaign.
  5. These contacts are then sequentially processed based on the campaign type.

IVR Campaigns

  1. For IVR based campaigns, the IVR number is taken from the contact entry if set.
  2. If the IVR number is not provided in the contact entry then the default IVR specified in the dialer configuration is used.
  3. The dialer checks via Freeswitch ESL if the gateway provided is valid.
    1. If it is valid, then the following command is sent to Freeswitch to initiate the call: 

      Originate command

      originate {session_in_hangup_hook=true, api_hangup_hook='lua callResults.lua', origination_uuid=call_uuid}sofia/gateway/gateway-id/customerNum IvrNumber XML Freeswitch-IP
    2. If invalid, the contact status is set to 'failed' and it will not be redialed.
  4. Once the call ends, a post-call script present on Freeswitch runs automatically and stores the call result to the database and sets the status to 'ended'.

Agent Campaigns

  1. If the campaign call type is of 'AGENT', then the contact status is set to 'agent_pending' and the following payload is posted to the voice connector API:

    Call details http://VC-IP-addr:port/fs-message/startprocess

        "callingNumber":"2001",//Customer number
        "queue":"Voice Queue", //Contains queue name or ID, will use default queue if blank
        "queueType":"NAME", //Queue identification type, can be NAME or ID
        "callUid":"8b5342ca-66c1-4d41-a2a1-c04be8ee5228", //Unique ID of call
        "eslHost":"", //The IP address of the Freeswitch server through which calls are being routed
        "serviceIdentifier":"1218", //Service identifier of the voice connector 
        "direction":"OUTBOUND" //Direction of this call, can be DIRECT_TRANSFER, INBOUND or OUTBOUND
  2. The voice connector sends back the following payload when it received either an agent reserved or no agent available notification from the CCM:

    Agent Details for Dialer http://Dialer-IP-addr:port/dialer-connector/agent

    	"agent": "2001", //Agent extension, empty when no agent available
    	"uuid": "b07ffee5-b80f-46af-af96-6e57c5030843", //Unique ID of call
    	"queue": "voice Queue 3" //Agent queue name, empty when no agent available
    1. If the agent field is empty, this means that no agent was available, so the dialer sets the contact status to 'pending' to try again the next time it queries for pending contacts.
    2. If the agent and queue fields have values then the following command is sent to Freeswitch which will call the customer and bridge the answered call to the agent:

      Freeswitch OUTBOUND command

      originate {ignore_early_media=true, session_in_hangup_hook=true, sip_h_X-CallType=PREVIEW, sip_h_X-queueType=NAME, sip_h_X-queue='voice Queue 5', api_hangup_hook='lua callResults.lua', origination_uuid=call_uuid}sofia/gateway/my-gateway/customerNum &bridge(user/agentExtension@eslHost)
  3. If the customer declines the call, the post call script sends an END_CHAT payload to the CCM to close the conversation. In either case it also saves the call result to the database and sets the status to 'ended'.

    END_CHAT https://CCM-FQDN/ccm/message/receive

      "id": "1234567",
      "header": {
        "channelData": {
          "channelCustomerIdentifier": "1000", //Customer phone number to be dialed  
          "serviceIdentifier": "1218", //Service identifier of the voice connector
          "language": {},
          "timestamp": 1690437057371,
          "securityInfo": {},
          "intent": "END_CHAT",
          "sender": {
            "id": "f1370ff7-43fa-496e-9966-e64061d35f5c",
            "senderName": "MY_IVR",
            "type": "IVR"
        "body": {<irrelevant>}

Additional Functions

Campaign controls

The dialer exposes three APIs that can be called by the campaign manager to start, stop or purge campaigns:

Failover Cases


The voice connector is down and the agent reservation request cannot be sent to it.

Contact status remains on pending and will be tried again.

The database is down and dialer cannot retrieve contactsDialer will retry on its next cycle.
Freeswitch gateway is down.Contact status is set to failed and call result set as Invalid Gateway.
Freeswitch is down and call command cant be sent.

Contact status is set to failed.

Campaign manager sends campaign control command(start/stop/purge) to dialer, but database is down.A Service Unavailable error is returned.
Campaign manager sends campaign control command to dialer, but no entries with supplied campaign ID are found.A Not Found error is returned.
Voice connector sends agent details to dialer but database is down.A Service Unavailable error is returned.
Voice connector sends agent details to dialer but an unexpected error occurs e.g. Freeswitch is down.

An Internal Server error is returned.


  • Dialing outbound IVR campaigns.
    • Dial out a call to customer and play a specified IVR menu.
  • Dialing outbound agent-based campaigns.
    • Reserve an agent against a customer, dial a call to the customer, and connect them to the reserved agent.
  • Run multiple campaigns simultaneously with a limited number of free call slots.
    • Algorithm decides how many calls per campaign to dial out for any given number of free call slots.
    • If free slots greater than total campaigns, then contacts are picked from each campaign in order of smallest campaign to largest.
    • Within a campaign, contacts are picked according to the FIFO order(queue).
    • If free slots lesser than or equal to total campaigns then 1 contact each picked from as many campaigns as there are slots, in order of smallest campaign to largest.
  • Record result of each call e.g. Normal clearing, user busy, invalid gateway etc and store in database along with other contact information.
  • Send result of each agent-based call as Delivery notifications to EFCX via the voice connector.
  • Campaign controls API to :
    • Stop pending contacts of a campaign.
    • Start stopped contacts of a campaign.
    • Purge pending contacts of a campaign.
  • API to check current number of ongoing calls.
JavaScript errors detected

Please note, these errors can depend on your browser setup.

If this problem persists, please contact our support.