If you've ever called any company's support or sales line, you've probably used a queue. Queueing is a crucial part of an IVR for any company to handle multiple callers at once. SignalWire makes it very easy to store callers in a queue in the order that they called and then connect them to a live agent whenever it's their turn. This guide will show you how to implement queues simply using XML bins and how to implement them using the SignalWire SDK.
You will need a SignalWire phone number that we can configure to handle inbound calls or to make outbound calls. You can read our handy guide on how to purchase a phone number here if you have not done so already.
You can also read here to learn more about webhooks and how to configure them. We will be using inbound voice call webhooks for recording inbound calls.
If you want to create an application that can handle more complex conferencing, you will also need to create an XML document in one of the SignalWire SDKs. This allows for greater customizability and the ability to build expansive applications serving multiple purposes in one document. You will need to make sure you have installed one of the SignalWire client SDKs in Python, Node.JS, PHP, or Ruby to write the XML document. You can view installation instructions here.
Lastly, if you are using the SignalWire SDK, you will need to host your code on a server to make it publically accessible! For local testing without using a server, ngrok is a great tool to allow you to create an SSH tunnel to your code on localhost making it publically accessible by SignalWire. You will then need to use it as your webhook for handling inbound calls.
At the most basic level, the only thing needed to create a simple queue is to use the verb
Enqueue to place an incoming caller into a queue. You can create an XML bin with the following code and attach it to a phone number as the webhook for handling inbound calls.
<?xml version="1.0" encoding="UTF-8"?> <Response> <Say> Thank you for calling Best Quality Vacuum. Ed Galbraith is currently unavailable or speaking with other customers. Please stay on the line to speak with one of his representatives. </Say> <Enqueue>Best Quality Vacuum</Enqueue> </Response>
To connect to the customer in the queue who is next in line, we simply need to use the
Dial verb to reach the same queue and include a URL with instructions for handling the customer's side of the call. In this case, we will play a short message.
<?xml version="1.0" encoding="UTF-8"?> <Response> <Say>Connecting to caller...the next voice you hear will be the customer.</Say> <Dial> <Queue url="https://bowl-test.signalwire.com/laml-bins/962230ad-10f5-485d-9bfa-458c7ae1213c">Best Quality Vacuum</Queue> </Dial> </Response>
The URL in the previous bin can point to another bin that includes the
Say verb to play a short message for the caller informing them that they will soon be connected to an agent. You could also use the
<?xml version="1.0" encoding="UTF-8"?> <Response> <Say>This call will be recorded for quality control and training. You will now be connected to the next representative.</Say> </Response>
The code sample below is an example of a queuing application on a Flask framework with the Python SDK. However, you can replicate this demo with any of our other SignalWire SDKs and a valid web framework.
This example will set a global array that contains the phone numbers of your agents. You can have only one agent or you could list a whole team.
When a call comes in, the code will first check if any digits were pressed and passed along with the HTTP request. If there were no digits pressed, we will then check to see if the caller number is in the support agent array. If the caller is a support agent, we will play a prompt asking them to either press 1 to connect to the next caller in the queue or press 2 to hang up the call and take a break. Once they press digits, we will pass those in the HTTP request back to the default route.
This time, we will check what digits are pressed and either dial the queue or hang up the call. If neither 1 or 2 is pressed, we will remind the agent to pick a choice and replay the prompt. If the caller is a customer and therefore not in the support agent array, we will play a short prompt advising them to wait in the queue for the next available agent.
from flask import Flask, request from signalwire.voice_response import VoiceResponse, Dial, Gather from dotenv import load_dotenv load_dotenv() app = Flask(__name__) # Set up support agents support_agents = ['+12141111111', '+13461111111'] @app.route("/default", methods=["GET", "POST"]) def voice(): # instantiate voice response as response response = VoiceResponse() # check if any digits have already been pressed and passed back to our default route if "Digits" in request.values: selection = request.values['Digits'] # check if caller is support agent if request.values.get('From') in support_agents: # if caller is support agent and digits pressed were 1, we will connect to the support queue if selection == "1": response.say("You will now be connected to the customer, please hold. " "The next voice you hear will be the customer's.") dial = Dial() dial.queue("support") response.append(dial) # if the caller is a support agent and digits pressed were 2, we will hangup the call elif selection == "2": response.say("That's okay, everyone needs a break! See you later for more customer calls, goodbye!") response.hangup() # if digits pressed were not 1 or 2 and caller is a support agent, we will ask them to make a selection and replay the prompt else: response.say("Please select 1 or 2 so that we can direct your call!") # if no digits were pressed, assume this is the first time calling in and play welcome message else: # if caller is support agent, use gather to gather input and play prompt to connect to caller or hang up if request.values.get('From') in support_agents: gather = Gather(num_digits=1) gather.say( "Hello team member. Thank you for dialing in. Press 1 to connect to the next caller or " "press 2 to end the call if you are not ready to speak to customers.") response.append(gather) # if caller is not support agent, play customer prompt and use enqueue to put them in the support queue else: response.say("Hello and thank you for calling! All of our agents are currently on the line with other " "customers. Please hold, and someone will be with you soon.") response.enqueue("support") # redirect to default after gathering digits so that the call can be routed correctly response.redirect("/voice") # convert response to string as compatibility api requires proper XML return str(response) # run app if __name__ == "__main__": app.run()
Updated 26 days ago