Phone IVR

An IVR (Interactive Voice Response) system is also known as phone menu system. It is an automated phone system that interacts with a caller via pre-recorded or dynamic text-to-speech messages and inputs, via the keypad.

IVR systems are popular as they can handle large call volumes and help reduce the costs associated with customer service. With our app, you can build an entire phone menu system on the Plivo platform (in any computer language), without relying on expensive physical infrastructure.

The instructions below will teach you how to build your own IVR system that can:

Read a pre recorded text in different languages if ‘1’ is pressed.

Play a song if ‘2’ is pressed.

Say “Sorry, I didn’t catch that. Please hang up and try again later.” if nothing is pressed.

The app will operate in the following sequence:

The user dials the Plivo IVR phone number.

The user is prompted with the message “Welcome to the Plivo IVR Demo App. Press 1 to listen to a pre recorded text in different languages. Press 2 to listen to a song.”

During the call, if the user presses ‘1’, then Plivo reads aother message “Press 1 for English. Press 2 for French. Press 3 for Russian” . If the user presses ‘2’, then Plivo plays a song.

If anything else is pressed or if the user does nothing, then Plivo says “Sorry, I didn’t catch that. Please hang up and try again later.” and hangs up.

Prerequisites

Use a web hosting service to host your web application. There are many inexpensive cloud hosting providers that you can use for just a few dollars a month. Follow the instructions of your hosting provider to host your web application.

Set up a Web Server

Let’s assume your web server is located at example.com. Below is a snippet to set up a route on your webserver. Lets call it, response/ivr. Now when we send an HTTP request to example.com/response/ivr this route will be invoked. You will now have to configure this URL in your Plivo application.

# -*- coding: utf-8 -*-
fromflaskimportFlask,Response,request,url_forimportplivoxml# This file will be played when a caller presses 2.
PLIVO_SONG="https://s3.amazonaws.com/plivocloud/music.mp3"# This is the message that Plivo reads when the caller dials in
IVR_MESSAGE1="Welcome to the Plivo IVR Demo App. Press 1 to listen to a pre recorded text in different languages. \
Press 2 to listen to a song."IVR_MESSAGE2="Press 1 for English. Press 2 for French. Press 3 for Russian"# This is the message that Plivo reads when the caller does nothing at all
NO_INPUT_MESSAGE="Sorry, I didn't catch that. Please hangup and try again \
later."# This is the message that Plivo reads when the caller inputs a wrong number.
WRONG_INPUT_MESSAGE="Sorry, it's wrong input."app=Flask(__name__)@app.route('/response/ivr/',methods=['GET','POST'])defivr():response=plivoxml.Response()ifrequest.method=='GET':getdigits_action_url=url_for('ivr',_external=True)getDigits=plivoxml.GetDigits(action=getdigits_action_url,method='POST',timeout=7,numDigits=1,retries=1)getDigits.addSpeak(IVR_MESSAGE1)response.add(getDigits)response.addSpeak(NO_INPUT_MESSAGE)printresponse.to_xml()returnResponse(str(response),mimetype='text/xml')elifrequest.method=='POST':digit=request.form.get('Digits')printdigitifdigit=="1":# Read out a text.
getdigits_action_url1=url_for('tree',_external=True)getDigits1=plivoxml.GetDigits(action=getdigits_action_url1,method='POST',timeout=7,numDigits=1,retries=1)getDigits1.addSpeak(IVR_MESSAGE2)response.add(getDigits1)response.addSpeak(NO_INPUT_MESSAGE)elifdigit=="2":# Listen to a song
response.addPlay(PLIVO_SONG)else:response.addSpeak(WRONG_INPUT_MESSAGE)printresponse.to_xml()returnResponse(str(response),mimetype='text/xml')@app.route('/response/tree/',methods=['GET','POST'])deftree():response=plivoxml.Response()digit=request.form.get('Digits')ifdigit=="1":text=u"This message is being read out in English"params={'language':"en-GB",}response.addSpeak(text,**params)elifdigit=="2":text=u"Ce message est lu en français"params={'language':"fr-FR",}response.addSpeak(text,**params)elifdigit=="3":text=u"Это сообщение было прочитано в России"params={'language':"ru-RU",}response.addSpeak(text,**params)else:response.addSpeak(WRONG_INPUT_MESSAGE)printresponse.to_xml()returnResponse(str(response),mimetype='text/xml')if__name__=='__main__':app.run(host='0.0.0.0',debug=True)

# encoding: utf-8require'rubygems'require'sinatra'require'plivo'includePlivo# This file will be played when a caller presses 2.$PLIVO_SONG="https://s3.amazonaws.com/plivocloud/music.mp3"# This is the message that Plivo reads when the caller dials in$IVR_MESSAGE1="Welcome to the Plivo IVR Demo App. Press 1 to listen to a pre recorded text in different languages. Press 2 to listen to a song."$IVR_MESSAGE2="Press 1 for English. Press 2 for French. Press 3 for Russian"# This is the message that Plivo reads when the caller does nothing at all$NO_INPUT_MESSAGE="Sorry, I didn't catch that. Please hangup and try again later."# This is the message that Plivo reads when the caller inputs a wrong number.$WRONG_INPUT_MESSAGE="Sorry, it's wrong input."get'/response/ivr/'dor=Response.new()getdigits_action_url="https://example.com/response/ivr/"params={'action'=>getdigits_action_url,'method'=>'POST','timeout'=>'7','numDigits'=>'1','retries'=>'1'}getDigits=r.GetDigits(params)getDigits.addSpeak($IVR_MESSAGE1)r.addSpeak($NO_INPUT_MESSAGE)putsr.to_xml()content_type'text/xml'returnr.to_s()endpost'/response/ivr/'dodigit=params[:Digits]r=Response.new()if(digit=="1")getdigits_action_url="https://example.com/response/tree/"params={'action'=>getdigits_action_url,'method'=>'GET','timeout'=>'7','numDigits'=>'1','retries'=>'1'}getDigits=r.GetDigits(params)getDigits.addSpeak($IVR_MESSAGE2)r.addSpeak($NO_INPUT_MESSAGE)elsif(digit=="2")r.addPlay($PLIVO_SONG)elser.addSpeak($WRONG_INPUT_MESSAGE)endputsr.to_xml()content_type'text/xml'returnr.to_s()endget'/response/tree/'dodigit=params[:Digits]r=Response.new()if(digit=="1")body="This message is being read out in English"params={'language'=>"en-GB"}r.addSpeak(body,params)elsif(digit=="2")body="Ce message est lu en français"params={'language'=>"fr-FR"}r.addSpeak(body,params)elsif(digit=="3")body="Это сообщение было прочитано в России"params={'language'=>"ru-RU"}r.addSpeak(body,params)elser.addSpeak($WRONG_INPUT_MESSAGE)endputsr.to_xml()content_type'text/xml'returnr.to_s()end

varplivo=require('plivo');varexpress=require('express');varbodyParser=require('body-parser');varapp=express();app.use(bodyParser.urlencoded({extended:true}));app.set('port',(process.env.PORT||5000));// This file will be played when a caller presses 2.varPLIVO_SONG="https://s3.amazonaws.com/plivocloud/music.mp3";// This is the message that Plivo reads when the caller dials invarIVR_MESSAGE1="Welcome to the Plivo IVR Demo App. Press 1 to listen to a pre recorded text in different languages. Press 2 to listen to a song.";varIVR_MESSAGE2="Press 1 for English. Press 2 for French. Press 3 for Russian";// This is the message that Plivo reads when the caller does nothing at allvarNO_INPUT_MESSAGE="Sorry, I didn't catch that. Please hangup and try again later.";// This is the message that Plivo reads when the caller inputs a wrong number.varWRONG_INPUT_MESSAGE="Sorry, you've entered an invalid input.";app.get('/response/ivr/',function(request,response){varr=plivo.Response();vargetdigits_action_url,params,getDigits;getdigits_action_url=request.protocol+'://'+request.headers.host+'/response/ivr/';params={'action':getdigits_action_url,'method':'POST','timeout':'7','numDigits':'1','retries':'1'};getDigits=r.addGetDigits(params);getDigits.addSpeak(IVR_MESSAGE1);r.addSpeak(NO_INPUT_MESSAGE);console.log(r.toXML());response.set({'Content-Type':'text/xml'});response.send(r.toXML());});app.post('/response/ivr/',function(request,response){varr=plivo.Response();vargetdigits_action_url,params,getDigits;vardigit=request.body.Digits;console.log(digit);if(digit==='1'){getdigits_action_url=request.protocol+'://'+request.headers.host+'/response/tree/';params={'action':getdigits_action_url,'method':'POST','timeout':'7','numDigits':'1','retries':'1'};getDigits=r.addGetDigits(params);getDigits.addSpeak(IVR_MESSAGE2);r.addSpeak(NO_INPUT_MESSAGE);}elseif(digit==='2'){r.addPlay(PLIVO_SONG);}else{r.addSpeak(WRONG_INPUT_MESSAGE);}console.log(r.toXML());response.set({'Content-Type':'text/xml'});response.send(r.toXML());});app.all('/response/tree/',function(request,response){varr=plivo.Response();vartext,params;vardigit=request.body.Digits||request.query.Digits;if(digit==="1"){text="This message is being read out in English";params={'language':'en-US'};r.addSpeak(text,params);}elseif(digit==="2"){text="Ce message est lu en français";params={'language':'fr-FR'};r.addSpeak(text,params);}elseif(digit==="3"){text="Это сообщение было прочитано в России";params={'language':'ru-RU'};r.addSpeak(text,params);}else{r.addSpeak(WRONG_INPUT_MESSAGE);}console.log(r.toXML());response.set({'Content-Type':'text/xml'});response.send(r.toXML());});app.listen(app.get('port'),function(){console.log('Node app is running on port',app.get('port'));});

<?phprequire'vendor/autoload.php';usePlivo\Response;# This file will be played when a caller presses 2.$PLIVO_SONG="https://s3.amazonaws.com/plivocloud/music.mp3";# This is the message that Plivo reads when the caller dials in$IVR_MESSAGE1="Welcome to the Plivo IVR Demo App. Press 1 to listen to a pre recorded text in different languages. Press 2 to listen to a song.";$IVR_MESSAGE2="Press 1 for English. Press 2 for French. Press 3 for Russian";# This is the message that Plivo reads when the caller does nothing at all$NO_INPUT_MESSAGE="Sorry, I didn't catch that. Please hangup and try again later.";# This is the message that Plivo reads when the caller inputs a wrong number.$WRONG_INPUT_MESSAGE="Sorry, wrong input.";$r=newResponse();switch($_SERVER['REQUEST_METHOD']){case"GET":$getdigits_action_url="https://example.com/phone_ivr.php";$params=array('action'=>$getdigits_action_url,'method'=>'POST','timeout'=>'7','numDigits'=>'1','retries'=>'1');$getDigits=$r->addGetDigits($params);$getDigits->addSpeak($IVR_MESSAGE1);$r->addSpeak($NO_INPUT_MESSAGE);Header('Content-type: text/xml');echo($r->toXML());break;case"POST":$digit=$_REQUEST['Digits'];if($digit=='1'){$getdigits_action_url="https://example.com/phone_tree.php";$params=array('action'=>$getdigits_action_url,'method'=>'GET','timeout'=>'7','numDigits'=>'1','retries'=>'1');$getDigits=$r->addGetDigits($params);$getDigits->addSpeak($IVR_MESSAGE2);$r->addSpeak($NO_INPUT_MESSAGE);}elseif($digit=='2'){$r->addPlay($PLIVO_SONG);}else{$r->addSpeak($WRONG_INPUT_MESSAGE);}Header('Content-type: text/xml');echo($r->toXML());break;}?><!--phone_tree.php--><?phprequire'vendor/autoload.php';usePlivo\Response;$WRONG_INPUT_MESSAGE="Sorry, it's a wrong input.";$r=newResponse();$digit=$_REQUEST['Digits'];if($digit=='1'){$body="This message is being read out in English";$params=array('language'=>"en-GB");$r->addSpeak($body,$params);}elseif($digit=='2'){$body="Ce message est lu en français";$params=array('language'=>"fr-FR");$r->addSpeak($body,$params);}elseif($digit=='3'){$body="Это сообщение было прочитано в России";$params=array('language'=>"ru-RU");$r->addSpeak($body,$params);}else{$r->addSpeak($WRONG_INPUT_MESSAGE);}Header('Content-type: text/xml');echo($r->toXML());?>

// phoneIvr.javapackageplivoexample;importjava.io.IOException;importjavax.servlet.ServletException;importjavax.servlet.http.HttpServlet;importjavax.servlet.http.HttpServletRequest;importjavax.servlet.http.HttpServletResponse;importorg.eclipse.jetty.server.Server;importorg.eclipse.jetty.servlet.ServletContextHandler;importorg.eclipse.jetty.servlet.ServletHolder;importcom.plivo.helper.exception.PlivoException;importcom.plivo.helper.xml.elements.GetDigits;importcom.plivo.helper.xml.elements.Play;importcom.plivo.helper.xml.elements.PlivoResponse;importcom.plivo.helper.xml.elements.Speak;publicclassphoneIvrextendsHttpServlet{privatestaticfinallongserialVersionUID=1L;// This file will be played when a caller presses 2.StringPLIVO_SONG="https://s3.amazonaws.com/plivocloud/music.mp3";// This is the message that Plivo reads when the caller dials inStringIVR_MESSAGE1="Welcome to the Plivo IVR Demo App. Press 1 to listen to a "+"pre recorded text in different languages. Press 2 to listen to a song.";StringIVR_MESSAGE2="Press 1 for English. Press 2 for French. Press 3 for Russian";// This is the message that Plivo reads when the caller does nothing at allStringNO_INPUT_MESSAGE="Sorry, I didn't catch that. Please hangup and try again later.";// This is the message that Plivo reads when the caller inputs a wrong number.StringWRONG_INPUT_MESSAGE="Sorry, it's wrong input.";@OverrideprotectedvoiddoGet(HttpServletRequestreq,HttpServletResponseresp)throwsServletException,IOException{PlivoResponseresponse=newPlivoResponse();GetDigitsgd=newGetDigits();gd.setAction("http://example/response/ivr/");gd.setMethod("POST");gd.setNumDigits(1);gd.setTimeout(7);gd.setRetries(1);Speakspk=newSpeak(IVR_MESSAGE1);Speakspeak=newSpeak(NO_INPUT_MESSAGE);try{gd.append(spk);response.append(gd);response.append(speak);System.out.println(response.toXML());resp.addHeader("Content-Type","text/xml");resp.getWriter().print(response.toXML());;}catch(PlivoExceptione){e.printStackTrace();}}protectedvoiddoPost(HttpServletRequestreq,HttpServletResponseresp)throwsServletException,IOException{Stringdigit=req.getParameter("Digits");PlivoResponseresponse=newPlivoResponse();if(digit.equals("1"){// Read out a textGetDigitsgd=newGetDigits();gd.setAction("http://example.com/response/tree/");gd.setMethod("POST");gd.setNumDigits(1);gd.setTimeout(7);gd.setRetries(1);Speakspk=newSpeak(IVR_MESSAGE2);try{gd.append(spk);response.append(gd);}catch(PlivoExceptione){e.printStackTrace();}}elseif(digit.equals("2")){// Listen to a songPlayplay=newPlay(PLIVO_SONG);try{response.append(play);}catch(PlivoExceptione){e.printStackTrace();}}else{// Wrong inputSpeakspeak=newSpeak(WRONG_INPUT_MESSAGE);try{response.append(speak);}catch(PlivoExceptione){e.printStackTrace();}}System.out.println(response.toXML());resp.addHeader("Content-Type","text/xml");resp.getWriter().print(response.toXML());}publicstaticvoidmain(String[]args)throwsException{Stringport=System.getenv("PORT");if(port==null)port="8000";Serverserver=newServer(Integer.valueOf(port));ServletContextHandlercontext=newServletContextHandler(ServletContextHandler.SESSIONS);context.setContextPath("/");server.setHandler(context);context.addServlet(newServletHolder(newphoneIvr()),"/response/ivr/");context.addServlet(newServletHolder(newivrTree()),"/response/tree/");server.start();server.join();}}// ivrTree.javapackageplivoexample;importjava.io.IOException;importjavax.servlet.ServletException;importjavax.servlet.http.HttpServlet;importjavax.servlet.http.HttpServletRequest;importjavax.servlet.http.HttpServletResponse;importcom.plivo.helper.exception.PlivoException;importcom.plivo.helper.xml.elements.PlivoResponse;importcom.plivo.helper.xml.elements.Speak;publicclassivrTreeextendsHttpServlet{privatestaticfinallongserialVersionUID=1L;// This is the message that Plivo reads when the caller inputs a wrong number.StringWRONG_INPUT_MESSAGE="Sorry, it's wrong input.";@OverrideprotectedvoiddoPost(HttpServletRequestreq,HttpServletResponseresp)throwsServletException,IOException{Stringdigit=req.getParameter("Digits");PlivoResponseresponse=newPlivoResponse();if(digit.equals("1")){// Read out text in EnglishSpeakspeak=newSpeak("This message is being read out in English");speak.setLanguage("en-GB");try{response.append(speak);}catch(PlivoExceptione){e.printStackTrace();}}elseif(digit.equals("2")){// Read out text in FrenchSpeakspeak=newSpeak("Ce message est lu en français");speak.setLanguage("fr-FR");try{response.append(speak);}catch(PlivoExceptione){e.printStackTrace();}}elseif(digit.equals("3")){// Read out text in RussianSpeakspeak=newSpeak("Это сообщение было прочитано в России");speak.setLanguage("ru-RU");try{response.append(speak);}catch(PlivoExceptione){e.printStackTrace();}}else{// Wrong inputSpeakspeak=newSpeak(WRONG_INPUT_MESSAGE);try{response.append(speak);}catch(PlivoExceptione){e.printStackTrace();}}System.out.println(response.toXML());resp.addHeader("Content-Type","text/xml");resp.getWriter().print(response.toXML());}}

usingSystem;usingSystem.Collections.Generic;usingSystem.Diagnostics;usingRestSharp;usingPlivo.XML;usingNancy;namespacephone_ivr{publicclassProgram:NancyModule{publicProgram(){// This file will be played when a caller presses 2.StringPLIVO_SONG="https://s3.amazonaws.com/plivocloud/music.mp3";// This is the message that Plivo reads when the caller dials inStringIVR_MESSAGE1="Welcome to the Plivo IVR Demo App. Press 1 to listen to a pre recorded text in different languages. Press 2 to listen to a song.";StringIVR_MESSAGE2="Press 1 for English. Press 2 for French. Press 3 for Russian";// This is the message that Plivo reads when the caller does nothing at allStringNO_INPUT_MESSAGE="Sorry, I didn't catch that. Please hangup and try again later.";// This is the message that Plivo reads when the caller inputs a wrong number.StringWRONG_INPUT_MESSAGE="Sorry, it's a wrong input.";Get["/response/ivr/"]=x=>{Plivo.XML.Responseresp=newPlivo.XML.Response();Stringgetdigits_action_url="http://example.com/response/ivr/";// Add GetDigits XML TagGetDigitsgd=newGetDigits("",newDictionary&lt;string,string&gt;(){{"action",getdigits_action_url},{"method","POST"},{"timeout","7"},{"numDigits","1"},{"retries","1"}});// Add Speak XML Taggd.AddSpeak(IVR_MESSAGE1,newDictionary&lt;string,string&gt;(){});resp.Add(gd);// Add Speak XML Tagresp.AddSpeak(NO_INPUT_MESSAGE,newDictionary&lt;string,string&gt;(){});Debug.WriteLine(resp.ToString());varoutput=resp.ToString();varres=(Nancy.Response)output;res.ContentType="text/xml";returnres;};Post["/response/ivr/"]=x=>{Stringdigit=Request.Form["Digits"];Debug.WriteLine("Digit pressed : {0}",digit);Plivo.XML.Responseresp=newPlivo.XML.Response();if(digit=="1"){Stringgetdigits_action_url="http://example.com/response/tree/";// Add GetDigits XML TagGetDigitsgd=newGetDigits("",newDictionary&lt;string,string&gt;(){{"action",getdigits_action_url},// The URL to which the digits are sent.{"method","GET"},// Submit to action URL using GET or POST.{"timeout","7"},// Time in seconds to wait to receive the first digit.{"numDigits","1"},// Maximum number of digits to be processed in the current operation.{"retries","1"}// Indicates the number of retries the user is allowed to input the digits});// Add Speak XML Taggd.AddSpeak(IVR_MESSAGE2,newDictionary&lt;string,string&gt;(){});resp.Add(gd);// Add Speak XML Tagresp.AddSpeak(NO_INPUT_MESSAGE,newDictionary&lt;string,string&gt;(){});}elseif(digit=="2"){// Add Play XML Tagresp.AddPlay(PLIVO_SONG,newDictionary&lt;string,string&gt;(){});}else{// Add Speak XML Tagresp.AddSpeak(WRONG_INPUT_MESSAGE,newDictionary&lt;string,string&gt;(){});}Debug.WriteLine(resp.ToString());varoutput=resp.ToString();varres=(Nancy.Response)output;res.ContentType="text/xml";returnres;};Get["/response/tree/"]=x=>{Plivo.XML.Responseresp=newPlivo.XML.Response();Stringdigit=Request.Query["Digits"];// Add Speak XMLTagif(digit=="1"){resp.AddSpeak("This message is being read out in English",newDictionary&lt;string,string&gt;(){{"language","en-GB"}});}elseif(digit=="2"){resp.AddSpeak("Ce message est lu en français",newDictionary&lt;string,string&gt;(){{"language","fr-FR"}});}elseif(digit=="3"){resp.AddSpeak("Это сообщение было прочитано в России",newDictionary&lt;string,string&gt;(){{"language","ru-RU"}});}else{resp.AddSpeak(WRONG_INPUT_MESSAGE,newDictionary&lt;string,string&gt;(){});}Debug.WriteLine(resp.ToString());varoutput=resp.ToString();varres=(Nancy.Response)output;res.ContentType="text/xml";returnres;};}}}

Create an Application

Give your application a name. Lets call it Phone IVR. Enter your server URL (e.g., http://www.example.com/response/ivr) in the Answer URL field and set the method as GET. See our Application API docs to learn how to modify your application through our APIs.

Click on Create to save your application.

Assign a Plivo number to your app

Navigate to the Numbers page and select the phone number you want to use for this app.

Select Phone IVR (name of the app) from the Plivo App dropdown list.

Click on ‘Update’ to save.

If you don’t have a number, go to the Buy Number page to purchase a Plivo phone number.

Test it out

When you make a call to your Plivo number, the call will be answered by Plivo and Phone menu will be played.

Sample Output

<Response><GetDigitsaction="http://dotnettest.apphb.com/response/ivr"method="POST"timeout="7"numDigits="1"retries="1"><Speak>
Welcome to the Plivo IVR Demo App. Press 1 to listen to a pre recorded text in different languages. Press 2 to listen to a song.
</Speak></GetDigits><Speak>
Sorry, I didn't catch that. Please hangup and try again later.
</Speak></Response>

If 1 is pressed, another menu is read out. Following is the generated Speak XML.