Archive for the ‘Voxeo’ Category

Never forget to make a call with scheduled conferencing

Thursday, July 10th, 2008

We all forget to make important calls from time-to-time. With this tutorial, you will be able to schedule a call ahead of time, so that Voxeo’s IVR system calls you at that time in the future, and then links you with the party you intended to call.

While you’re utilizing your free Voxeo developer account, you might as well keep the whole shabang free, right? Head on over to x10hosting.com or forwardhosting.com, and register for an account. These are two of the very few hosting companies that will allow you to run cron jobs for free. Now that you are all setup, let’s get into the design aspect, cron job first.

While cron web interfaces will certainly be different, the underlying principal is the same: cron will wait until the system time matches your job time, and then will execute an action. Most web portals to cron jobs will allow you specify minute, hour, day, month, and weekday.

Let’s assume you have to call your wife every Friday night at 5 pm to let her know that you’re coming straight home from work. We’ll set minute to “00″, the hour to “17″, the weekday to “4″, and the rest to “*”. This will make the cron job execute on Fridays at 1700. You may need to adjust the time on your cron job to account for differences between system time and your time. For example, the x10hosting box on which my cron job runs is set to US central time. For the cron job command, use the Unix command “curl” like so:

curl http://api.voxeo.net/SessionControl/CCXML10.start?tokenid=dd5a1d7f44e97f49856eb6e894c9c669d152e89a571f6201eb3b265045b7a1d2bb52ff8d9856fbbbbbbbbbba\&numdial=5551231234

This command sends an http request to api.voxeo.net for our CCXML 1.0 token. The request also contains the variable “numdial.”

( Please note that the backslash is used in cron to escape the ampersand. This request will not work properly from a browser window )

Cron job interface

Now for the XML part:

<?xml version="1.0" encoding="UTF-8"?>
<ccxml version="1.0" xmlns:voxeo="http://community.voxeo.com/xmlns/ccxml">

<var name="state0" expr="'init'"/>
<var name="callid_out1"/>
<var name="callid_out2"/>
<var name="pin"/>
<var name="holdMusicDlg"/>

<eventprocessor statevariable="state0">

  <transition state="init" event="ccxml.loaded">
    <createcall dest="'tel:+15555555555'" connectionid="callid_out1" callerid="'1112223333'" timeout="'30s'"/>
  </transition>

  <transition state="init" event="connection.connected">
    <assign name="callid_out1" expr="event$.connectionid"/>
    <assign name="state0" expr="'enterpin'"/>
    <dialogstart src="'null://?termdigits=#&text=Press 1 and then pound if you want to dial' + session.values.numdial"&
    type="'application/x-fetchdigits'"/>
  </transition>

  <transition state="enterpin" event="dialog.exit">
    <log expr="'PIN = [' + event$.values.digits + ']‘”/>
    <if cond=”‘1′ != event$.values.digits”>
      <exit/>
    <else/>
      <assign name=”pin” expr=”event$.values.digits”/>
    </if>

    <assign name=”state0″ expr=”‘calling’”/>
    <dialogstart src=”‘holdingPattern.vxml’” type=”‘application/xml+vxml’” namelist=”pin” dialogid=”holdMusicDlg”/>
    <createcall dest=”‘tel:+1′ + session.values.numdial” connectionid=”callid_out2″ callerid=”‘5555555555′”/>

  </transition>

  <transition state=”calling” event=”connection.failed”>
    <assign name=”state0″ expr=”‘callfailed’”/>
    <dialogterminate dialogid=”holdMusicDlg”/>
  </transition>

  <transition state=”callfailed” event=”dialog.exit”>
    <assign name=”state0″ expr=”‘playingCallFailed’”/>
    <dialogstart src=”‘callFailure.vxml’” type=”‘application/xml+vxml’” connectionid=”callid_out1″/>
  </transition>

  <transition state=”playingCallFailed” event=”dialog.exit”>
    <disconnect/>
  </transition>

  <transition state=”calling” event=”connection.connected”>
    <if cond=”event$.connectionid == callid_out1″>
      <exit/>
    <else/>
      <assign name=”state0″ expr=”‘beforeBridging’”/>
      <dialogterminate dialogid=”holdMusicDlg”/>
    </if>
  </transition>

  <transition state=”beforeBridging” event=”dialog.exit”>
    <send name=”‘pause’” target=”session.id” delay=”‘200ms’”/>
  </transition>

  <transition state=”beforeBridging” event=”pause”>
    <assign name=”state0″ expr=”‘bridged’”/>
    <join id1=”callid_out1″ id2=”callid_out2″/>
  </transition>

  <transition event=”error.conference.join”>
    <log expr=”‘*** ERROR DURING JOIN ***’”/>
    <exit/>
  </transition>

  <transition event=”error.*”>
    <log expr=”‘an error has occured (’ + event$.reason + ‘)’”/>

    <voxeo:sendemail to=”‘yourEmail@there.com’”
      from=”‘myApp@here.com’”
      type=”‘debug’”
      body=” ‘generic error detected ! ‘ “/>
    <exit/>
  </transition>
</eventprocessor>
</ccxml>

This application has a fairly simple flow. It calls 1-555-555-5555, and then asks the callee to press 1 and then # to connect to whatever number was passed in via the http request (in this case numdial=5551231234).

That’s it. To make this work for you, you need to change four values:

1. token ID in http request
2. numdial variable in http request
3. “5555555555″ is found twice in the CCXML file - both instances should be changed to your number
4. sendemail “to” and “from” in CCXML file

Good luck with your development - mix in a little MySQL and PHP action to make adding more cron jobs easier.

Till next time,

Jeremy McCall
Voxeo Network Operations

LogSearch - Categories, Filtering and Themes

Tuesday, June 24th, 2008

Last week we announced LogSearch Beta for our Evolution developer portal. As part of the beta process we will be improving it with a number of new features based on feedback from our customers. 

The first round of changes adds several new features including: message categories, filtering, easy reversing and a new black color theme.

The first thing you will now notice is that when you login you will see a tool bar at the top with a bunch of checkboxes in it:

These boxes don’t do much until you run a search but once you search for something you will start to see some of the power of what it can provide. 

To start with lets run a search for a session and see what we get:

As you can see you get the full set of log messages here. Whats is new here is that you now can see that we have colorizing of the log messages making it easer to pick out the important messages in the log stream. 

The first thing you might want to try doing is clicking on one of the filters and see what happens. For example if you click “Playback” you will filter out everything but the browser playback messages:

The next thing you might want to try is clicking on the “User Filter” button to filter stuff down to only being user facing log messages:

Another new feature is the new button to easily reverse the results to be in chronological order instead of most recent first. This can make it a lot easer to read things like session logs where you are trying to understand the flow of what happened. Do be aware however that if your search spans a large amount of time it may take longer to display the initial search results in this mode since we need to search over the entire time block and gather all the results before we display them in the UI:

Lastly one other thing you may like to try is switching to the “black” theme we now include. To enable this open your preferences dialog and select VoxeoBlack on the theme menu on the General tab:

You will then get your UI rendered in proper old school programer colors:

 Hopefully these improvements will help make the tool more useful.  As always we are looking for feedback on ways we can improve our offerings so please leave us feedback either in the comments below or in our LogSearch feedback forum on the Evolution developer site

New Prophecy version (8.0.198.0) now available for download…

Wednesday, June 11th, 2008

FYI, a new version of Prophecy was released last Thursday. Version 8.0.198.0 is now available for download. The very detailed release notes go into all the many changes and fixes. Enjoy…

Technorati Tags:
, , ,

Voice Mashups with Twitter, part 2: Sending telephony presence to Twitter

Monday, April 21st, 2008

What if you wanted to share your telephony “presence” information with another application? i.e. you wanted to let the application know whether or not you were on the phone? For instance, when someone called you a message that you were “on the phone” could then be displayed in the other application…. perhaps a web page with a directory of staff - showing who’s on the phone… perhaps an instant messaging client…

twitter.pngWell, out at eComm 2008 in March, our CTO, RJ Auburn, demonstrated exactly that kind of integration using just CCXML and web services. In his talk he showed a quick application in CCXML that would send out your presence information on the current web 2.0 darling Twitter. Essentially, what happens is this:

  • Someone calls a phone number (presumably because you gave it to them)

  • Call is connected to your actual phone
  • Call presence information is sent out in your Twitter stream.

For instance, if you call one of these numbers (please do so only if you actually want to talk to me, and please only from 9am-5pm Eastern US time- thanks!):

You’ll reach me (or my voicemail) and the corresponding status updates will appear in my Twitter stream (shown in reverse chronological order):
twitterphonepresence.jpg

Now I don’t know that I would really personally want to send out this information in my twitter stream every time someone called me (although in all honesty I don’t talk on the phone as much as I used to), but you get the idea. Your “telephony presence” can be sent out to another application. It’s to me a very cool example of how you can easily mashup voice with web services. While Twitter is used here for this example, the code could basically be used to send this presence information to any type of service that lets you communicate using simple web services. Let’s dive in a bit further…

The eComm Slides

First, though, I should mention that this example was part of RJ’s talk at eComm 2008 and you can see it in his slide deck starting at slide 27:

As soon as audio is available for the presentation, we’ll provide a link here to actually listen to the presentation.

The Web Service

Now to jump into the actual code, RJ was able to do this so easily largely because Twitter’s API is so incredibly simple to use, as I discussed in a previous post about Twitter. The full CCXML code is below, but here’s the key part where RJ defined the URL to use to update Twitter:

  <var name="tURL"
       expr="'http://zscgeek:password@twitter.com/statuses/

That’s it. (Note that while RJ is on Twitter as zscgeek, you can rest assured that his real password is NOT “password”!)

After creating this variable “tURL” (as in “target URL”), RJ proceeds to simply assign some text to a variable “status” and then call the target URL with that “status” variable as an argument. For example:

      <var name="status" expr="'RJ is on the phone'"/>
      <send targettype="'basichttp'" name="'update'"
            target="tURL" namelist="status"/>

Here “RJ is on the phone” is assigned to “status” and then the Twitter API is called. As shown in the code below, this same block of code is re-used with each different telephony state (and obviously with a different status message).

The Code

So here’s the code… nice and short and sweet… just enough to fit on a Keynote slide without straining eyesight (yes, it would probably fit on a PowerPoint slide, too, but remember that we’re Mac fans here). I’m not going to walk through each step of the code, but if you scan down you can see that basically the code is:

  • Upon connection of the call:
    1. connecting the call to RJ’s cell phone (not his real number)
    2. sending the “RJ is on the phone” status update to Twitter
  • Upon entering one of the other states (no answer, call disconnected), sending the appropriate Twitter status update.

Now if you aren’t familiar with the power of CCXML, you might want to look at our documentation and tutorial on CCXML or view one of the video tutorials on CCXML that we recently posted.

With that, here’s the code:


<?xml version="1.0" encoding="UTF-8"?>
<ccxml xmlns="http://www.w3.org/2002/09/ccxml" version="1.0">
  <var name="state" expr="'init'"/>
  <var name="incomingcall"/>
  <var name="tURL"
       expr="'http://zscgeek:password@twitter.com/statuses/update.xml'"/>
  <eventprocessor statevariable="state">
    <transition event="connection.alerting" state="init">
      <accept/>
    </transition>
    <transition event="connection.connected" state="init">
      <assign name="state" expr="'calling'"/>
      <assign name="incomingcall" expr="event$.connectionid"/>
      <createcall dest="'tel:+18315551111'"/>
    </transition>
    <transition event="connection.connected" state="calling">
      <assign name="state" expr="'connected'"/>
      <join id1="event$.connectionid" id2="incomingcall"/>
      <var name="status" expr="'RJ is on the phone'"/>
      <send targettype="'basichttp'" name="'update'"
            target="tURL" namelist="status"/>
    </transition>
    <transition event="connection.failed" state="calling">
      <assign name="state" expr="'done'"/>
      <var name="status" expr="'RJ is not answering his phone'"/>
      <send targettype="'basichttp'" name="'update'"
            target="tURL" namelist="status"/>
    </transition>
    <transition event="connection.disconnected" state="connected">
      <assign name="state" expr="'done'"/>
      <var name="status" expr="'RJ is off the phone'"/>
      <send targettype="'basichttp'" name="'update'"
            target="tURL" namelist="status"/>
    </transition>
    <transition event="send.successful" state="done">
      <exit/>
    </transition>
  </eventprocessor>
</ccxml>

Feel free to use it, modify it, etc., etc. (And if you do something cool with it, please do let us know, either as a reply to this post or via email.) While this is with Twitter, we’d love to hear where else you can think of sending telephony presence info…

P.S. If you’d like to experiment with this but are not sure of how to get started, head on over to www.voxeo.com/free and either sign up for a free developer account on our Evolution portal or download our free Prophecy software to run it on your own server.

Technorati Tags:
, , , , , , , , , ,

Creating dynamic voice apps that use Google’s App Engine, part 2

Friday, April 18th, 2008

googleappengine.jpgJust a brief update on my piece about how to use voice with Google’s App Engine… I now have been invited into the preview of Google’s App Engine, so I’ve created a second application on our Evolution platform with this one pointing to my shiny new GAE app at:

http://voicexmltest2.appspot.com/

For now, it’s the same (lame) python code, but the app does have it’s own phone numbers:

Direct Local # (857) 362-8430
PIN Access (800) 289-5570 then PIN: 9996075378
PIN Access (407) 386-2174 then PIN: 9996075378
Skype VoIP +99000936 9996075378
FWD VoIP **86919996075378
SIP VoIP sip:9996075378@sip.voxeo.net

Why didn’t I simply modify the original Evolution application? Well, I could have, but I figured this way I can also still experiment with the AppDrop.com application as well.

The nice thing with a true Google App Engine account is that I can use “appcfg.py” to automagically update the files up on the App Engine site, which is very slick. (Thanks, Google, for the invite!) Next week, my intent is to work with the python code to get it actually manipulating the XML… stay tuned… (and check my original article if you would like to experiment with voice and Google App Engine, too).

Technorati Tags:
, , , , , , , , , , , ,

Certified Tech Tip: Multi-slot SISR subgrammars with Prophecy 8

Monday, February 11th, 2008

voicexmlcertifieddeveloper.gif

For our last certified tech-tip, we explored the older SISR-formatted returns that one can use when designing a recognition grammar for a VoiceXML application. For this week, we will tackle two different things related to SISR grammars when using the Prophecy 8 software:1 - How to use the newer SISR “.out” grammar return syntax2 - How we can craft a subgrammar returning multiple slot valuesIt would seem as if the second item is pretty elementary, but it does bear a little bit of illustration, especially in terms of how the values in the sub-rules will bubble up to the top-level return. For the sake of simplicity, we will do a much-simplified month/day grammar that contains a single entry. One you grasp the syntax, you can easily flesh this out more fully to include all possible months & days, or even overhaul it into a first-name & last-name grammar.Let’s take a peek at the grammar file itself, and then look at the relevant working parts:

<?xml version= “1.0″?>

<!DOCTYPE grammar PUBLIC “-//W3C//DTD GRAMMAR 1.0//EN” “http://www.w3.org/TR/speech-grammar/grammar.dtd”>

<grammar mode=”voice” xmlns=”http://www.w3.org/2001/06/grammar” xml:lang=”en-US” version=”1.0″ root=”TOPLEVEL” tag-format=”semantics/1.0″>

 <rule id=”TOPLEVEL”>

  <one-of>

   <item>

   <item>

    <ruleref uri=”#MONTH”/> <tag>out.monthslot=rules.MONTH.monthsubslot;</tag>

   </item>

   <item>

    <ruleref uri=”#DAY”/> <tag>out.dayslot=rules.DAY.daysubslot;</tag>

   </item>

    <tag>out.yearslot=”2008″;</tag>

   </item>

  </one-of>

 </rule>

 <rule id=”MONTH”>

  <one-of>

   <item> january <tag> out.monthsubslot=”January “;</tag> </item>

  </one-of>

 </rule>

 <rule id=”DAY”>

  <one-of>

   <item> first <tag> out.daysubslot=”first”;</tag> </item>

  </one-of>

 </rule>

</grammar>

The grammar above consists of two sub-rules titled “MONTH” and “DATE”, and we have a single top-level rule titled “TOPLEVEL”. The sub-rules each specify a month and day slot respectively, and these slots will bubble up to the to-level when we invoke the syntax that we have below:

<ruleref uri=”#SUBRULE”> <tag>out.slotname.SUBRULENAME.subslot;</tag>

And we then reference these various slots within the VoiceXML as follows:

<log expr=”‘*** SLOT RESULT = ‘ + lastresult$.interpretation.slotname”/>

We also threw in a quick example of using the “out” syntax in a more generic manner for our “yearslot” value. In this case, it simply allows us to return a year value back to the VoiceXML from the top-level rule as opposed to having to reference the sub-rule values.This is added in to show how a “flat-file” non subgrammar can return a slot value using the newer SISR syntax that follows this format:

<tag>out.slotname;</tag>

So when using our month/day grammar above, one might still be unclear on how we get at all these slot values within the VoiceXML dialog. Once recognition has occurred, we would specify something like this:

<log expr=”‘*** YEAR RESULT = ‘ + lastresult$.interpretation.yearslot”/>

<log expr=”‘*** MONTH RESULT = ‘ + lastresult$.interpretation.monthslot”/>

<log expr=”‘*** DAY RESULT = ‘ + lastresult$.interpretation.dayslot”/>

Eventually, we will get around to creating some fully fleshed-out additions to our VoiceXML documentation on the subject of SISR grammars, but until then, we will post any cool tricks and tips here for the edification of our developers. As always, if heres anyone who’d like to see a posting, or techtip on a particular subject, just drop us a line, and we would be happy to accommodate.Next TechTip: Using SSML markup within a CallXML 3.0 application. Stay tuned to the blog; this next one is really cool.

~Matthew Henry