SlideShare a Scribd company logo
1 of 143
Download to read offline
Taking a SIP of Java



RJ Auburn
Voxeo Corporation
Chief Technology Officer
Telephony
            2
Sucks
        3
Expensive
            4
Complex
          5
Proprietary
              6
This is not how it should be...



                                  7
Simple
         8
Ubiquitous
             9
Open
       10
So what are the layers?



                          11
Application



API      XML        Tools



       Platform



                            12
Application
      Application



API      XML        Tools



       Platform



                            13
Application



API     XML         Tools



       Platform



                            14
Application



API     XML         Tools



       Platform



                            15
Application



API     XML         Tools



       Platform



                            16
Some Basics:
Signaling vs Media



                     17
Call Control vs Media

>   Phone systems often are split into two
    components: Signaling and Media
>   Signaling handles the setup and tear-down of
    sessions and phone calls.
>   Media is responsible for the transport voice path




                                                        18
Media vs Call Control in the PSTN - SIP

                    Proxy         Proxy
                            SIP
                      A             B




                                          SIP
              SIP




      Alice                 RTP                 Bob




                                                      19
Media vs Call Control in the PSTN - SS7

                    SCP                    SCP
                                 SS7
                     A                      B




                                                 SS7
                7
              SS




      Alice               Switched TDM Media           Bob




                                                             20
Media vs Call Control in the PSTN - ISDN


                   D Channel (q.931)
                       Signaling


     Dev                               Dev
      A                                 B

                     B Channels (23)
                         Media




                                             21
All this means is the APIʼs
and standards for media vs
   call control tend to be
           different.


                               22
So now for
a bit about SIP
 (Call Control)


                  23
SIP

>   Session Initiation Protocol (SIP)
    defines how to establish a
    communication session between
    two endpoints
>   Primarily used for voice, but can for IM or virtually
    any other protocol
>   Almost always used in client/server configuration
    with quot;SIP proxiesquot; in control of quot;SIP endpointsquot;
    • Work going on in P2PSIP - see www.p2psip.org
>   Text-based protocol, originally modeled on HTTP
                                                            24
SIP Communication
                    INVITE
     Alice          180 RINGING   Bob
                    200 OK
                    ACK




                    RTP (voice)



                    BYE
                    200 OK




                                        25
Major SIP Methods

>   INVITE
>   BYE
>   REFER
>   REGISTER
>   SUBSCRIBE
>   NOTIFY
    oh ya...

>   INFO (wait, we are not supposed to talk about this one)

                                                              26
Response Codes

>   1xx - Provisional
>   2xx - All is good. Final
>   3xx - Redirects
>   4/5/6xx - Errors




                               27
SIP Resources

>   Internet Engineering Task Force (IETF)
    • RFC 3261
    • Hitchhikerʼs Guide to SIP
>   Open Source Info
    • VoIP Info Wiki: www.voip-info.org
>   Industry Sites
    • SIP Forum: www.sipforum.org
    • SIP Foundry: www.sipfoundry.org
                                             28
So lets talk about...



                        29
Religion
           30
Religion
           31
XML
      32
VoiceXML and CCXML
                     33
VoiceXML

>   Language created by the W3C to
    model computer human dialogs.
>   Supports speech and touchtone.
>   Built around a form filling model called the FIA.
>   Voice equivalent to HTML.
>   Focused on dialogs. Very limited call control.

>   http://www.w3.org/TR/voicexml/

                                                       34
CCXML

>   Call Control XML (CCXML) is the
    W3C standard for call control
    using XML
>   Sister standard to VoiceXML
>   Integrates with VoiceXML for dialog control
>   Provides a framework for issuing call control
    commands and handling call control events

>   http://www.w3.org/TR/ccxml/
                                                    35
VoiceXML and CCXML Architecture




                                                   ASR


   Phone         CCXML           VoiceXML   mrcp
           sip             sip
                                                   TTS



                     rtp




                                                         36
Like Tribbles...
                   37
It has taken over the Enterprise...
                                      38
How about some code?



                       39
Sample CCXML/VoiceXML application.

>   Caller dials in to the application
>   Caller is bridged to the subscriber
>   Results of the call attempt are posted to Twitter via
    their REST API




                             40
start



                  isRJ()
      yes                           no

prompt for dest            play twitter status


   call dest                  call rj’s cell



                  end
Call router + Twitter
<?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?>
<ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;>
  <var name=quot;statequot; expr=quot;'init'quot;/>
  <var name=quot;incomingcallquot;/>
  <eventprocessor statevariable=quot;statequot;>
    <transition event=quot;connection.alertingquot; state=quot;initquot;>
      <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/>
      <accept/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;
         cond=quot;event$.connection.remote=='tel:+18315551234'quot;>
      <assign name=quot;statequot; expr=quot;'rjconnected'quot;/>
      <dialogstart src=quot;'rj.vxml'quot;
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;>
      <assign name=quot;statequot; expr=quot;'callconnected'quot;/>
      <dialogstart src=quot;'caller.vxml'quot;
    </transition>
    <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
      <createcall dest=quot;'tel:+18315551234'quot;/>
    </transition>
    <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
      <createcall dest=quot;event$.values.destquot;/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;callingquot;>
      <assign name=quot;statequot; expr=quot;'connected'quot;/>
      <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/>
    </transition>
    <transition event=quot;connection.failedquot; state=quot;callingquot;>
         <exit/>
    </transition>
    <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;>
         <exit/>
    </transition>
  </eventprocessor>
</ccxml>




                                                                     42
Call router + Twitter
<?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?>
<ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;>
  <var name=quot;statequot; expr=quot;'init'quot;/>
  <var name=quot;incomingcallquot;/>
  <eventprocessor statevariable=quot;statequot;>
    <transition event=quot;connection.alertingquot; state=quot;initquot;>
      <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/>
      <accept/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;
         cond=quot;event$.connection.remote=='tel:+18315551234'quot;>
      <assign name=quot;statequot; expr=quot;'rjconnected'quot;/>
      <dialogstart src=quot;'rj.vxml'quot;
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;>
      <assign name=quot;statequot; expr=quot;'callconnected'quot;/>
      <dialogstart src=quot;'caller.vxml'quot;
    </transition>
    <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
      <createcall dest=quot;'tel:+18315551234'quot;/>
    </transition>
    <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
      <createcall dest=quot;event$.values.destquot;/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;callingquot;>
      <assign name=quot;statequot; expr=quot;'connected'quot;/>
      <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/>
    </transition>
    <transition event=quot;connection.failedquot; state=quot;callingquot;>
         <exit/>
    </transition>
    <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;>
         <exit/>
    </transition>
  </eventprocessor>
</ccxml>




                                                                     43
Call router + Twitter
<?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?>
<ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;>
  <var name=quot;statequot; expr=quot;'init'quot;/>
  <var name=quot;incomingcallquot;/>
  <eventprocessor statevariable=quot;statequot;>
    <transition event=quot;connection.alertingquot; state=quot;initquot;>
      <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/>
      <accept/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;
         cond=quot;event$.connection.remote=='tel:+18315551234'quot;>
      <assign name=quot;statequot; expr=quot;'rjconnected'quot;/>
      <dialogstart src=quot;'rj.vxml'quot;
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;>
    <?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?>
      <assign name=quot;statequot; expr=quot;'callconnected'quot;/>
      <dialogstart src=quot;'caller.vxml'quot;
    <ccxml version=quot;1.0quot;
    </transition>
    <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;>
      <assign xmlns=quot;http://www.w3.org/2002/09/ccxmlquot;>
               name=quot;statequot; expr=quot;'calling'quot;/>
      <createcall dest=quot;'tel:+18315551234'quot;/>
    </ccxml>
    </transition>
    <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
      <createcall dest=quot;event$.values.destquot;/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;callingquot;>
      <assign name=quot;statequot; expr=quot;'connected'quot;/>
      <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/>
    </transition>
    <transition event=quot;connection.failedquot; state=quot;callingquot;>
         <exit/>
    </transition>
    <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;>
         <exit/>
    </transition>
  </eventprocessor>
</ccxml>




                                                                     44
Call router + Twitter
<?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?>
<ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;>
  <var name=quot;statequot; expr=quot;'init'quot;/>
  <var name=quot;incomingcallquot;/>
  <eventprocessor statevariable=quot;statequot;>
    <transition event=quot;connection.alertingquot; state=quot;initquot;>
      <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/>
      <accept/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;
         cond=quot;event$.connection.remote=='tel:+18315551234'quot;>
      <assign name=quot;statequot; expr=quot;'rjconnected'quot;/>
      <dialogstart src=quot;'rj.vxml'quot;
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;>
      <assign name=quot;statequot; expr=quot;'callconnected'quot;/>
      <dialogstart src=quot;'caller.vxml'quot;
    </transition>
    <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
      <createcall dest=quot;'tel:+18315551234'quot;/>
    </transition>
    <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
      <createcall dest=quot;event$.values.destquot;/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;callingquot;>
      <assign name=quot;statequot; expr=quot;'connected'quot;/>
      <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/>
    </transition>
    <transition event=quot;connection.failedquot; state=quot;callingquot;>
         <exit/>
    </transition>
    <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;>
         <exit/>
    </transition>
  </eventprocessor>
</ccxml>




                                                                     45
Call router + Twitter
<?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?>
<ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;>
  <var name=quot;statequot; expr=quot;'init'quot;/>
  <var name=quot;incomingcallquot;/>
  <eventprocessor statevariable=quot;statequot;>
    <transition event=quot;connection.alertingquot; state=quot;initquot;>
      <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/>
      <accept/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;
         cond=quot;event$.connection.remote=='tel:+18315551234'quot;>
      <assign name=quot;statequot; expr=quot;'rjconnected'quot;/>
      <dialogstart src=quot;'rj.vxml'quot;
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;>
      <assign name=quot;statequot; expr=quot;'callconnected'quot;/>
      <dialogstart src=quot;'caller.vxml'quot; expr=quot;'init'quot;/>
                <var name=quot;statequot;
    </transition>
    <transition<var name=quot;incomingcallquot;/>
                 event=quot;dialog.exitquot; state=quot;callconnectedquot;>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
                <eventprocessor statevariable=quot;statequot;>
      <createcall dest=quot;'tel:+18315551234'quot;/>
    </transition>
    <transition</eventprocessor>
                 event=quot;dialog.exitquot; state=quot;rjconnectedquot;>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
      <createcall dest=quot;event$.values.destquot;/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;callingquot;>
      <assign name=quot;statequot; expr=quot;'connected'quot;/>
      <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/>
    </transition>
    <transition event=quot;connection.failedquot; state=quot;callingquot;>
         <exit/>
    </transition>
    <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;>
         <exit/>
    </transition>
  </eventprocessor>
</ccxml>




                                                                     46
Call router + Twitter
<?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?>
<ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;>
  <var name=quot;statequot; expr=quot;'init'quot;/>
  <var name=quot;incomingcallquot;/>
  <eventprocessor statevariable=quot;statequot;>
    <transition event=quot;connection.alertingquot; state=quot;initquot;>
      <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/>
      <accept/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;
         cond=quot;event$.connection.remote=='tel:+18315551234'quot;>
      <assign name=quot;statequot; expr=quot;'rjconnected'quot;/>
      <dialogstart src=quot;'rj.vxml'quot;
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;>
      <assign name=quot;statequot; expr=quot;'callconnected'quot;/>
      <dialogstart src=quot;'caller.vxml'quot;
    </transition>
    <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
      <createcall dest=quot;'tel:+18315551234'quot;/>
    </transition>
    <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
      <createcall dest=quot;event$.values.destquot;/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;callingquot;>
      <assign name=quot;statequot; expr=quot;'connected'quot;/>
      <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/>
    </transition>
    <transition event=quot;connection.failedquot; state=quot;callingquot;>
         <exit/>
    </transition>
    <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;>
         <exit/>
    </transition>
  </eventprocessor>
</ccxml>




                                                                     47
Call router + Twitter
<?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?>
<ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;>
  <var name=quot;statequot; expr=quot;'init'quot;/>
  <var name=quot;incomingcallquot;/>
  <eventprocessor statevariable=quot;statequot;>
    <transition event=quot;connection.alertingquot; state=quot;initquot;>
      <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/>
      <accept/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;
         cond=quot;event$.connection.remote=='tel:+18315551234'quot;>
      <assign name=quot;statequot; expr=quot;'rjconnected'quot;/>
      <dialogstart src=quot;'rj.vxml'quot;
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;>
      <assign name=quot;statequot; expr=quot;'callconnected'quot;/>
<transition event=quot;connection.alertingquot; state=quot;initquot;>
      <dialogstart src=quot;'caller.vxml'quot;
  <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/>
    </transition>
    <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;>
  <accept/> dest=quot;'tel:+18315551234'quot;/>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
      <createcall
</transition>
    </transition>
    <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
      <createcall dest=quot;event$.values.destquot;/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;callingquot;>
      <assign name=quot;statequot; expr=quot;'connected'quot;/>
      <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/>
    </transition>
    <transition event=quot;connection.failedquot; state=quot;callingquot;>
         <exit/>
    </transition>
    <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;>
         <exit/>
    </transition>
  </eventprocessor>
</ccxml>




                                                                     48
Call router + Twitter
<?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?>
<ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;>
  <var name=quot;statequot; expr=quot;'init'quot;/>
  <var name=quot;incomingcallquot;/>
  <eventprocessor statevariable=quot;statequot;>
    <transition event=quot;connection.alertingquot; state=quot;initquot;>
      <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/>
      <accept/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;
         cond=quot;event$.connection.remote=='tel:+18315551234'quot;>
      <assign name=quot;statequot; expr=quot;'rjconnected'quot;/>
      <dialogstart src=quot;'rj.vxml'quot;
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;>
      <assign name=quot;statequot; expr=quot;'callconnected'quot;/>
      <dialogstart src=quot;'caller.vxml'quot;
    </transition>
    <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
      <createcall dest=quot;'tel:+18315551234'quot;/>
    </transition>
    <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
      <createcall dest=quot;event$.values.destquot;/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;callingquot;>
      <assign name=quot;statequot; expr=quot;'connected'quot;/>
      <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/>
    </transition>
    <transition event=quot;connection.failedquot; state=quot;callingquot;>
         <exit/>
    </transition>
    <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;>
         <exit/>
    </transition>
  </eventprocessor>
</ccxml>




                                                                     49
Call router + Twitter
<?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?>
<ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;>
  <var name=quot;statequot; expr=quot;'init'quot;/>
  <var name=quot;incomingcallquot;/>
  <eventprocessor statevariable=quot;statequot;>
    <transition event=quot;connection.alertingquot; state=quot;initquot;>
      <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/>
      <accept/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;
         cond=quot;event$.connection.remote=='tel:+18315551234'quot;>
      <assign name=quot;statequot; expr=quot;'rjconnected'quot;/>
      <dialogstart src=quot;'rj.vxml'quot;
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;>
 <transition event=quot;connection.connectedquot; state=quot;initquot;
      <assign name=quot;statequot; expr=quot;'callconnected'quot;/>
      <dialogstart src=quot;'caller.vxml'quot;
       cond=quot;event$.connection.remote=='tel:+18315551234'quot;>
    </transition>
    <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;>
    <assign name=quot;statequot; expr=quot;'calling'quot;/>
      <assign name=quot;statequot; expr=quot;'rjconnected'quot;/>
      <createcall dest=quot;'tel:+18315551234'quot;/>
    <dialogstart src=quot;'rj.vxml'quot;
    </transition>
    <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;>
 </transition>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
      <createcall dest=quot;event$.values.destquot;/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;callingquot;>
      <assign name=quot;statequot; expr=quot;'connected'quot;/>
      <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/>
    </transition>
    <transition event=quot;connection.failedquot; state=quot;callingquot;>
         <exit/>
    </transition>
    <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;>
         <exit/>
    </transition>
  </eventprocessor>
</ccxml>




                                                                     50
Call router + Twitter
<?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?>
<ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;>
  <var name=quot;statequot; expr=quot;'init'quot;/>
  <var name=quot;incomingcallquot;/>
  <var name=quot;tURLquot;
       expr=quot;'http://zscgeek:password@twitter.com/statuses/update.xml'quot;/>
  <eventprocessor statevariable=quot;statequot;>
    <transition event=quot;connection.alertingquot; state=quot;initquot;>
      <accept/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;>
 <?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
      <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/>
 <vxml xmlns=quot;http://www.w3.org/2001/vxmlquot; version=quot;2.1quot;>
      <createcall dest=quot;'tel:+18312392883'quot;/>
    </transition>
      <form>
    <transition event=quot;connection.connectedquot; state=quot;callingquot;>
      <assign name=quot;statequot; expr=quot;'connected'quot;/>
      <field name=quot;destquot; type=quot;digits?length=10quot;>
      <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/>
      <var name=quot;statusquot; expr=quot;'RJ is on the phone'quot;/>
      <send <prompt>Welcome RJ. Please enter the phone
            targettype=quot;'basichttp'quot; name=quot;'update'quot;
            target=quot;tURLquot; namelist=quot;statusquot;/>
    </transition>      number you wish to reach.</prompt>
    <transition event=quot;connection.failedquot; state=quot;callingquot;>
      <filled>
      <assign name=quot;statequot; expr=quot;'done'quot;/>
      <var name=quot;statusquot; expr=quot;'RJ is not answering his phone'quot;/>
      <send <exit namelist=quot;destquot;/>
            targettype=quot;'basichttp'quot; name=quot;'update'quot;
            target=quot;tURLquot; namelist=quot;statusquot;/>
      </filled>
    </transition>
      </field>
    <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;>
      <assign name=quot;statequot; expr=quot;'done'quot;/>
      </form>
      <var name=quot;statusquot; expr=quot;'RJ is off the phone'quot;/>
      <send targettype=quot;'basichttp'quot; name=quot;'update'quot;
 </vxml> target=quot;tURLquot; namelist=quot;statusquot;/>
    </transition>
    <transition event=quot;send.successfulquot; state=quot;donequot;>
      <exit/>
    </transition>
  </eventprocessor>
</ccxml>




                                                                            51
Call router + Twitter
<?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?>
<ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;>
  <var name=quot;statequot; expr=quot;'init'quot;/>
  <var name=quot;incomingcallquot;/>
  <eventprocessor statevariable=quot;statequot;>
    <transition event=quot;connection.alertingquot; state=quot;initquot;>
      <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/>
      <accept/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;
         cond=quot;event$.connection.remote=='tel:+18315551234'quot;>
      <assign name=quot;statequot; expr=quot;'rjconnected'quot;/>
      <dialogstart src=quot;'rj.vxml'quot;
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;>
      <assign name=quot;statequot; expr=quot;'callconnected'quot;/>
      <dialogstart src=quot;'caller.vxml'quot;
    </transition>
    <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
      <createcall dest=quot;'tel:+18315551234'quot;/>
    </transition>
    <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
      <createcall dest=quot;event$.values.destquot;/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;callingquot;>
      <assign name=quot;statequot; expr=quot;'connected'quot;/>
      <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/>
    </transition>
    <transition event=quot;connection.failedquot; state=quot;callingquot;>
         <exit/>
    </transition>
    <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;>
         <exit/>
    </transition>
  </eventprocessor>
</ccxml>




                                                                     52
Call router + Twitter
<?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?>
<ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;>
  <var name=quot;statequot; expr=quot;'init'quot;/>
  <var name=quot;incomingcallquot;/>
  <eventprocessor statevariable=quot;statequot;>
    <transition event=quot;connection.alertingquot; state=quot;initquot;>
      <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/>
      <accept/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;
         cond=quot;event$.connection.remote=='tel:+18315551234'quot;>
      <assign name=quot;statequot; expr=quot;'rjconnected'quot;/>
      <dialogstart src=quot;'rj.vxml'quot;
 <transition event=quot;connection.connectedquot; state=quot;initquot;>
    </transition>
    <assign name=quot;statequot; expr=quot;'callconnected'quot;/>
    <transition name=quot;statequot; expr=quot;'callconnected'quot;/>
      <assign
                 event=quot;connection.connectedquot; state=quot;initquot;>

    <dialogstart src=quot;'caller.vxml'quot;
      <dialogstart src=quot;'caller.vxml'quot;
    </transition>
 </transition>
    <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
      <createcall dest=quot;'tel:+18315551234'quot;/>
    </transition>
    <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
      <createcall dest=quot;event$.values.destquot;/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;callingquot;>
      <assign name=quot;statequot; expr=quot;'connected'quot;/>
      <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/>
    </transition>
    <transition event=quot;connection.failedquot; state=quot;callingquot;>
         <exit/>
    </transition>
    <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;>
         <exit/>
    </transition>
  </eventprocessor>
</ccxml>




                                                                     53
Call router + Twitter
<?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?>
<ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;>
  <var name=quot;statequot; expr=quot;'init'quot;/>
  <var name=quot;incomingcallquot;/>
  <var name=quot;tURLquot;
       expr=quot;'http://zscgeek:password@twitter.com/statuses/update.xml'quot;/>
  <eventprocessor statevariable=quot;statequot;>
    <transition event=quot;connection.alertingquot; state=quot;initquot;>
 <?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?>
      <accept/>
    </transition>
 <vxml xmlns=quot;http://www.w3.org/2001/vxmlquot; version=quot;2.1quot;>
    <transition event=quot;connection.connectedquot; state=quot;initquot;>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
    <form> name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/>
      <assign
      <createcall dest=quot;'tel:+18312392883'quot;/>
       <block>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;callingquot;>
         <data src=quot;http://twitter.com/statuses/
      <assign name=quot;statequot; expr=quot;'connected'quot;/>
      <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/>
 user_timeline.xml?screen_name=zscgeekquot;
      <var name=quot;statusquot; expr=quot;'RJ is on the phone'quot;/>
      <send targettype=quot;'basichttp'quot; name=quot;'update'quot;
                          name=quot;twitterquot; ecmaxmltype=quot;e4xquot; />
            target=quot;tURLquot; namelist=quot;statusquot;/>
    </transition>
         <prompt>Thank you for calling RJ.
    <transition event=quot;connection.failedquot; state=quot;callingquot;>
      <assign We will connect you now.
              name=quot;statequot; expr=quot;'done'quot;/>
      <var name=quot;statusquot; expr=quot;'RJ is not answering his phone'quot;/>
              His twitter status is
      <send targettype=quot;'basichttp'quot; name=quot;'update'quot;
            target=quot;tURLquot; namelist=quot;statusquot;/>
              <value expr=quot;twitter.statuses.status[0].textquot;/>
    </transition>
    <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;>
         </prompt>
      <assign name=quot;statequot; expr=quot;'done'quot;/>
      <var name=quot;statusquot; expr=quot;'RJ is off the phone'quot;/>
       </block>
      <send targettype=quot;'basichttp'quot; name=quot;'update'quot;
            target=quot;tURLquot; namelist=quot;statusquot;/>
    </form> event=quot;send.successfulquot; state=quot;donequot;>
    </transition>
    <transition
 </vxml>
      <exit/>
    </transition>
  </eventprocessor>
</ccxml>




                                                                            54
Call router + Twitter
<?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?>
<ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;>
  <var name=quot;statequot; expr=quot;'init'quot;/>
  <var name=quot;incomingcallquot;/>
  <eventprocessor statevariable=quot;statequot;>
    <transition event=quot;connection.alertingquot; state=quot;initquot;>
      <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/>
      <accept/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;
         cond=quot;event$.connection.remote=='tel:+18315551234'quot;>
      <assign name=quot;statequot; expr=quot;'rjconnected'quot;/>
      <dialogstart src=quot;'rj.vxml'quot;
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;>
      <assign name=quot;statequot; expr=quot;'callconnected'quot;/>
      <dialogstart src=quot;'caller.vxml'quot;
    </transition>
    <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
      <createcall dest=quot;'tel:+18315551234'quot;/>
    </transition>
    <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
      <createcall dest=quot;event$.values.destquot;/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;callingquot;>
      <assign name=quot;statequot; expr=quot;'connected'quot;/>
      <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/>
    </transition>
    <transition event=quot;connection.failedquot; state=quot;callingquot;>
         <exit/>
    </transition>
    <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;>
         <exit/>
    </transition>
  </eventprocessor>
</ccxml>




                                                                     55
Call router + Twitter
<?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?>
<ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;>
  <var name=quot;statequot; expr=quot;'init'quot;/>
  <var name=quot;incomingcallquot;/>
  <eventprocessor statevariable=quot;statequot;>
    <transition event=quot;connection.alertingquot; state=quot;initquot;>
      <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/>
      <accept/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;
         cond=quot;event$.connection.remote=='tel:+18315551234'quot;>
      <assign name=quot;statequot; expr=quot;'rjconnected'quot;/>
      <dialogstart src=quot;'rj.vxml'quot;
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;>
      <assign name=quot;statequot; expr=quot;'callconnected'quot;/>
      <dialogstart src=quot;'caller.vxml'quot;
    </transition>
<transition event=quot;dialog.exitquot; state=quot;callconnectedquot;>
    <transition
                 event=quot;dialog.exitquot; state=quot;callconnectedquot;>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
      <createcall dest=quot;'tel:+18315551234'quot;/>
  <assign name=quot;statequot; expr=quot;'calling'quot;/>
    </transition>
    <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;>
  <createcall dest=quot;'tel:+18315551234'quot;/>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
</transition> dest=quot;event$.values.destquot;/>
      <createcall
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;callingquot;>
      <assign name=quot;statequot; expr=quot;'connected'quot;/>
      <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/>
    </transition>
    <transition event=quot;connection.failedquot; state=quot;callingquot;>
         <exit/>
    </transition>
    <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;>
         <exit/>
    </transition>
  </eventprocessor>
</ccxml>




                                                                     56
Call router + Twitter
<?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?>
<ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;>
  <var name=quot;statequot; expr=quot;'init'quot;/>
  <var name=quot;incomingcallquot;/>
  <eventprocessor statevariable=quot;statequot;>
    <transition event=quot;connection.alertingquot; state=quot;initquot;>
      <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/>
      <accept/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;
         cond=quot;event$.connection.remote=='tel:+18315551234'quot;>
      <assign name=quot;statequot; expr=quot;'rjconnected'quot;/>
      <dialogstart src=quot;'rj.vxml'quot;
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;>
      <assign name=quot;statequot; expr=quot;'callconnected'quot;/>
      <dialogstart src=quot;'caller.vxml'quot;
    </transition>
    <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
      <createcall dest=quot;'tel:+18315551234'quot;/>
    </transition>
    <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
      <createcall dest=quot;event$.values.destquot;/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;callingquot;>
      <assign name=quot;statequot; expr=quot;'connected'quot;/>
      <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/>
    </transition>
    <transition event=quot;connection.failedquot; state=quot;callingquot;>
         <exit/>
    </transition>
    <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;>
         <exit/>
    </transition>
  </eventprocessor>
</ccxml>




                                                                     57
Call router + Twitter
 <?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?>
 <ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;>
   <var name=quot;statequot; expr=quot;'init'quot;/>
   <var name=quot;incomingcallquot;/>
   <eventprocessor statevariable=quot;statequot;>
     <transition event=quot;connection.alertingquot; state=quot;initquot;>
       <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/>
       <accept/>
     </transition>
     <transition event=quot;connection.connectedquot; state=quot;initquot;
          cond=quot;event$.connection.remote=='tel:+18315551234'quot;>
       <assign name=quot;statequot; expr=quot;'rjconnected'quot;/>
       <dialogstart src=quot;'rj.vxml'quot;
     </transition>
     <transition event=quot;connection.connectedquot; state=quot;initquot;>
       <assign name=quot;statequot; expr=quot;'callconnected'quot;/>
       <dialogstart src=quot;'caller.vxml'quot;
     </transition>
     <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;>
<transition name=quot;statequot; expr=quot;'calling'quot;/>
       <assign event=quot;dialog.exitquot; state=quot;rjconnectedquot;>
       <createcall dest=quot;'tel:+18315551234'quot;/>
  <assign name=quot;statequot; expr=quot;'calling'quot;/>
     </transition>
     <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;>
  <createcall dest=quot;event$.values.destquot;/>
       <assign name=quot;statequot; expr=quot;'calling'quot;/>
</transition> dest=quot;event$.values.destquot;/>
       <createcall
     </transition>
     <transition event=quot;connection.connectedquot; state=quot;callingquot;>
       <assign name=quot;statequot; expr=quot;'connected'quot;/>
       <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/>
     </transition>
     <transition event=quot;connection.failedquot; state=quot;callingquot;>
          <exit/>
     </transition>
     <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;>
          <exit/>
     </transition>
   </eventprocessor>
 </ccxml>




                                                                      58
Call router + Twitter
<?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?>
<ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;>
  <var name=quot;statequot; expr=quot;'init'quot;/>
  <var name=quot;incomingcallquot;/>
  <eventprocessor statevariable=quot;statequot;>
    <transition event=quot;connection.alertingquot; state=quot;initquot;>
      <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/>
      <accept/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;
         cond=quot;event$.connection.remote=='tel:+18315551234'quot;>
      <assign name=quot;statequot; expr=quot;'rjconnected'quot;/>
      <dialogstart src=quot;'rj.vxml'quot;
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;>
      <assign name=quot;statequot; expr=quot;'callconnected'quot;/>
      <dialogstart src=quot;'caller.vxml'quot;
    </transition>
    <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
      <createcall dest=quot;'tel:+18315551234'quot;/>
    </transition>
    <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
      <createcall dest=quot;event$.values.destquot;/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;callingquot;>
      <assign name=quot;statequot; expr=quot;'connected'quot;/>
      <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/>
    </transition>
    <transition event=quot;connection.failedquot; state=quot;callingquot;>
         <exit/>
    </transition>
    <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;>
         <exit/>
    </transition>
  </eventprocessor>
</ccxml>




                                                                     59
Call router + Twitter
<?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?>
<ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;>
  <var name=quot;statequot; expr=quot;'init'quot;/>
  <var name=quot;incomingcallquot;/>
  <eventprocessor statevariable=quot;statequot;>
    <transition event=quot;connection.alertingquot; state=quot;initquot;>
      <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/>
      <accept/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;
         cond=quot;event$.connection.remote=='tel:+18315551234'quot;>
      <assign name=quot;statequot; expr=quot;'rjconnected'quot;/>
      <dialogstart src=quot;'rj.vxml'quot;
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;>
      <assign name=quot;statequot; expr=quot;'callconnected'quot;/>
      <dialogstart src=quot;'caller.vxml'quot;
    </transition>
   <transition event=quot;connection.connectedquot;
    <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;>
   state=quot;callingquot;> expr=quot;'calling'quot;/>
      <assign name=quot;statequot;
      <createcall dest=quot;'tel:+18315551234'quot;/>
    </transition>
    <transition event=quot;dialog.exitquot; expr=quot;'connected'quot;/>
      <assign name=quot;statequot; state=quot;rjconnectedquot;>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
      <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/>
      <createcall dest=quot;event$.values.destquot;/>
    </transition>
   </transition>
    <transition event=quot;connection.connectedquot; state=quot;callingquot;>
      <assign name=quot;statequot; expr=quot;'connected'quot;/>
      <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/>
    </transition>
    <transition event=quot;connection.failedquot; state=quot;callingquot;>
         <exit/>
    </transition>
    <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;>
         <exit/>
    </transition>
  </eventprocessor>
</ccxml>




                                                                     60
Call router + Twitter
<?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?>
<ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;>
  <var name=quot;statequot; expr=quot;'init'quot;/>
  <var name=quot;incomingcallquot;/>
  <eventprocessor statevariable=quot;statequot;>
    <transition event=quot;connection.alertingquot; state=quot;initquot;>
      <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/>
      <accept/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;
         cond=quot;event$.connection.remote=='tel:+18315551234'quot;>
      <assign name=quot;statequot; expr=quot;'rjconnected'quot;/>
      <dialogstart src=quot;'rj.vxml'quot;
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;>
      <assign name=quot;statequot; expr=quot;'callconnected'quot;/>
      <dialogstart src=quot;'caller.vxml'quot;
    </transition>
    <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
      <createcall dest=quot;'tel:+18315551234'quot;/>
    </transition>
    <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
      <createcall dest=quot;event$.values.destquot;/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;callingquot;>
      <assign name=quot;statequot; expr=quot;'connected'quot;/>
      <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/>
    </transition>
    <transition event=quot;connection.failedquot; state=quot;callingquot;>
         <exit/>
    </transition>
    <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;>
         <exit/>
    </transition>
  </eventprocessor>
</ccxml>




                                                                     61
Call router + Twitter
 <?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?>
 <ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;>
   <var name=quot;statequot; expr=quot;'init'quot;/>
   <var name=quot;incomingcallquot;/>
   <eventprocessor statevariable=quot;statequot;>
     <transition event=quot;connection.alertingquot; state=quot;initquot;>
       <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/>
       <accept/>
     </transition>
     <transition event=quot;connection.connectedquot; state=quot;initquot;
          cond=quot;event$.connection.remote=='tel:+18315551234'quot;>
       <assign name=quot;statequot; expr=quot;'rjconnected'quot;/>
       <dialogstart src=quot;'rj.vxml'quot;
     </transition>
     <transition event=quot;connection.connectedquot; state=quot;initquot;>
       <assign name=quot;statequot; expr=quot;'callconnected'quot;/>
       <dialogstart src=quot;'caller.vxml'quot;
<transition event=quot;connection.failedquot; state=quot;callingquot;>
     </transition>
     <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;>
     <exit/> name=quot;statequot; expr=quot;'calling'quot;/>
       <assign
</transition> dest=quot;'tel:+18315551234'quot;/>
       <createcall
     </transition>
     <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;>
<transition name=quot;statequot; expr=quot;'calling'quot;/>
       <assign event=quot;connection.disconnectedquot; state=quot;connectedquot;>
       <createcall dest=quot;event$.values.destquot;/>
     <exit/>
     </transition>
     <transition event=quot;connection.connectedquot; state=quot;callingquot;>
</transition>
       <assign name=quot;statequot; expr=quot;'connected'quot;/>
       <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/>
     </transition>
     <transition event=quot;connection.failedquot; state=quot;callingquot;>
          <exit/>
     </transition>
     <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;>
          <exit/>
     </transition>
   </eventprocessor>
 </ccxml>




                                                                      62
Call router + Twitter
<?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?>
<ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;>
  <var name=quot;statequot; expr=quot;'init'quot;/>
  <var name=quot;incomingcallquot;/>
  <eventprocessor statevariable=quot;statequot;>
    <transition event=quot;connection.alertingquot; state=quot;initquot;>
      <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/>
      <accept/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;
         cond=quot;event$.connection.remote=='tel:+18315551234'quot;>
      <assign name=quot;statequot; expr=quot;'rjconnected'quot;/>
      <dialogstart src=quot;'rj.vxml'quot;
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;initquot;>
      <assign name=quot;statequot; expr=quot;'callconnected'quot;/>
      <dialogstart src=quot;'caller.vxml'quot;
    </transition>
    <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
      <createcall dest=quot;'tel:+18315551234'quot;/>
    </transition>
    <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;>
      <assign name=quot;statequot; expr=quot;'calling'quot;/>
      <createcall dest=quot;event$.values.destquot;/>
    </transition>
    <transition event=quot;connection.connectedquot; state=quot;callingquot;>
      <assign name=quot;statequot; expr=quot;'connected'quot;/>
      <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/>
    </transition>
    <transition event=quot;connection.failedquot; state=quot;callingquot;>
         <exit/>
    </transition>
    <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;>
         <exit/>
    </transition>
  </eventprocessor>
</ccxml>




                                                                     63
So... How about APIʼs...



                           64
A Favorite of Carriers
                         65
Java
       66
SIP Servlets
  >   Standard Java based API for
      writing SIP applications.
  >   1.0 standardized as JSR-116.
  >   1.1 just released as JSR-289
  >   Extends the HTTP Servlet
      model to support SIP and
      telephony applications
  >   http://www.sipservlet.com/
  >   Supported by a large number of
      application servers including
      Oracle (BEA), IBM, Sun,
      Voxeo.
                                       67
Request Methods

>   doInvite(SipServletRequest req);
>   doAck(SipServletRequest req);
>   doOptions(SipServletRequest req);
>   doBye(SipServletRequest req);
>   doCancel(SipServletRequest req);
>   doSubscribe(SipServletRequest req);
>   doNotify(SipServletRequest req);
>   doMessage(SipServletRequest req);
>   doInfo(SipServletRequest req);
>   doPrack(SipServletRequest req);

                                          68
Response Methods

>   doProvisionalResponse(SipServletResponse res);
>   doSuccessResponse(SipServletResponse res);
>   doRedirectResponse(SipServletResponse res);
>   doErrorResponse(SipServletResponse res);




                                                     69
Basic Request

public class BasicSIPServlet extends SipServlet {
    protected void doInfo(SipServletRequest req)
       throws ServletException, IOException
    {
       req.createResponse(SipServletResponse.SC_TRYING).send();
       // do stuff
       req.createResponse(SipServletResponse.SC_OK).send();
    }
}




                                                                  70
Accessing SIP Headers

protected void doInvite(SipServletRequest req) throws
ServletException, IOException {


   String cpc ;

   if (req.getHeader(quot;User-Agentquot;).equals(quot;Sonusquot;)) {

   
 cpc = req.getHeader(quot;CallPartyquot;);

   } else if (req.getHeader(quot;User-Agentquot;).equals(quot;ZTEquot;)) {

   
 cpc = req.getHeader(quot;CPSquot;);

   }
}




                                                              71
JSR-309
  >   Java Media Server
      API
  >   Based on the
      CCXML media
      model
  >   Still in draft stage
  >   Provides dialog
      resources,
      conferencing, media
      routing to Java
      applications
                             72
Sample Application Overview

>   Lets try that application again in java...




                              73
start



                  isRJ()
      yes                           no

prompt for dest            play twitter status


   call dest                  call rj’s cell



                  end
SIP Flow

     Caller                         App                               Dest
              INVITE - doInvite()
                   200 OK

                ACK doAck()


                                          INVITE - transferDialog()
                                                  200 OK -
                                             doSuccessResponse()

                                                    ACK




                                                                             75
Call router + Twitter

public class TwitterSIPServlet extends SipServlet {
  SipFactory factory;
    public void init() throws ServletException {
      super.init();
      factory =(SipFactory)getServletContext().getAttribute(quot;javax.servlet.sip.SipFactoryquot;);
    }
  protected void doInvite(SipServletRequest req) {
    if(req.isInitial()){
      SipApplicationSession sipApp = factory.createApplicationSession();
      TwitterSIPServletSession service = new TwitterSIPServletSession(req.getSession(),
factory);
      sipApp.setAttribute(quot;router-appquot;, service);
      service.init(req);
    }
  }
    protected void doSuccessResponse(SipServletResponse resp) {
      resp.createAck().send();
    }
  protected void doAck(SipServletRequest req) {
    final TwitterSIPServletSession service
            = (TwitterSIPServletSession) req.getApplicationSession().getAttribute(quot;router-
appquot;);
    service.startDialog();
  }
    protected void doBye(SipServletRequest req) {
      // Need to send BYE request to the other legs
    }
}




                                                                                               76
Call router + Twitter

public class TwitterSIPServlet extends SipServlet {
  SipFactory factory;
    public void init() throws ServletException {
      super.init();
      factory =(SipFactory)getServletContext().getAttribute(quot;javax.servlet.sip.SipFactoryquot;);
    }
  protected void doInvite(SipServletRequest req) {
    if(req.isInitial()){
      SipApplicationSession sipApp = factory.createApplicationSession();
      TwitterSIPServletSession service = new TwitterSIPServletSession(req.getSession(),
factory);
      sipApp.setAttribute(quot;router-appquot;, service);
      service.init(req);
    }
  }
    protected void doSuccessResponse(SipServletResponse resp) {
      resp.createAck().send();
    }
  protected void doAck(SipServletRequest req) {
    final TwitterSIPServletSession service
            = (TwitterSIPServletSession) req.getApplicationSession().getAttribute(quot;router-
appquot;);
    service.startDialog();
  }
    protected void doBye(SipServletRequest req) {
      // Need to send BYE request to the other legs
    }
}




                                                                                               77
Call router + Twitter

public class TwitterSIPServlet extends SipServlet {
  SipFactory factory;
  public void init() throws ServletException {
public class TwitterSIPServlet extends SipServlet {
    super.init();
    factory =(SipFactory)getServletContext().getAttribute(quot;javax.servlet.sip.SipFactoryquot;);
  SipFactory factory;
  }
  protected void doInvite(SipServletRequest req) {
    if(req.isInitial()){
  public void init() sipApp = factory.createApplicationSession();
       SipApplicationSession throws ServletException {
       TwitterSIPServletSession service = new TwitterSIPServletSession(req.getSession(),
      super.init();
factory);
       sipApp.setAttribute(quot;router-appquot;, service);
    }
      factory = (SipFactory)getServletContext()
       service.init(req);
  }                   .getAttribute(quot;javax.servlet.sip.SipFactoryquot;);
    }
    protected void doSuccessResponse(SipServletResponse resp) {
      resp.createAck().send();
}   }
  protected void doAck(SipServletRequest req) {
    final TwitterSIPServletSession service
            = (TwitterSIPServletSession) req.getApplicationSession().getAttribute(quot;router-
appquot;);
    service.startDialog();
  }
    protected void doBye(SipServletRequest req) {
      // Need to send BYE request to the other legs
    }
}




                                                                                             78
Call router + Twitter

public class TwitterSIPServlet extends SipServlet {
  SipFactory factory;
    public void init() throws ServletException {
      super.init();
      factory =(SipFactory)getServletContext().getAttribute(quot;javax.servlet.sip.SipFactoryquot;);
    }
  protected void doInvite(SipServletRequest req) {
    if(req.isInitial()){
      SipApplicationSession sipApp = factory.createApplicationSession();
      TwitterSIPServletSession service = new TwitterSIPServletSession(req.getSession(),
factory);
      sipApp.setAttribute(quot;router-appquot;, service);
      service.init(req);
    }
  }
    protected void doSuccessResponse(SipServletResponse resp) {
      resp.createAck().send();
    }
  protected void doAck(SipServletRequest req) {
    final TwitterSIPServletSession service
            = (TwitterSIPServletSession) req.getApplicationSession().getAttribute(quot;router-
appquot;);
    service.startDialog();
  }
    protected void doBye(SipServletRequest req) {
      // Need to send BYE request to the other legs
    }
}




                                                                                               79
Call router + Twitter

public class TwitterSIPServlet extends SipServlet {
  SipFactory factory;
    public void init() throws ServletException {
      super.init();
      factory =(SipFactory)getServletContext().getAttribute(quot;javax.servlet.sip.SipFactoryquot;);
    }
  protected void doInvite(SipServletRequest req) {
 protected void doInvite(SipServletRequest req) {
    if(req.isInitial()){
      SipApplicationSession sipApp = factory.createApplicationSession();
    if(req.isInitial()){
      TwitterSIPServletSession service = new TwitterSIPServletSession(req.getSession(),
factory);
      sipApp.setAttribute(quot;router-appquot;, service);
      SipApplicationSession sipApp
      service.init(req);
    }                                  = factory.createApplicationSession();
  }
        TwitterSIPServletSession service
    protected void doSuccessResponse(SipServletResponse resp) {
    }      = new TwitterSIPServletSession(req.getSession(),
      resp.createAck().send();                                                  factory);
        sipApp.setAttribute(quot;router-appquot;, service);
  protected void doAck(SipServletRequest req) {
       service.init(req);
    final TwitterSIPServletSession service
            = (TwitterSIPServletSession) req.getApplicationSession().getAttribute(quot;router-
    }
appquot;);
    service.startDialog();
 }}
    protected void doBye(SipServletRequest req) {
      // Need to send BYE request to the other legs
    }
}




                                                                                               80
Call router + Twitter

public class TwitterSIPServlet extends SipServlet {
  SipFactory factory;
    public void init() throws ServletException {
      super.init();
      factory =(SipFactory)getServletContext().getAttribute(quot;javax.servlet.sip.SipFactoryquot;);
    }
  protected void doInvite(SipServletRequest req) {
    if(req.isInitial()){
      SipApplicationSession sipApp = factory.createApplicationSession();
      TwitterSIPServletSession service = new TwitterSIPServletSession(req.getSession(),
factory);
      sipApp.setAttribute(quot;router-appquot;, service);
      service.init(req);
    }
  }
    protected void doSuccessResponse(SipServletResponse resp) {
      resp.createAck().send();
    }
  protected void doAck(SipServletRequest req) {
    final TwitterSIPServletSession service
            = (TwitterSIPServletSession) req.getApplicationSession().getAttribute(quot;router-
appquot;);
    service.startDialog();
  }
    protected void doBye(SipServletRequest req) {
      // Need to send BYE request to the other legs
    }
}




                                                                                               81
Call router + Twitter

public class TwitterSIPServlet extends SipServlet {
  SipFactory factory;
    public void init() throws ServletException {
      super.init();
      factory =(SipFactory)getServletContext().getAttribute(quot;javax.servlet.sip.SipFactoryquot;);
    }
  protected void doInvite(SipServletRequest req) {
    if(req.isInitial()){
      SipApplicationSession sipApp = factory.createApplicationSession();
      TwitterSIPServletSession service = new TwitterSIPServletSession(req.getSession(),
factory);
 protected void doSuccessResponse(SipServletResponse resp) {
      sipApp.setAttribute(quot;router-appquot;, service);
    resp.createAck().send();
    }
      service.init(req);

 }}
    protected void doSuccessResponse(SipServletResponse resp) {
      resp.createAck().send();
    }
  protected void doAck(SipServletRequest req) {
    final TwitterSIPServletSession service
            = (TwitterSIPServletSession) req.getApplicationSession().getAttribute(quot;router-
appquot;);
    service.startDialog();
  }
    protected void doBye(SipServletRequest req) {
      // Need to send BYE request to the other legs
    }
}




                                                                                               82
Call router + Twitter

public class TwitterSIPServlet extends SipServlet {
  SipFactory factory;
    public void init() throws ServletException {
      super.init();
      factory =(SipFactory)getServletContext().getAttribute(quot;javax.servlet.sip.SipFactoryquot;);
    }
  protected void doInvite(SipServletRequest req) {
    if(req.isInitial()){
      SipApplicationSession sipApp = factory.createApplicationSession();
      TwitterSIPServletSession service = new TwitterSIPServletSession(req.getSession(),
factory);
      sipApp.setAttribute(quot;router-appquot;, service);
      service.init(req);
    }
  }
    protected void doSuccessResponse(SipServletResponse resp) {
      resp.createAck().send();
    }
  protected void doAck(SipServletRequest req) {
    final TwitterSIPServletSession service
            = (TwitterSIPServletSession) req.getApplicationSession().getAttribute(quot;router-
appquot;);
    service.startDialog();
  }
    protected void doBye(SipServletRequest req) {
      // Need to send BYE request to the other legs
    }
}




                                                                                               83
Call router + Twitter

public class TwitterSIPServlet extends SipServlet {
  SipFactory factory;
    public void init() throws ServletException {
      super.init();
      factory =(SipFactory)getServletContext().getAttribute(quot;javax.servlet.sip.SipFactoryquot;);
    }

 protected void doAck(SipServletRequest req) {
  protected void doInvite(SipServletRequest req) {
    if(req.isInitial()){
    final TwitterSIPServletSession service
      SipApplicationSession sipApp = factory.createApplicationSession();
      TwitterSIPServletSession service = new TwitterSIPServletSession(req.getSession(),
factory);
             = (TwitterSIPServletSession) req.getApplicationSession()
      sipApp.setAttribute(quot;router-appquot;, service);
      service.init(req);      .getAttribute(quot;router-appquot;);
    }
  } service.startDialog();

 } resp.createAck().send();
  protected void doSuccessResponse(SipServletResponse resp) {
    }
  protected void doAck(SipServletRequest req) {
    final TwitterSIPServletSession service
            = (TwitterSIPServletSession) req.getApplicationSession().getAttribute(quot;router-
appquot;);
    service.startDialog();
  }
    protected void doBye(SipServletRequest req) {
      // Need to send BYE request to the other legs
    }
}




                                                                                               84
Call router + Twitter

public class TwitterSIPServlet extends SipServlet {
  SipFactory factory;
    public void init() throws ServletException {
      super.init();
      factory =(SipFactory)getServletContext().getAttribute(quot;javax.servlet.sip.SipFactoryquot;);
    }
  protected void doInvite(SipServletRequest req) {
    if(req.isInitial()){
      SipApplicationSession sipApp = factory.createApplicationSession();
      TwitterSIPServletSession service = new TwitterSIPServletSession(req.getSession(),
factory);
      sipApp.setAttribute(quot;router-appquot;, service);
      service.init(req);
    }
  }
    protected void doSuccessResponse(SipServletResponse resp) {
      resp.createAck().send();
    }
  protected void doAck(SipServletRequest req) {
    final TwitterSIPServletSession service
            = (TwitterSIPServletSession) req.getApplicationSession().getAttribute(quot;router-
appquot;);
    service.startDialog();
  }
    protected void doBye(SipServletRequest req) {
      // Need to send BYE request to the other legs
    }
}




                                                                                               85
Call router + Twitter

public class TwitterSIPServlet extends SipServlet {
  SipFactory factory;
    public void init() throws ServletException {
      super.init();
      factory =(SipFactory)getServletContext().getAttribute(quot;javax.servlet.sip.SipFactoryquot;);
    }
  protected void doInvite(SipServletRequest req) {
    if(req.isInitial()){
      SipApplicationSession sipApp = factory.createApplicationSession();
      TwitterSIPServletSession service = new TwitterSIPServletSession(req.getSession(),
factory); protected void doBye(SipServletRequest req)                      {
      sipApp.setAttribute(quot;router-appquot;, service);
      service.init(req);the frack has cleanup code in
              // Who
    }
  }           // slide demo’s anyway?
    protected }void doSuccessResponse(SipServletResponse resp) {
      resp.createAck().send();
    }
  protected void doAck(SipServletRequest req) {
    final TwitterSIPServletSession service
            = (TwitterSIPServletSession) req.getApplicationSession().getAttribute(quot;router-
appquot;);
    service.startDialog();
  }
    protected void doBye(SipServletRequest req) {
      // Need to send BYE request to the other legs
    }
}




                                                                                               86
Call router + Twitter

public class TwitterSIPServlet extends SipServlet {
  SipFactory factory;
    public void init() throws ServletException {
      super.init();
      factory =(SipFactory)getServletContext().getAttribute(quot;javax.servlet.sip.SipFactoryquot;);
    }
  protected void doInvite(SipServletRequest req) {
    if(req.isInitial()){
      SipApplicationSession sipApp = factory.createApplicationSession();
      TwitterSIPServletSession service = new TwitterSIPServletSession(req.getSession(),
factory);
      sipApp.setAttribute(quot;router-appquot;, service);
      service.init(req);
    }
  }
    protected void doSuccessResponse(SipServletResponse resp) {
      resp.createAck().send();
    }
  protected void doAck(SipServletRequest req) {
    final TwitterSIPServletSession service
            = (TwitterSIPServletSession) req.getApplicationSession().getAttribute(quot;router-
appquot;);
    service.startDialog();
  }
    protected void doBye(SipServletRequest req) {
      // Need to send BYE request to the other legs
    }
}




                                                                                               87
Call router + Twitter
public class TwitterSIPServletSession   {
   final SipSession mySipSession;
   final SipFactory myFactory;
   MediaGroup myMediaGroup;
   boolean isRJ = false;
    public TwitterSIPServletSession(SipSession aSipSession, SipFactory aFactory) {
       ...
    }
    public void init(final SipServletRequest req) {
       ...
    }
    public void startDialog() {
       ...
    }

    class CallerPlayerListener implements MediaEventListener<PlayerEvent> {
       ...
    }
    class RJDialerSignalDetectorListener
                               implements MediaEventListener<SignalDetectorEvent> {
       ...
    }
    void transferDialog(String uri) throws ServletParseException, IOException {
       ...
    }
}




                                                                                      88
Call router + Twitter
public class TwitterSIPServletSession   {
   final SipSession mySipSession;
   final SipFactory myFactory;
   MediaGroup myMediaGroup;
   boolean isRJ = false;
    public TwitterSIPServletSession(SipSession aSipSession, SipFactory aFactory) {
       ...
    }
    public void init(final SipServletRequest req) {
       ...
    }
    public void startDialog() {
       ...
    }

    class CallerPlayerListener implements MediaEventListener<PlayerEvent> {
       ...
    }
    class RJDialerSignalDetectorListener
                               implements MediaEventListener<SignalDetectorEvent> {
       ...
    }
    void transferDialog(String uri) throws ServletParseException, IOException {
       ...
    }
}




                                                                                      89
Call router + Twitter
public class TwitterSIPServletSession   {
   final SipSession mySipSession;
   final SipFactory myFactory;
   MediaGroup myMediaGroup;
   boolean isRJ = false;
     public TwitterSIPServletSession(SipSession aSipSession, SipFactory aFactory) {
        ...
     }
     public void init(final SipServletRequest req) {
    public class TwitterSIPServletSession
        ...                                               {
     }
         final SipSession mySipSession;
     public void startDialog() {
         final SipFactory myFactory;
        ...
     }
         MediaGroup myMediaGroup;
         boolean isRJ = false;
     class CallerPlayerListener implements MediaEventListener<PlayerEvent>   {
         ...
     }
         public TwitterSIPServletSession(SipSession aSipSession,
     class RJDialerSignalDetectorListener
                                implements MediaEventListener<SignalDetectorEvent> {
        ...                                           SipFactory aFactory) {
     }      mySipSession = aSipSession;
        ... myFactory = aFactory;
     void transferDialog(String uri) throws ServletParseException, IOException {

}
     }   }
    }




                                                                                       90
Call router + Twitter
public class TwitterSIPServletSession   {
   final SipSession mySipSession;
   final SipFactory myFactory;
   MediaGroup myMediaGroup;
   boolean isRJ = false;
    public TwitterSIPServletSession(SipSession aSipSession, SipFactory aFactory) {
       ...
    }
    public void init(final SipServletRequest req) {
       ...
    }
    public void startDialog() {
       ...
    }

    class CallerPlayerListener implements MediaEventListener<PlayerEvent> {
       ...
    }
    class RJDialerSignalDetectorListener
                               implements MediaEventListener<SignalDetectorEvent> {
       ...
    }
    void transferDialog(String uri) throws ServletParseException, IOException {
       ...
    }
}




                                                                                      91
Call router + Twitter
public class TwitterSIPServletSession      {
   final SipSession mySipSession;
   final SipFactory myFactory;
   MediaGroup myMediaGroup;
   boolean isRJ = false;
        public TwitterSIPServletSession(SipSession aSipSession, SipFactory aFactory) {
           ...
        }
    public void init(final SipServletRequest req) throws ServletException {
       MediaSession myMediaSession = MediaSessionFactory.createMediaSession();
     public void init(final SipServletRequest req) {
            ...
        }
       NetworkConnection myNetworkConnection =
     public void startDialog() {
    myMediaSession.createContainer(NetworkConnectionConfig.c_Basic);
        ...
        }
        myMediaGroup =
    myMediaSession.createContainer(MediaGroupConfig.c_PlayerSignalDetector);
     class CallerPlayerListener implements MediaEventListener<PlayerEvent> {
            ...
        }
          MediaEventListener<NetworkConnectionEvent> myNetworkConnectionListener
                          = new MediaEventListener<NetworkConnectionEvent>() {
        class RJDialerSignalDetectorListener
                                   implements MediaEventListener<SignalDetectorEvent> {
           ... ....
        } };
          myNetworkConnection.addListener(myNetworkConnectionListener);
        void transferDialog(String uri) throws ServletParseException, IOException {
            ...
        } myNetworkConnection.modify(quot;quot;, new String(req.getRawContent()));
}
    }




                                                                                          92
Call router + Twitter
public class TwitterSIPServletSession   {
   final SipSession mySipSession;
   final SipFactory myFactory;
   MediaGroup myMediaGroup;
   boolean isRJ = false;
   public TwitterSIPServletSession(SipSession aSipSession, SipFactory aFactory) {
      ...
   }
  MediaEventListener<NetworkConnectionEvent> myNetworkConnectionListener = new
  MediaEventListener<NetworkConnectionEvent>() {
   public void init(final SipServletRequest req) {
       ...
     public void onEvent(NetworkConnectionEvent anEvent) {
   }
         if (NetworkConnectionConstants.ev_Modify.equals(anEvent.getEventID())) {
   public void (req.getFrom().getURI().getUser().equals(quot;8312392883quot;)) {
                startDialog() {
       ... if
   }          isRJ = true;
              myMediaGroup.getSignalDetector().addListener(
                            new RJDialerSignalDetectorListener());
   class CallerPlayerListener implements MediaEventListener<PlayerEvent> {
       ... } else {
   }
              myMediaGroup.getSignalDetector().addListener(
                            new CallerPlayerListener());
   class RJDialerSignalDetectorListener
                                implements MediaEventListener<SignalDetectorEvent> {
       ... }
   }        myMediaGroup.join(Direction.DUPLEX, myNetworkConnection);
            String sdpAnswer = myNetworkConnection.getRawLocalSessionDescription();
   void transferDialog(String uri) throws ServletParseException, IOException {
       ... SipServletMessage msg = req.createResponse(200, quot;OKquot;);
   }        msg.setContent(sdpAnswer.getBytes(), quot;application/sdpquot;);
}
            msg.send();
         }
     }
  };




                                                                                       93
Call router + Twitter
public class TwitterSIPServletSession   {
   final SipSession mySipSession;
   final SipFactory myFactory;
   MediaGroup myMediaGroup;
   boolean isRJ = false;
    public TwitterSIPServletSession(SipSession aSipSession, SipFactory aFactory) {
       ...
    }
    public void init(final SipServletRequest req) {
       ...
    }
    public void startDialog() {
       ...
    }

    class CallerPlayerListener implements MediaEventListener<PlayerEvent> {
       ...
    }
    class RJDialerSignalDetectorListener
                               implements MediaEventListener<SignalDetectorEvent> {
       ...
    }
    void transferDialog(String uri) throws ServletParseException, IOException {
       ...
    }
}




                                                                                      94
Call router + Twitter
 public class TwitterSIPServletSession    {
    final SipSession mySipSession;
    final SipFactory myFactory;
    MediaGroup myMediaGroup;
public void startDialog() {
    boolean isRJ = false;
        if (isRJ) {
          Parameters collectOptions = mediaSessionFactory.createParameters();
        public TwitterSIPServletSession(SipSession aSipSession, SipFactory aFactory) {
           ... prompt = URI.create(quot;data:application/ssml+xml,quot;+
            URI
        }
                quot;<?xml version=quot;1.0quot;?>quot;+
        public void init(final SipServletRequest req) {
           ... quot;<speak>quot;+
        }              quot;Welcome RJ. Please enter the phone number you wish to reach.quot;+
                 quot;</speak>quot;);
        public void startDialog() {
          collectOptions.put(SignalDetectorConstants.p_Prompt, prompt);
           ...
        } mg.getSignalDetector().receiveSignals(10, null, RTC.bargeIn, collectOptions);
        } else {
        class CallerPlayerListener twitter_apiMediaEventListener<PlayerEvent> {
            net.unto.twitter.Api implements
           ...          = new net.unto.twitter.Api(quot;zscgeekquot;, quot;passwordquot;);
        }
            URI prompt = URI.create(quot;data:application/ssml+xml,quot;+
        class RJDialerSignalDetectorListener
                quot;<?xml version=quot;1.0quot;?>quot;+
                                    implements MediaEventListener<SignalDetectorEvent> {
           ... quot;<speak>quot;+
        }           quot;Thank you for calling RJ. We will connect you now.quot;+
                    quot;His twitter status is:quot;+
        void transferDialog(String uri) throws ServletParseException, IOException {
           ...      twitter_api.getStatus()+
        }       quot;</speak>quot;);
    }
            myMediaGroup.getPlayer().play(prompt, null, null);
        }
}




                                                                                           95
Call router + Twitter
public class TwitterSIPServletSession   {
   final SipSession mySipSession;
   final SipFactory myFactory;
   MediaGroup myMediaGroup;
   boolean isRJ = false;
    public TwitterSIPServletSession(SipSession aSipSession, SipFactory aFactory) {
       ...
    }
    public void init(final SipServletRequest req) {
       ...
    }
    public void startDialog() {
       ...
    }

    class CallerPlayerListener implements MediaEventListener<PlayerEvent> {
       ...
    }
    class RJDialerSignalDetectorListener
                               implements MediaEventListener<SignalDetectorEvent> {
       ...
    }
    void transferDialog(String uri) throws ServletParseException, IOException {
       ...
    }
}




                                                                                      96
Call router + Twitter
public class TwitterSIPServletSession   {
   final SipSession mySipSession;
   final SipFactory myFactory;
   MediaGroup myMediaGroup;
   boolean isRJ = false;
    public TwitterSIPServletSession(SipSession aSipSession, SipFactory aFactory) {
       ...
    }
    public void init(final SipServletRequest req) {
       ...
    }
    public void startDialog() {
       ...
    class CallerPlayerListener implements MediaEventListener<PlayerEvent> {
    }
       public void onEvent(PlayerEvent anEvent) {
    class CallerPlayerListenerquot;+anEvent.getSignalString());
           log(quot;Collected: implements MediaEventListener<PlayerEvent> {
       ...
    }      MediaSession mediaSession =
                             anEvent.getSource().getMediaSession().release();
    class RJDialerSignalDetectorListener
           transferDialog(quot;sip:+18315551234@gateway:5060quot;);
                               implements MediaEventListener<SignalDetectorEvent> {
       ...
    } }
    }
    void transferDialog(String uri) throws ServletParseException, IOException {
        ...
    }
}




                                                                                      97
Call router + Twitter
public class TwitterSIPServletSession   {
   final SipSession mySipSession;
   final SipFactory myFactory;
   MediaGroup myMediaGroup;
   boolean isRJ = false;
    public TwitterSIPServletSession(SipSession aSipSession, SipFactory aFactory) {
       ...
    }
    public void init(final SipServletRequest req) {
       ...
    }
    public void startDialog() {
       ...
    }

    class CallerPlayerListener implements MediaEventListener<PlayerEvent> {
       ...
    }
    class RJDialerSignalDetectorListener
                               implements MediaEventListener<SignalDetectorEvent> {
       ...
    }
    void transferDialog(String uri) throws ServletParseException, IOException {
       ...
    }
}




                                                                                      98
Call router + Twitter
public class TwitterSIPServletSession   {
   final SipSession mySipSession;
   final SipFactory myFactory;
   MediaGroup myMediaGroup;
   boolean isRJ = false;
    public TwitterSIPServletSession(SipSession aSipSession, SipFactory aFactory) {
       ...
    }
    public void init(final SipServletRequest req) {
       ...
    }
    class RJDialerSignalDetectorListener implements
    MediaEventListener<SignalDetectorEvent> {
    public void startDialog() {
       ...
    } public void onEvent(SignalDetectorEvent anEvent) {
           log(quot;Collected: quot;+anEvent.getSignalString());
    class CallerPlayerListener implements =
           MediaSession mediaSession MediaEventListener<PlayerEvent> {
       ...
    }                     anEvent.getSource().getMediaSession().release();
           transferDialog(quot;sip:quot; + anEvent.getSignalString()
    class RJDialerSignalDetectorListener
                          + quot;@gateway:5060quot;);
                                implements MediaEventListener<SignalDetectorEvent> {
       ...
    } }
    }
    void transferDialog(String uri) throws ServletParseException, IOException {
        ...
    }
}




                                                                                       99
Call router + Twitter
public class TwitterSIPServletSession   {
   final SipSession mySipSession;
   final SipFactory myFactory;
   MediaGroup myMediaGroup;
   boolean isRJ = false;
    public TwitterSIPServletSession(SipSession aSipSession, SipFactory aFactory) {
       ...
    }
    public void init(final SipServletRequest req) {
       ...
    }
    public void startDialog() {
       ...
    }

    class CallerPlayerListener implements MediaEventListener<PlayerEvent> {
       ...
    }
    class RJDialerSignalDetectorListener
                               implements MediaEventListener<SignalDetectorEvent> {
       ...
    }
    void transferDialog(String uri) throws ServletParseException, IOException {
       ...
    }
}




                                                                                      100
Call router + Twitter
public class TwitterSIPServletSession   {
   final SipSession mySipSession;
   final SipFactory myFactory;
   MediaGroup myMediaGroup;
   boolean isRJ = false;
    public TwitterSIPServletSession(SipSession aSipSession, SipFactory aFactory) {
       ...
    }
    public void init(final SipServletRequest req) {
       ...
    }
    void transferDialog(String uri) {
    public void startDialog() request =
         SipServletRequest {
       ...
    }           myFactory.createRequest(mySipSession.getApplicationSession(),
                                           quot;INVITEquot;,
                                           quot;sip:addressbook@sip-as-uri:5060quot;,
    class CallerPlayerListener implements MediaEventListener<PlayerEvent> {
       ...
    }                                      uri);
         request.send();
    class RJDialerSignalDetectorListener
    }                          implements MediaEventListener<SignalDetectorEvent> {
        ...
    }
    void transferDialog(String uri) throws ServletParseException, IOException {
       ...
    }
}




                                                                                      101
Call router + Twitter
public class TwitterSIPServletSession   {
   final SipSession mySipSession;
   final SipFactory myFactory;
   MediaGroup myMediaGroup;
   boolean isRJ = false;
    public TwitterSIPServletSession(SipSession aSipSession, SipFactory aFactory) {
       ...
    }
    public void init(final SipServletRequest req) {
       ...
    }
    public void startDialog() {
       ...
    }

    class CallerPlayerListener implements MediaEventListener<PlayerEvent> {
       ...
    }
    class RJDialerSignalDetectorListener
                               implements MediaEventListener<SignalDetectorEvent> {
       ...
    }
    void transferDialog(String uri) throws ServletParseException, IOException {
       ...
    }
}




                                                                                      102
Made it to the finish line!
                             103
So. We Have Java...
                      104
But is it Simple?
                    105
Is it cool?
              106
Is It Web 2.0?
                 107
Well Not Exactly...



                      108
So...



        109
Tropo.com



            110
answer();
say(quot;Hello, world!quot;);
      hangup();

      Tropo is Simple
                        111
Ruby




 Telephony in YOUR Language
(thanks to the magic of JSR223)
                                  112
•! answer
•! redirect   •! ask
•! reject     •! say      •! log
              •! record   •! wait      •! call
                          •! default   •! transfer
                                       •! hangup




              Simple to Learn
                                                     113
•Hosted service
•Accessible via Phone, SIP, Skype etc
•Inbound and Outbound calling
•Free for developers
•No setup costs
•Five minutes from sign-up to live deployment


                  +              = GO

               Simple to Deploy
                                                114
What are the Ingredients?
                            115
JavaOne - A Sip Of Java - RJ Auburn
JavaOne - A Sip Of Java - RJ Auburn
JavaOne - A Sip Of Java - RJ Auburn
JavaOne - A Sip Of Java - RJ Auburn
JavaOne - A Sip Of Java - RJ Auburn
JavaOne - A Sip Of Java - RJ Auburn
JavaOne - A Sip Of Java - RJ Auburn
JavaOne - A Sip Of Java - RJ Auburn
JavaOne - A Sip Of Java - RJ Auburn
JavaOne - A Sip Of Java - RJ Auburn
JavaOne - A Sip Of Java - RJ Auburn
JavaOne - A Sip Of Java - RJ Auburn
JavaOne - A Sip Of Java - RJ Auburn
JavaOne - A Sip Of Java - RJ Auburn
JavaOne - A Sip Of Java - RJ Auburn
JavaOne - A Sip Of Java - RJ Auburn
JavaOne - A Sip Of Java - RJ Auburn
JavaOne - A Sip Of Java - RJ Auburn
JavaOne - A Sip Of Java - RJ Auburn
JavaOne - A Sip Of Java - RJ Auburn
JavaOne - A Sip Of Java - RJ Auburn
JavaOne - A Sip Of Java - RJ Auburn
JavaOne - A Sip Of Java - RJ Auburn
JavaOne - A Sip Of Java - RJ Auburn
JavaOne - A Sip Of Java - RJ Auburn
JavaOne - A Sip Of Java - RJ Auburn
JavaOne - A Sip Of Java - RJ Auburn
JavaOne - A Sip Of Java - RJ Auburn

More Related Content

Similar to JavaOne - A Sip Of Java - RJ Auburn

Introduction to VoIP, RTP and SIP
Introduction to VoIP, RTP and SIP Introduction to VoIP, RTP and SIP
Introduction to VoIP, RTP and SIP ThousandEyes
 
Cisco TIP Presentation
Cisco TIP PresentationCisco TIP Presentation
Cisco TIP PresentationIMTC
 
Vo Ip Rajibdeka
Vo Ip RajibdekaVo Ip Rajibdeka
Vo Ip Rajibdekarajibdk
 
respond_to :voice - the convergence of voice and web interfaces with Rails an...
respond_to :voice - the convergence of voice and web interfaces with Rails an...respond_to :voice - the convergence of voice and web interfaces with Rails an...
respond_to :voice - the convergence of voice and web interfaces with Rails an...jpalley
 
Asterisk - Glen Bastes
Asterisk - Glen BastesAsterisk - Glen Bastes
Asterisk - Glen Bastessoss
 
Brightcove live tech overview
Brightcove live tech overviewBrightcove live tech overview
Brightcove live tech overviewJordi Cenzano
 
Brendan kearns berlin 2012 vn3
Brendan kearns berlin 2012 vn3Brendan kearns berlin 2012 vn3
Brendan kearns berlin 2012 vn3Brendan Kearns
 
Docfoc.com ngn - signaling &amp;amp; protocol analysis
Docfoc.com ngn - signaling &amp;amp; protocol analysisDocfoc.com ngn - signaling &amp;amp; protocol analysis
Docfoc.com ngn - signaling &amp;amp; protocol analysisRashid Khan
 
SIP in action Itexpo West
SIP in action Itexpo WestSIP in action Itexpo West
SIP in action Itexpo WestGraham Francis
 
Sinnreich Henry Johnston Alan Pt 2
Sinnreich Henry Johnston Alan   Pt 2Sinnreich Henry Johnston Alan   Pt 2
Sinnreich Henry Johnston Alan Pt 2Carl Ford
 
Homer metrics | LORENZO MANGANI Y FEDERICO CABIDDU - VoIP2DAY 2017
Homer metrics | LORENZO MANGANI Y FEDERICO CABIDDU - VoIP2DAY 2017Homer metrics | LORENZO MANGANI Y FEDERICO CABIDDU - VoIP2DAY 2017
Homer metrics | LORENZO MANGANI Y FEDERICO CABIDDU - VoIP2DAY 2017VOIP2DAY
 
Jitsi Videobridge, Octopodes, and Kotlin
Jitsi Videobridge, Octopodes, and KotlinJitsi Videobridge, Octopodes, and Kotlin
Jitsi Videobridge, Octopodes, and KotlinBoris Grozev
 
Sip Trunking Getting It Right The 1st Time
Sip Trunking   Getting It Right The 1st TimeSip Trunking   Getting It Right The 1st Time
Sip Trunking Getting It Right The 1st TimeGraham Francis
 
Federico Cabiddu - VoIP2DAY 2016 | VoIP and RTC Troubleshooting using the Sip...
Federico Cabiddu - VoIP2DAY 2016 | VoIP and RTC Troubleshooting using the Sip...Federico Cabiddu - VoIP2DAY 2016 | VoIP and RTC Troubleshooting using the Sip...
Federico Cabiddu - VoIP2DAY 2016 | VoIP and RTC Troubleshooting using the Sip...VOIP2DAY
 
1 Vo Ip Overview
1 Vo Ip Overview1 Vo Ip Overview
1 Vo Ip OverviewMayank Vora
 

Similar to JavaOne - A Sip Of Java - RJ Auburn (20)

Voip basics
Voip   basicsVoip   basics
Voip basics
 
Introduction to VoIP, RTP and SIP
Introduction to VoIP, RTP and SIP Introduction to VoIP, RTP and SIP
Introduction to VoIP, RTP and SIP
 
Introduction to VOIP
Introduction to VOIPIntroduction to VOIP
Introduction to VOIP
 
Cisco TIP Presentation
Cisco TIP PresentationCisco TIP Presentation
Cisco TIP Presentation
 
Vo Ip Rajibdeka
Vo Ip RajibdekaVo Ip Rajibdeka
Vo Ip Rajibdeka
 
respond_to :voice - the convergence of voice and web interfaces with Rails an...
respond_to :voice - the convergence of voice and web interfaces with Rails an...respond_to :voice - the convergence of voice and web interfaces with Rails an...
respond_to :voice - the convergence of voice and web interfaces with Rails an...
 
Resume 8 Yrs.Exp. c c++,Telecom
Resume 8 Yrs.Exp. c c++,TelecomResume 8 Yrs.Exp. c c++,Telecom
Resume 8 Yrs.Exp. c c++,Telecom
 
Asterisk - Glen Bastes
Asterisk - Glen BastesAsterisk - Glen Bastes
Asterisk - Glen Bastes
 
Brightcove live tech overview
Brightcove live tech overviewBrightcove live tech overview
Brightcove live tech overview
 
Brendan kearns berlin 2012 vn3
Brendan kearns berlin 2012 vn3Brendan kearns berlin 2012 vn3
Brendan kearns berlin 2012 vn3
 
Docfoc.com ngn - signaling &amp;amp; protocol analysis
Docfoc.com ngn - signaling &amp;amp; protocol analysisDocfoc.com ngn - signaling &amp;amp; protocol analysis
Docfoc.com ngn - signaling &amp;amp; protocol analysis
 
SIP in action Itexpo West
SIP in action Itexpo WestSIP in action Itexpo West
SIP in action Itexpo West
 
Sinnreich Henry Johnston Alan Pt 2
Sinnreich Henry Johnston Alan   Pt 2Sinnreich Henry Johnston Alan   Pt 2
Sinnreich Henry Johnston Alan Pt 2
 
Introduction to PPP
Introduction to PPPIntroduction to PPP
Introduction to PPP
 
Homer metrics | LORENZO MANGANI Y FEDERICO CABIDDU - VoIP2DAY 2017
Homer metrics | LORENZO MANGANI Y FEDERICO CABIDDU - VoIP2DAY 2017Homer metrics | LORENZO MANGANI Y FEDERICO CABIDDU - VoIP2DAY 2017
Homer metrics | LORENZO MANGANI Y FEDERICO CABIDDU - VoIP2DAY 2017
 
VoIP Recording
VoIP RecordingVoIP Recording
VoIP Recording
 
Jitsi Videobridge, Octopodes, and Kotlin
Jitsi Videobridge, Octopodes, and KotlinJitsi Videobridge, Octopodes, and Kotlin
Jitsi Videobridge, Octopodes, and Kotlin
 
Sip Trunking Getting It Right The 1st Time
Sip Trunking   Getting It Right The 1st TimeSip Trunking   Getting It Right The 1st Time
Sip Trunking Getting It Right The 1st Time
 
Federico Cabiddu - VoIP2DAY 2016 | VoIP and RTC Troubleshooting using the Sip...
Federico Cabiddu - VoIP2DAY 2016 | VoIP and RTC Troubleshooting using the Sip...Federico Cabiddu - VoIP2DAY 2016 | VoIP and RTC Troubleshooting using the Sip...
Federico Cabiddu - VoIP2DAY 2016 | VoIP and RTC Troubleshooting using the Sip...
 
1 Vo Ip Overview
1 Vo Ip Overview1 Vo Ip Overview
1 Vo Ip Overview
 

More from Voxeo Corp

Voxeo Summit Day 2 -What's new in CXP 14
Voxeo Summit Day 2 -What's new in CXP 14Voxeo Summit Day 2 -What's new in CXP 14
Voxeo Summit Day 2 -What's new in CXP 14Voxeo Corp
 
Voxeo Summit Day 2 -Voxeo APIs and SDKs
Voxeo Summit Day 2 -Voxeo APIs and SDKsVoxeo Summit Day 2 -Voxeo APIs and SDKs
Voxeo Summit Day 2 -Voxeo APIs and SDKsVoxeo Corp
 
Voxeo Summit Day 2 - Voxeo CXP - IVR on Steroids
Voxeo Summit Day 2 - Voxeo CXP - IVR on SteroidsVoxeo Summit Day 2 - Voxeo CXP - IVR on Steroids
Voxeo Summit Day 2 - Voxeo CXP - IVR on SteroidsVoxeo Corp
 
Voxeo Summit Day 2 - Using CXP hotspot analytics
Voxeo Summit Day 2 - Using CXP hotspot analyticsVoxeo Summit Day 2 - Using CXP hotspot analytics
Voxeo Summit Day 2 - Using CXP hotspot analyticsVoxeo Corp
 
Voxeo Summit Day 2 - Securing customer interactions
Voxeo Summit Day 2 - Securing customer interactionsVoxeo Summit Day 2 - Securing customer interactions
Voxeo Summit Day 2 - Securing customer interactionsVoxeo Corp
 
Voxeo Summit Day 2 - Real-time communications with WebRTC
Voxeo Summit Day 2 - Real-time communications with WebRTCVoxeo Summit Day 2 - Real-time communications with WebRTC
Voxeo Summit Day 2 - Real-time communications with WebRTCVoxeo Corp
 
Voxeo Summit Day 2 - Voxeo CXP for business users
Voxeo Summit Day 2 - Voxeo CXP for business usersVoxeo Summit Day 2 - Voxeo CXP for business users
Voxeo Summit Day 2 - Voxeo CXP for business usersVoxeo Corp
 
Voxeo Summit Day 2 - Creating raving fans
Voxeo Summit Day 2 - Creating raving fansVoxeo Summit Day 2 - Creating raving fans
Voxeo Summit Day 2 - Creating raving fansVoxeo Corp
 
Voxeo Summit Day 2 - Advanced CCXML topics
Voxeo Summit Day 2 - Advanced CCXML topicsVoxeo Summit Day 2 - Advanced CCXML topics
Voxeo Summit Day 2 - Advanced CCXML topicsVoxeo Corp
 
Voxeo Summit Day 2 - The science of customer obsession
Voxeo Summit Day 2 - The science of customer obsessionVoxeo Summit Day 2 - The science of customer obsession
Voxeo Summit Day 2 - The science of customer obsessionVoxeo Corp
 
Voxeo Summit Day 1 - Extending your IVR investment to mobile
Voxeo Summit Day 1 - Extending your IVR investment to mobileVoxeo Summit Day 1 - Extending your IVR investment to mobile
Voxeo Summit Day 1 - Extending your IVR investment to mobileVoxeo Corp
 
Voxeo Summit Day 1 - The Art of The Possible
Voxeo Summit Day 1 - The Art of The PossibleVoxeo Summit Day 1 - The Art of The Possible
Voxeo Summit Day 1 - The Art of The PossibleVoxeo Corp
 
Voxeo Summit Day 1 - Prophecy log search
Voxeo Summit Day 1 - Prophecy log searchVoxeo Summit Day 1 - Prophecy log search
Voxeo Summit Day 1 - Prophecy log searchVoxeo Corp
 
Voxeo Summit Day 1 - Customer experience analytics
Voxeo Summit Day 1 - Customer experience analyticsVoxeo Summit Day 1 - Customer experience analytics
Voxeo Summit Day 1 - Customer experience analyticsVoxeo Corp
 
Voxeo Summit Day 1 - Communications-enabled Business Processes (CEBP)
Voxeo Summit Day 1 - Communications-enabled Business Processes (CEBP)Voxeo Summit Day 1 - Communications-enabled Business Processes (CEBP)
Voxeo Summit Day 1 - Communications-enabled Business Processes (CEBP)Voxeo Corp
 
Voxeo Summit Day 1 - A view into the Voxeo cloud
Voxeo Summit Day 1 - A view into the Voxeo cloudVoxeo Summit Day 1 - A view into the Voxeo cloud
Voxeo Summit Day 1 - A view into the Voxeo cloudVoxeo Corp
 
Voxeo Summit Day 1 - Lessons learned from large scale deployments
Voxeo Summit Day 1 - Lessons learned from large scale deploymentsVoxeo Summit Day 1 - Lessons learned from large scale deployments
Voxeo Summit Day 1 - Lessons learned from large scale deploymentsVoxeo Corp
 
Voxeo Jam Session: What's New in Prophecy 11 and VoiceObjects 11?
Voxeo Jam Session: What's New in Prophecy 11 and VoiceObjects 11?Voxeo Jam Session: What's New in Prophecy 11 and VoiceObjects 11?
Voxeo Jam Session: What's New in Prophecy 11 and VoiceObjects 11?Voxeo Corp
 
How Do You Hear Me Now?
How Do You Hear Me Now?How Do You Hear Me Now?
How Do You Hear Me Now?Voxeo Corp
 
IPv6 and How It Impacts Communication Applications
IPv6 and How It Impacts Communication ApplicationsIPv6 and How It Impacts Communication Applications
IPv6 and How It Impacts Communication ApplicationsVoxeo Corp
 

More from Voxeo Corp (20)

Voxeo Summit Day 2 -What's new in CXP 14
Voxeo Summit Day 2 -What's new in CXP 14Voxeo Summit Day 2 -What's new in CXP 14
Voxeo Summit Day 2 -What's new in CXP 14
 
Voxeo Summit Day 2 -Voxeo APIs and SDKs
Voxeo Summit Day 2 -Voxeo APIs and SDKsVoxeo Summit Day 2 -Voxeo APIs and SDKs
Voxeo Summit Day 2 -Voxeo APIs and SDKs
 
Voxeo Summit Day 2 - Voxeo CXP - IVR on Steroids
Voxeo Summit Day 2 - Voxeo CXP - IVR on SteroidsVoxeo Summit Day 2 - Voxeo CXP - IVR on Steroids
Voxeo Summit Day 2 - Voxeo CXP - IVR on Steroids
 
Voxeo Summit Day 2 - Using CXP hotspot analytics
Voxeo Summit Day 2 - Using CXP hotspot analyticsVoxeo Summit Day 2 - Using CXP hotspot analytics
Voxeo Summit Day 2 - Using CXP hotspot analytics
 
Voxeo Summit Day 2 - Securing customer interactions
Voxeo Summit Day 2 - Securing customer interactionsVoxeo Summit Day 2 - Securing customer interactions
Voxeo Summit Day 2 - Securing customer interactions
 
Voxeo Summit Day 2 - Real-time communications with WebRTC
Voxeo Summit Day 2 - Real-time communications with WebRTCVoxeo Summit Day 2 - Real-time communications with WebRTC
Voxeo Summit Day 2 - Real-time communications with WebRTC
 
Voxeo Summit Day 2 - Voxeo CXP for business users
Voxeo Summit Day 2 - Voxeo CXP for business usersVoxeo Summit Day 2 - Voxeo CXP for business users
Voxeo Summit Day 2 - Voxeo CXP for business users
 
Voxeo Summit Day 2 - Creating raving fans
Voxeo Summit Day 2 - Creating raving fansVoxeo Summit Day 2 - Creating raving fans
Voxeo Summit Day 2 - Creating raving fans
 
Voxeo Summit Day 2 - Advanced CCXML topics
Voxeo Summit Day 2 - Advanced CCXML topicsVoxeo Summit Day 2 - Advanced CCXML topics
Voxeo Summit Day 2 - Advanced CCXML topics
 
Voxeo Summit Day 2 - The science of customer obsession
Voxeo Summit Day 2 - The science of customer obsessionVoxeo Summit Day 2 - The science of customer obsession
Voxeo Summit Day 2 - The science of customer obsession
 
Voxeo Summit Day 1 - Extending your IVR investment to mobile
Voxeo Summit Day 1 - Extending your IVR investment to mobileVoxeo Summit Day 1 - Extending your IVR investment to mobile
Voxeo Summit Day 1 - Extending your IVR investment to mobile
 
Voxeo Summit Day 1 - The Art of The Possible
Voxeo Summit Day 1 - The Art of The PossibleVoxeo Summit Day 1 - The Art of The Possible
Voxeo Summit Day 1 - The Art of The Possible
 
Voxeo Summit Day 1 - Prophecy log search
Voxeo Summit Day 1 - Prophecy log searchVoxeo Summit Day 1 - Prophecy log search
Voxeo Summit Day 1 - Prophecy log search
 
Voxeo Summit Day 1 - Customer experience analytics
Voxeo Summit Day 1 - Customer experience analyticsVoxeo Summit Day 1 - Customer experience analytics
Voxeo Summit Day 1 - Customer experience analytics
 
Voxeo Summit Day 1 - Communications-enabled Business Processes (CEBP)
Voxeo Summit Day 1 - Communications-enabled Business Processes (CEBP)Voxeo Summit Day 1 - Communications-enabled Business Processes (CEBP)
Voxeo Summit Day 1 - Communications-enabled Business Processes (CEBP)
 
Voxeo Summit Day 1 - A view into the Voxeo cloud
Voxeo Summit Day 1 - A view into the Voxeo cloudVoxeo Summit Day 1 - A view into the Voxeo cloud
Voxeo Summit Day 1 - A view into the Voxeo cloud
 
Voxeo Summit Day 1 - Lessons learned from large scale deployments
Voxeo Summit Day 1 - Lessons learned from large scale deploymentsVoxeo Summit Day 1 - Lessons learned from large scale deployments
Voxeo Summit Day 1 - Lessons learned from large scale deployments
 
Voxeo Jam Session: What's New in Prophecy 11 and VoiceObjects 11?
Voxeo Jam Session: What's New in Prophecy 11 and VoiceObjects 11?Voxeo Jam Session: What's New in Prophecy 11 and VoiceObjects 11?
Voxeo Jam Session: What's New in Prophecy 11 and VoiceObjects 11?
 
How Do You Hear Me Now?
How Do You Hear Me Now?How Do You Hear Me Now?
How Do You Hear Me Now?
 
IPv6 and How It Impacts Communication Applications
IPv6 and How It Impacts Communication ApplicationsIPv6 and How It Impacts Communication Applications
IPv6 and How It Impacts Communication Applications
 

Recently uploaded

Generative Artificial Intelligence: How generative AI works.pdf
Generative Artificial Intelligence: How generative AI works.pdfGenerative Artificial Intelligence: How generative AI works.pdf
Generative Artificial Intelligence: How generative AI works.pdfIngrid Airi González
 
DevEX - reference for building teams, processes, and platforms
DevEX - reference for building teams, processes, and platformsDevEX - reference for building teams, processes, and platforms
DevEX - reference for building teams, processes, and platformsSergiu Bodiu
 
Passkey Providers and Enabling Portability: FIDO Paris Seminar.pptx
Passkey Providers and Enabling Portability: FIDO Paris Seminar.pptxPasskey Providers and Enabling Portability: FIDO Paris Seminar.pptx
Passkey Providers and Enabling Portability: FIDO Paris Seminar.pptxLoriGlavin3
 
Take control of your SAP testing with UiPath Test Suite
Take control of your SAP testing with UiPath Test SuiteTake control of your SAP testing with UiPath Test Suite
Take control of your SAP testing with UiPath Test SuiteDianaGray10
 
Why device, WIFI, and ISP insights are crucial to supporting remote Microsoft...
Why device, WIFI, and ISP insights are crucial to supporting remote Microsoft...Why device, WIFI, and ISP insights are crucial to supporting remote Microsoft...
Why device, WIFI, and ISP insights are crucial to supporting remote Microsoft...panagenda
 
Sample pptx for embedding into website for demo
Sample pptx for embedding into website for demoSample pptx for embedding into website for demo
Sample pptx for embedding into website for demoHarshalMandlekar2
 
Potential of AI (Generative AI) in Business: Learnings and Insights
Potential of AI (Generative AI) in Business: Learnings and InsightsPotential of AI (Generative AI) in Business: Learnings and Insights
Potential of AI (Generative AI) in Business: Learnings and InsightsRavi Sanghani
 
(How to Program) Paul Deitel, Harvey Deitel-Java How to Program, Early Object...
(How to Program) Paul Deitel, Harvey Deitel-Java How to Program, Early Object...(How to Program) Paul Deitel, Harvey Deitel-Java How to Program, Early Object...
(How to Program) Paul Deitel, Harvey Deitel-Java How to Program, Early Object...AliaaTarek5
 
Generative AI for Technical Writer or Information Developers
Generative AI for Technical Writer or Information DevelopersGenerative AI for Technical Writer or Information Developers
Generative AI for Technical Writer or Information DevelopersRaghuram Pandurangan
 
The Fit for Passkeys for Employee and Consumer Sign-ins: FIDO Paris Seminar.pptx
The Fit for Passkeys for Employee and Consumer Sign-ins: FIDO Paris Seminar.pptxThe Fit for Passkeys for Employee and Consumer Sign-ins: FIDO Paris Seminar.pptx
The Fit for Passkeys for Employee and Consumer Sign-ins: FIDO Paris Seminar.pptxLoriGlavin3
 
UiPath Community: Communication Mining from Zero to Hero
UiPath Community: Communication Mining from Zero to HeroUiPath Community: Communication Mining from Zero to Hero
UiPath Community: Communication Mining from Zero to HeroUiPathCommunity
 
Moving Beyond Passwords: FIDO Paris Seminar.pdf
Moving Beyond Passwords: FIDO Paris Seminar.pdfMoving Beyond Passwords: FIDO Paris Seminar.pdf
Moving Beyond Passwords: FIDO Paris Seminar.pdfLoriGlavin3
 
2024 April Patch Tuesday
2024 April Patch Tuesday2024 April Patch Tuesday
2024 April Patch TuesdayIvanti
 
The Future Roadmap for the Composable Data Stack - Wes McKinney - Data Counci...
The Future Roadmap for the Composable Data Stack - Wes McKinney - Data Counci...The Future Roadmap for the Composable Data Stack - Wes McKinney - Data Counci...
The Future Roadmap for the Composable Data Stack - Wes McKinney - Data Counci...Wes McKinney
 
The State of Passkeys with FIDO Alliance.pptx
The State of Passkeys with FIDO Alliance.pptxThe State of Passkeys with FIDO Alliance.pptx
The State of Passkeys with FIDO Alliance.pptxLoriGlavin3
 
How AI, OpenAI, and ChatGPT impact business and software.
How AI, OpenAI, and ChatGPT impact business and software.How AI, OpenAI, and ChatGPT impact business and software.
How AI, OpenAI, and ChatGPT impact business and software.Curtis Poe
 
A Journey Into the Emotions of Software Developers
A Journey Into the Emotions of Software DevelopersA Journey Into the Emotions of Software Developers
A Journey Into the Emotions of Software DevelopersNicole Novielli
 
Transcript: New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024
Transcript: New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024Transcript: New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024
Transcript: New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024BookNet Canada
 
Assure Ecommerce and Retail Operations Uptime with ThousandEyes
Assure Ecommerce and Retail Operations Uptime with ThousandEyesAssure Ecommerce and Retail Operations Uptime with ThousandEyes
Assure Ecommerce and Retail Operations Uptime with ThousandEyesThousandEyes
 
Arizona Broadband Policy Past, Present, and Future Presentation 3/25/24
Arizona Broadband Policy Past, Present, and Future Presentation 3/25/24Arizona Broadband Policy Past, Present, and Future Presentation 3/25/24
Arizona Broadband Policy Past, Present, and Future Presentation 3/25/24Mark Goldstein
 

Recently uploaded (20)

Generative Artificial Intelligence: How generative AI works.pdf
Generative Artificial Intelligence: How generative AI works.pdfGenerative Artificial Intelligence: How generative AI works.pdf
Generative Artificial Intelligence: How generative AI works.pdf
 
DevEX - reference for building teams, processes, and platforms
DevEX - reference for building teams, processes, and platformsDevEX - reference for building teams, processes, and platforms
DevEX - reference for building teams, processes, and platforms
 
Passkey Providers and Enabling Portability: FIDO Paris Seminar.pptx
Passkey Providers and Enabling Portability: FIDO Paris Seminar.pptxPasskey Providers and Enabling Portability: FIDO Paris Seminar.pptx
Passkey Providers and Enabling Portability: FIDO Paris Seminar.pptx
 
Take control of your SAP testing with UiPath Test Suite
Take control of your SAP testing with UiPath Test SuiteTake control of your SAP testing with UiPath Test Suite
Take control of your SAP testing with UiPath Test Suite
 
Why device, WIFI, and ISP insights are crucial to supporting remote Microsoft...
Why device, WIFI, and ISP insights are crucial to supporting remote Microsoft...Why device, WIFI, and ISP insights are crucial to supporting remote Microsoft...
Why device, WIFI, and ISP insights are crucial to supporting remote Microsoft...
 
Sample pptx for embedding into website for demo
Sample pptx for embedding into website for demoSample pptx for embedding into website for demo
Sample pptx for embedding into website for demo
 
Potential of AI (Generative AI) in Business: Learnings and Insights
Potential of AI (Generative AI) in Business: Learnings and InsightsPotential of AI (Generative AI) in Business: Learnings and Insights
Potential of AI (Generative AI) in Business: Learnings and Insights
 
(How to Program) Paul Deitel, Harvey Deitel-Java How to Program, Early Object...
(How to Program) Paul Deitel, Harvey Deitel-Java How to Program, Early Object...(How to Program) Paul Deitel, Harvey Deitel-Java How to Program, Early Object...
(How to Program) Paul Deitel, Harvey Deitel-Java How to Program, Early Object...
 
Generative AI for Technical Writer or Information Developers
Generative AI for Technical Writer or Information DevelopersGenerative AI for Technical Writer or Information Developers
Generative AI for Technical Writer or Information Developers
 
The Fit for Passkeys for Employee and Consumer Sign-ins: FIDO Paris Seminar.pptx
The Fit for Passkeys for Employee and Consumer Sign-ins: FIDO Paris Seminar.pptxThe Fit for Passkeys for Employee and Consumer Sign-ins: FIDO Paris Seminar.pptx
The Fit for Passkeys for Employee and Consumer Sign-ins: FIDO Paris Seminar.pptx
 
UiPath Community: Communication Mining from Zero to Hero
UiPath Community: Communication Mining from Zero to HeroUiPath Community: Communication Mining from Zero to Hero
UiPath Community: Communication Mining from Zero to Hero
 
Moving Beyond Passwords: FIDO Paris Seminar.pdf
Moving Beyond Passwords: FIDO Paris Seminar.pdfMoving Beyond Passwords: FIDO Paris Seminar.pdf
Moving Beyond Passwords: FIDO Paris Seminar.pdf
 
2024 April Patch Tuesday
2024 April Patch Tuesday2024 April Patch Tuesday
2024 April Patch Tuesday
 
The Future Roadmap for the Composable Data Stack - Wes McKinney - Data Counci...
The Future Roadmap for the Composable Data Stack - Wes McKinney - Data Counci...The Future Roadmap for the Composable Data Stack - Wes McKinney - Data Counci...
The Future Roadmap for the Composable Data Stack - Wes McKinney - Data Counci...
 
The State of Passkeys with FIDO Alliance.pptx
The State of Passkeys with FIDO Alliance.pptxThe State of Passkeys with FIDO Alliance.pptx
The State of Passkeys with FIDO Alliance.pptx
 
How AI, OpenAI, and ChatGPT impact business and software.
How AI, OpenAI, and ChatGPT impact business and software.How AI, OpenAI, and ChatGPT impact business and software.
How AI, OpenAI, and ChatGPT impact business and software.
 
A Journey Into the Emotions of Software Developers
A Journey Into the Emotions of Software DevelopersA Journey Into the Emotions of Software Developers
A Journey Into the Emotions of Software Developers
 
Transcript: New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024
Transcript: New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024Transcript: New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024
Transcript: New from BookNet Canada for 2024: Loan Stars - Tech Forum 2024
 
Assure Ecommerce and Retail Operations Uptime with ThousandEyes
Assure Ecommerce and Retail Operations Uptime with ThousandEyesAssure Ecommerce and Retail Operations Uptime with ThousandEyes
Assure Ecommerce and Retail Operations Uptime with ThousandEyes
 
Arizona Broadband Policy Past, Present, and Future Presentation 3/25/24
Arizona Broadband Policy Past, Present, and Future Presentation 3/25/24Arizona Broadband Policy Past, Present, and Future Presentation 3/25/24
Arizona Broadband Policy Past, Present, and Future Presentation 3/25/24
 

JavaOne - A Sip Of Java - RJ Auburn

  • 1. Taking a SIP of Java RJ Auburn Voxeo Corporation Chief Technology Officer
  • 3. Sucks 3
  • 7. This is not how it should be... 7
  • 8. Simple 8
  • 10. Open 10
  • 11. So what are the layers? 11
  • 12. Application API XML Tools Platform 12
  • 13. Application Application API XML Tools Platform 13
  • 14. Application API XML Tools Platform 14
  • 15. Application API XML Tools Platform 15
  • 16. Application API XML Tools Platform 16
  • 18. Call Control vs Media > Phone systems often are split into two components: Signaling and Media > Signaling handles the setup and tear-down of sessions and phone calls. > Media is responsible for the transport voice path 18
  • 19. Media vs Call Control in the PSTN - SIP Proxy Proxy SIP A B SIP SIP Alice RTP Bob 19
  • 20. Media vs Call Control in the PSTN - SS7 SCP SCP SS7 A B SS7 7 SS Alice Switched TDM Media Bob 20
  • 21. Media vs Call Control in the PSTN - ISDN D Channel (q.931) Signaling Dev Dev A B B Channels (23) Media 21
  • 22. All this means is the APIʼs and standards for media vs call control tend to be different. 22
  • 23. So now for a bit about SIP (Call Control) 23
  • 24. SIP > Session Initiation Protocol (SIP) defines how to establish a communication session between two endpoints > Primarily used for voice, but can for IM or virtually any other protocol > Almost always used in client/server configuration with quot;SIP proxiesquot; in control of quot;SIP endpointsquot; • Work going on in P2PSIP - see www.p2psip.org > Text-based protocol, originally modeled on HTTP 24
  • 25. SIP Communication INVITE Alice 180 RINGING Bob 200 OK ACK RTP (voice) BYE 200 OK 25
  • 26. Major SIP Methods > INVITE > BYE > REFER > REGISTER > SUBSCRIBE > NOTIFY oh ya... > INFO (wait, we are not supposed to talk about this one) 26
  • 27. Response Codes > 1xx - Provisional > 2xx - All is good. Final > 3xx - Redirects > 4/5/6xx - Errors 27
  • 28. SIP Resources > Internet Engineering Task Force (IETF) • RFC 3261 • Hitchhikerʼs Guide to SIP > Open Source Info • VoIP Info Wiki: www.voip-info.org > Industry Sites • SIP Forum: www.sipforum.org • SIP Foundry: www.sipfoundry.org 28
  • 29. So lets talk about... 29
  • 30. Religion 30
  • 31. Religion 31
  • 32. XML 32
  • 34. VoiceXML > Language created by the W3C to model computer human dialogs. > Supports speech and touchtone. > Built around a form filling model called the FIA. > Voice equivalent to HTML. > Focused on dialogs. Very limited call control. > http://www.w3.org/TR/voicexml/ 34
  • 35. CCXML > Call Control XML (CCXML) is the W3C standard for call control using XML > Sister standard to VoiceXML > Integrates with VoiceXML for dialog control > Provides a framework for issuing call control commands and handling call control events > http://www.w3.org/TR/ccxml/ 35
  • 36. VoiceXML and CCXML Architecture ASR Phone CCXML VoiceXML mrcp sip sip TTS rtp 36
  • 38. It has taken over the Enterprise... 38
  • 39. How about some code? 39
  • 40. Sample CCXML/VoiceXML application. > Caller dials in to the application > Caller is bridged to the subscriber > Results of the call attempt are posted to Twitter via their REST API 40
  • 41. start isRJ() yes no prompt for dest play twitter status call dest call rj’s cell end
  • 42. Call router + Twitter <?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?> <ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;> <var name=quot;statequot; expr=quot;'init'quot;/> <var name=quot;incomingcallquot;/> <eventprocessor statevariable=quot;statequot;> <transition event=quot;connection.alertingquot; state=quot;initquot;> <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/> <accept/> </transition> <transition event=quot;connection.connectedquot; state=quot;initquot; cond=quot;event$.connection.remote=='tel:+18315551234'quot;> <assign name=quot;statequot; expr=quot;'rjconnected'quot;/> <dialogstart src=quot;'rj.vxml'quot; </transition> <transition event=quot;connection.connectedquot; state=quot;initquot;> <assign name=quot;statequot; expr=quot;'callconnected'quot;/> <dialogstart src=quot;'caller.vxml'quot; </transition> <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;> <assign name=quot;statequot; expr=quot;'calling'quot;/> <createcall dest=quot;'tel:+18315551234'quot;/> </transition> <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;> <assign name=quot;statequot; expr=quot;'calling'quot;/> <createcall dest=quot;event$.values.destquot;/> </transition> <transition event=quot;connection.connectedquot; state=quot;callingquot;> <assign name=quot;statequot; expr=quot;'connected'quot;/> <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/> </transition> <transition event=quot;connection.failedquot; state=quot;callingquot;> <exit/> </transition> <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;> <exit/> </transition> </eventprocessor> </ccxml> 42
  • 43. Call router + Twitter <?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?> <ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;> <var name=quot;statequot; expr=quot;'init'quot;/> <var name=quot;incomingcallquot;/> <eventprocessor statevariable=quot;statequot;> <transition event=quot;connection.alertingquot; state=quot;initquot;> <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/> <accept/> </transition> <transition event=quot;connection.connectedquot; state=quot;initquot; cond=quot;event$.connection.remote=='tel:+18315551234'quot;> <assign name=quot;statequot; expr=quot;'rjconnected'quot;/> <dialogstart src=quot;'rj.vxml'quot; </transition> <transition event=quot;connection.connectedquot; state=quot;initquot;> <assign name=quot;statequot; expr=quot;'callconnected'quot;/> <dialogstart src=quot;'caller.vxml'quot; </transition> <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;> <assign name=quot;statequot; expr=quot;'calling'quot;/> <createcall dest=quot;'tel:+18315551234'quot;/> </transition> <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;> <assign name=quot;statequot; expr=quot;'calling'quot;/> <createcall dest=quot;event$.values.destquot;/> </transition> <transition event=quot;connection.connectedquot; state=quot;callingquot;> <assign name=quot;statequot; expr=quot;'connected'quot;/> <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/> </transition> <transition event=quot;connection.failedquot; state=quot;callingquot;> <exit/> </transition> <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;> <exit/> </transition> </eventprocessor> </ccxml> 43
  • 44. Call router + Twitter <?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?> <ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;> <var name=quot;statequot; expr=quot;'init'quot;/> <var name=quot;incomingcallquot;/> <eventprocessor statevariable=quot;statequot;> <transition event=quot;connection.alertingquot; state=quot;initquot;> <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/> <accept/> </transition> <transition event=quot;connection.connectedquot; state=quot;initquot; cond=quot;event$.connection.remote=='tel:+18315551234'quot;> <assign name=quot;statequot; expr=quot;'rjconnected'quot;/> <dialogstart src=quot;'rj.vxml'quot; </transition> <transition event=quot;connection.connectedquot; state=quot;initquot;> <?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?> <assign name=quot;statequot; expr=quot;'callconnected'quot;/> <dialogstart src=quot;'caller.vxml'quot; <ccxml version=quot;1.0quot; </transition> <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;> <assign xmlns=quot;http://www.w3.org/2002/09/ccxmlquot;> name=quot;statequot; expr=quot;'calling'quot;/> <createcall dest=quot;'tel:+18315551234'quot;/> </ccxml> </transition> <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;> <assign name=quot;statequot; expr=quot;'calling'quot;/> <createcall dest=quot;event$.values.destquot;/> </transition> <transition event=quot;connection.connectedquot; state=quot;callingquot;> <assign name=quot;statequot; expr=quot;'connected'quot;/> <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/> </transition> <transition event=quot;connection.failedquot; state=quot;callingquot;> <exit/> </transition> <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;> <exit/> </transition> </eventprocessor> </ccxml> 44
  • 45. Call router + Twitter <?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?> <ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;> <var name=quot;statequot; expr=quot;'init'quot;/> <var name=quot;incomingcallquot;/> <eventprocessor statevariable=quot;statequot;> <transition event=quot;connection.alertingquot; state=quot;initquot;> <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/> <accept/> </transition> <transition event=quot;connection.connectedquot; state=quot;initquot; cond=quot;event$.connection.remote=='tel:+18315551234'quot;> <assign name=quot;statequot; expr=quot;'rjconnected'quot;/> <dialogstart src=quot;'rj.vxml'quot; </transition> <transition event=quot;connection.connectedquot; state=quot;initquot;> <assign name=quot;statequot; expr=quot;'callconnected'quot;/> <dialogstart src=quot;'caller.vxml'quot; </transition> <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;> <assign name=quot;statequot; expr=quot;'calling'quot;/> <createcall dest=quot;'tel:+18315551234'quot;/> </transition> <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;> <assign name=quot;statequot; expr=quot;'calling'quot;/> <createcall dest=quot;event$.values.destquot;/> </transition> <transition event=quot;connection.connectedquot; state=quot;callingquot;> <assign name=quot;statequot; expr=quot;'connected'quot;/> <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/> </transition> <transition event=quot;connection.failedquot; state=quot;callingquot;> <exit/> </transition> <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;> <exit/> </transition> </eventprocessor> </ccxml> 45
  • 46. Call router + Twitter <?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?> <ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;> <var name=quot;statequot; expr=quot;'init'quot;/> <var name=quot;incomingcallquot;/> <eventprocessor statevariable=quot;statequot;> <transition event=quot;connection.alertingquot; state=quot;initquot;> <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/> <accept/> </transition> <transition event=quot;connection.connectedquot; state=quot;initquot; cond=quot;event$.connection.remote=='tel:+18315551234'quot;> <assign name=quot;statequot; expr=quot;'rjconnected'quot;/> <dialogstart src=quot;'rj.vxml'quot; </transition> <transition event=quot;connection.connectedquot; state=quot;initquot;> <assign name=quot;statequot; expr=quot;'callconnected'quot;/> <dialogstart src=quot;'caller.vxml'quot; expr=quot;'init'quot;/> <var name=quot;statequot; </transition> <transition<var name=quot;incomingcallquot;/> event=quot;dialog.exitquot; state=quot;callconnectedquot;> <assign name=quot;statequot; expr=quot;'calling'quot;/> <eventprocessor statevariable=quot;statequot;> <createcall dest=quot;'tel:+18315551234'quot;/> </transition> <transition</eventprocessor> event=quot;dialog.exitquot; state=quot;rjconnectedquot;> <assign name=quot;statequot; expr=quot;'calling'quot;/> <createcall dest=quot;event$.values.destquot;/> </transition> <transition event=quot;connection.connectedquot; state=quot;callingquot;> <assign name=quot;statequot; expr=quot;'connected'quot;/> <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/> </transition> <transition event=quot;connection.failedquot; state=quot;callingquot;> <exit/> </transition> <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;> <exit/> </transition> </eventprocessor> </ccxml> 46
  • 47. Call router + Twitter <?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?> <ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;> <var name=quot;statequot; expr=quot;'init'quot;/> <var name=quot;incomingcallquot;/> <eventprocessor statevariable=quot;statequot;> <transition event=quot;connection.alertingquot; state=quot;initquot;> <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/> <accept/> </transition> <transition event=quot;connection.connectedquot; state=quot;initquot; cond=quot;event$.connection.remote=='tel:+18315551234'quot;> <assign name=quot;statequot; expr=quot;'rjconnected'quot;/> <dialogstart src=quot;'rj.vxml'quot; </transition> <transition event=quot;connection.connectedquot; state=quot;initquot;> <assign name=quot;statequot; expr=quot;'callconnected'quot;/> <dialogstart src=quot;'caller.vxml'quot; </transition> <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;> <assign name=quot;statequot; expr=quot;'calling'quot;/> <createcall dest=quot;'tel:+18315551234'quot;/> </transition> <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;> <assign name=quot;statequot; expr=quot;'calling'quot;/> <createcall dest=quot;event$.values.destquot;/> </transition> <transition event=quot;connection.connectedquot; state=quot;callingquot;> <assign name=quot;statequot; expr=quot;'connected'quot;/> <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/> </transition> <transition event=quot;connection.failedquot; state=quot;callingquot;> <exit/> </transition> <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;> <exit/> </transition> </eventprocessor> </ccxml> 47
  • 48. Call router + Twitter <?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?> <ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;> <var name=quot;statequot; expr=quot;'init'quot;/> <var name=quot;incomingcallquot;/> <eventprocessor statevariable=quot;statequot;> <transition event=quot;connection.alertingquot; state=quot;initquot;> <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/> <accept/> </transition> <transition event=quot;connection.connectedquot; state=quot;initquot; cond=quot;event$.connection.remote=='tel:+18315551234'quot;> <assign name=quot;statequot; expr=quot;'rjconnected'quot;/> <dialogstart src=quot;'rj.vxml'quot; </transition> <transition event=quot;connection.connectedquot; state=quot;initquot;> <assign name=quot;statequot; expr=quot;'callconnected'quot;/> <transition event=quot;connection.alertingquot; state=quot;initquot;> <dialogstart src=quot;'caller.vxml'quot; <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/> </transition> <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;> <accept/> dest=quot;'tel:+18315551234'quot;/> <assign name=quot;statequot; expr=quot;'calling'quot;/> <createcall </transition> </transition> <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;> <assign name=quot;statequot; expr=quot;'calling'quot;/> <createcall dest=quot;event$.values.destquot;/> </transition> <transition event=quot;connection.connectedquot; state=quot;callingquot;> <assign name=quot;statequot; expr=quot;'connected'quot;/> <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/> </transition> <transition event=quot;connection.failedquot; state=quot;callingquot;> <exit/> </transition> <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;> <exit/> </transition> </eventprocessor> </ccxml> 48
  • 49. Call router + Twitter <?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?> <ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;> <var name=quot;statequot; expr=quot;'init'quot;/> <var name=quot;incomingcallquot;/> <eventprocessor statevariable=quot;statequot;> <transition event=quot;connection.alertingquot; state=quot;initquot;> <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/> <accept/> </transition> <transition event=quot;connection.connectedquot; state=quot;initquot; cond=quot;event$.connection.remote=='tel:+18315551234'quot;> <assign name=quot;statequot; expr=quot;'rjconnected'quot;/> <dialogstart src=quot;'rj.vxml'quot; </transition> <transition event=quot;connection.connectedquot; state=quot;initquot;> <assign name=quot;statequot; expr=quot;'callconnected'quot;/> <dialogstart src=quot;'caller.vxml'quot; </transition> <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;> <assign name=quot;statequot; expr=quot;'calling'quot;/> <createcall dest=quot;'tel:+18315551234'quot;/> </transition> <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;> <assign name=quot;statequot; expr=quot;'calling'quot;/> <createcall dest=quot;event$.values.destquot;/> </transition> <transition event=quot;connection.connectedquot; state=quot;callingquot;> <assign name=quot;statequot; expr=quot;'connected'quot;/> <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/> </transition> <transition event=quot;connection.failedquot; state=quot;callingquot;> <exit/> </transition> <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;> <exit/> </transition> </eventprocessor> </ccxml> 49
  • 50. Call router + Twitter <?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?> <ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;> <var name=quot;statequot; expr=quot;'init'quot;/> <var name=quot;incomingcallquot;/> <eventprocessor statevariable=quot;statequot;> <transition event=quot;connection.alertingquot; state=quot;initquot;> <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/> <accept/> </transition> <transition event=quot;connection.connectedquot; state=quot;initquot; cond=quot;event$.connection.remote=='tel:+18315551234'quot;> <assign name=quot;statequot; expr=quot;'rjconnected'quot;/> <dialogstart src=quot;'rj.vxml'quot; </transition> <transition event=quot;connection.connectedquot; state=quot;initquot;> <transition event=quot;connection.connectedquot; state=quot;initquot; <assign name=quot;statequot; expr=quot;'callconnected'quot;/> <dialogstart src=quot;'caller.vxml'quot; cond=quot;event$.connection.remote=='tel:+18315551234'quot;> </transition> <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;> <assign name=quot;statequot; expr=quot;'calling'quot;/> <assign name=quot;statequot; expr=quot;'rjconnected'quot;/> <createcall dest=quot;'tel:+18315551234'quot;/> <dialogstart src=quot;'rj.vxml'quot; </transition> <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;> </transition> <assign name=quot;statequot; expr=quot;'calling'quot;/> <createcall dest=quot;event$.values.destquot;/> </transition> <transition event=quot;connection.connectedquot; state=quot;callingquot;> <assign name=quot;statequot; expr=quot;'connected'quot;/> <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/> </transition> <transition event=quot;connection.failedquot; state=quot;callingquot;> <exit/> </transition> <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;> <exit/> </transition> </eventprocessor> </ccxml> 50
  • 51. Call router + Twitter <?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?> <ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;> <var name=quot;statequot; expr=quot;'init'quot;/> <var name=quot;incomingcallquot;/> <var name=quot;tURLquot; expr=quot;'http://zscgeek:password@twitter.com/statuses/update.xml'quot;/> <eventprocessor statevariable=quot;statequot;> <transition event=quot;connection.alertingquot; state=quot;initquot;> <accept/> </transition> <transition event=quot;connection.connectedquot; state=quot;initquot;> <?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?> <assign name=quot;statequot; expr=quot;'calling'quot;/> <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/> <vxml xmlns=quot;http://www.w3.org/2001/vxmlquot; version=quot;2.1quot;> <createcall dest=quot;'tel:+18312392883'quot;/> </transition> <form> <transition event=quot;connection.connectedquot; state=quot;callingquot;> <assign name=quot;statequot; expr=quot;'connected'quot;/> <field name=quot;destquot; type=quot;digits?length=10quot;> <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/> <var name=quot;statusquot; expr=quot;'RJ is on the phone'quot;/> <send <prompt>Welcome RJ. Please enter the phone targettype=quot;'basichttp'quot; name=quot;'update'quot; target=quot;tURLquot; namelist=quot;statusquot;/> </transition> number you wish to reach.</prompt> <transition event=quot;connection.failedquot; state=quot;callingquot;> <filled> <assign name=quot;statequot; expr=quot;'done'quot;/> <var name=quot;statusquot; expr=quot;'RJ is not answering his phone'quot;/> <send <exit namelist=quot;destquot;/> targettype=quot;'basichttp'quot; name=quot;'update'quot; target=quot;tURLquot; namelist=quot;statusquot;/> </filled> </transition> </field> <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;> <assign name=quot;statequot; expr=quot;'done'quot;/> </form> <var name=quot;statusquot; expr=quot;'RJ is off the phone'quot;/> <send targettype=quot;'basichttp'quot; name=quot;'update'quot; </vxml> target=quot;tURLquot; namelist=quot;statusquot;/> </transition> <transition event=quot;send.successfulquot; state=quot;donequot;> <exit/> </transition> </eventprocessor> </ccxml> 51
  • 52. Call router + Twitter <?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?> <ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;> <var name=quot;statequot; expr=quot;'init'quot;/> <var name=quot;incomingcallquot;/> <eventprocessor statevariable=quot;statequot;> <transition event=quot;connection.alertingquot; state=quot;initquot;> <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/> <accept/> </transition> <transition event=quot;connection.connectedquot; state=quot;initquot; cond=quot;event$.connection.remote=='tel:+18315551234'quot;> <assign name=quot;statequot; expr=quot;'rjconnected'quot;/> <dialogstart src=quot;'rj.vxml'quot; </transition> <transition event=quot;connection.connectedquot; state=quot;initquot;> <assign name=quot;statequot; expr=quot;'callconnected'quot;/> <dialogstart src=quot;'caller.vxml'quot; </transition> <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;> <assign name=quot;statequot; expr=quot;'calling'quot;/> <createcall dest=quot;'tel:+18315551234'quot;/> </transition> <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;> <assign name=quot;statequot; expr=quot;'calling'quot;/> <createcall dest=quot;event$.values.destquot;/> </transition> <transition event=quot;connection.connectedquot; state=quot;callingquot;> <assign name=quot;statequot; expr=quot;'connected'quot;/> <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/> </transition> <transition event=quot;connection.failedquot; state=quot;callingquot;> <exit/> </transition> <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;> <exit/> </transition> </eventprocessor> </ccxml> 52
  • 53. Call router + Twitter <?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?> <ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;> <var name=quot;statequot; expr=quot;'init'quot;/> <var name=quot;incomingcallquot;/> <eventprocessor statevariable=quot;statequot;> <transition event=quot;connection.alertingquot; state=quot;initquot;> <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/> <accept/> </transition> <transition event=quot;connection.connectedquot; state=quot;initquot; cond=quot;event$.connection.remote=='tel:+18315551234'quot;> <assign name=quot;statequot; expr=quot;'rjconnected'quot;/> <dialogstart src=quot;'rj.vxml'quot; <transition event=quot;connection.connectedquot; state=quot;initquot;> </transition> <assign name=quot;statequot; expr=quot;'callconnected'quot;/> <transition name=quot;statequot; expr=quot;'callconnected'quot;/> <assign event=quot;connection.connectedquot; state=quot;initquot;> <dialogstart src=quot;'caller.vxml'quot; <dialogstart src=quot;'caller.vxml'quot; </transition> </transition> <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;> <assign name=quot;statequot; expr=quot;'calling'quot;/> <createcall dest=quot;'tel:+18315551234'quot;/> </transition> <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;> <assign name=quot;statequot; expr=quot;'calling'quot;/> <createcall dest=quot;event$.values.destquot;/> </transition> <transition event=quot;connection.connectedquot; state=quot;callingquot;> <assign name=quot;statequot; expr=quot;'connected'quot;/> <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/> </transition> <transition event=quot;connection.failedquot; state=quot;callingquot;> <exit/> </transition> <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;> <exit/> </transition> </eventprocessor> </ccxml> 53
  • 54. Call router + Twitter <?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?> <ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;> <var name=quot;statequot; expr=quot;'init'quot;/> <var name=quot;incomingcallquot;/> <var name=quot;tURLquot; expr=quot;'http://zscgeek:password@twitter.com/statuses/update.xml'quot;/> <eventprocessor statevariable=quot;statequot;> <transition event=quot;connection.alertingquot; state=quot;initquot;> <?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?> <accept/> </transition> <vxml xmlns=quot;http://www.w3.org/2001/vxmlquot; version=quot;2.1quot;> <transition event=quot;connection.connectedquot; state=quot;initquot;> <assign name=quot;statequot; expr=quot;'calling'quot;/> <form> name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/> <assign <createcall dest=quot;'tel:+18312392883'quot;/> <block> </transition> <transition event=quot;connection.connectedquot; state=quot;callingquot;> <data src=quot;http://twitter.com/statuses/ <assign name=quot;statequot; expr=quot;'connected'quot;/> <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/> user_timeline.xml?screen_name=zscgeekquot; <var name=quot;statusquot; expr=quot;'RJ is on the phone'quot;/> <send targettype=quot;'basichttp'quot; name=quot;'update'quot; name=quot;twitterquot; ecmaxmltype=quot;e4xquot; /> target=quot;tURLquot; namelist=quot;statusquot;/> </transition> <prompt>Thank you for calling RJ. <transition event=quot;connection.failedquot; state=quot;callingquot;> <assign We will connect you now. name=quot;statequot; expr=quot;'done'quot;/> <var name=quot;statusquot; expr=quot;'RJ is not answering his phone'quot;/> His twitter status is <send targettype=quot;'basichttp'quot; name=quot;'update'quot; target=quot;tURLquot; namelist=quot;statusquot;/> <value expr=quot;twitter.statuses.status[0].textquot;/> </transition> <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;> </prompt> <assign name=quot;statequot; expr=quot;'done'quot;/> <var name=quot;statusquot; expr=quot;'RJ is off the phone'quot;/> </block> <send targettype=quot;'basichttp'quot; name=quot;'update'quot; target=quot;tURLquot; namelist=quot;statusquot;/> </form> event=quot;send.successfulquot; state=quot;donequot;> </transition> <transition </vxml> <exit/> </transition> </eventprocessor> </ccxml> 54
  • 55. Call router + Twitter <?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?> <ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;> <var name=quot;statequot; expr=quot;'init'quot;/> <var name=quot;incomingcallquot;/> <eventprocessor statevariable=quot;statequot;> <transition event=quot;connection.alertingquot; state=quot;initquot;> <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/> <accept/> </transition> <transition event=quot;connection.connectedquot; state=quot;initquot; cond=quot;event$.connection.remote=='tel:+18315551234'quot;> <assign name=quot;statequot; expr=quot;'rjconnected'quot;/> <dialogstart src=quot;'rj.vxml'quot; </transition> <transition event=quot;connection.connectedquot; state=quot;initquot;> <assign name=quot;statequot; expr=quot;'callconnected'quot;/> <dialogstart src=quot;'caller.vxml'quot; </transition> <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;> <assign name=quot;statequot; expr=quot;'calling'quot;/> <createcall dest=quot;'tel:+18315551234'quot;/> </transition> <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;> <assign name=quot;statequot; expr=quot;'calling'quot;/> <createcall dest=quot;event$.values.destquot;/> </transition> <transition event=quot;connection.connectedquot; state=quot;callingquot;> <assign name=quot;statequot; expr=quot;'connected'quot;/> <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/> </transition> <transition event=quot;connection.failedquot; state=quot;callingquot;> <exit/> </transition> <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;> <exit/> </transition> </eventprocessor> </ccxml> 55
  • 56. Call router + Twitter <?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?> <ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;> <var name=quot;statequot; expr=quot;'init'quot;/> <var name=quot;incomingcallquot;/> <eventprocessor statevariable=quot;statequot;> <transition event=quot;connection.alertingquot; state=quot;initquot;> <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/> <accept/> </transition> <transition event=quot;connection.connectedquot; state=quot;initquot; cond=quot;event$.connection.remote=='tel:+18315551234'quot;> <assign name=quot;statequot; expr=quot;'rjconnected'quot;/> <dialogstart src=quot;'rj.vxml'quot; </transition> <transition event=quot;connection.connectedquot; state=quot;initquot;> <assign name=quot;statequot; expr=quot;'callconnected'quot;/> <dialogstart src=quot;'caller.vxml'quot; </transition> <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;> <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;> <assign name=quot;statequot; expr=quot;'calling'quot;/> <createcall dest=quot;'tel:+18315551234'quot;/> <assign name=quot;statequot; expr=quot;'calling'quot;/> </transition> <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;> <createcall dest=quot;'tel:+18315551234'quot;/> <assign name=quot;statequot; expr=quot;'calling'quot;/> </transition> dest=quot;event$.values.destquot;/> <createcall </transition> <transition event=quot;connection.connectedquot; state=quot;callingquot;> <assign name=quot;statequot; expr=quot;'connected'quot;/> <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/> </transition> <transition event=quot;connection.failedquot; state=quot;callingquot;> <exit/> </transition> <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;> <exit/> </transition> </eventprocessor> </ccxml> 56
  • 57. Call router + Twitter <?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?> <ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;> <var name=quot;statequot; expr=quot;'init'quot;/> <var name=quot;incomingcallquot;/> <eventprocessor statevariable=quot;statequot;> <transition event=quot;connection.alertingquot; state=quot;initquot;> <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/> <accept/> </transition> <transition event=quot;connection.connectedquot; state=quot;initquot; cond=quot;event$.connection.remote=='tel:+18315551234'quot;> <assign name=quot;statequot; expr=quot;'rjconnected'quot;/> <dialogstart src=quot;'rj.vxml'quot; </transition> <transition event=quot;connection.connectedquot; state=quot;initquot;> <assign name=quot;statequot; expr=quot;'callconnected'quot;/> <dialogstart src=quot;'caller.vxml'quot; </transition> <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;> <assign name=quot;statequot; expr=quot;'calling'quot;/> <createcall dest=quot;'tel:+18315551234'quot;/> </transition> <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;> <assign name=quot;statequot; expr=quot;'calling'quot;/> <createcall dest=quot;event$.values.destquot;/> </transition> <transition event=quot;connection.connectedquot; state=quot;callingquot;> <assign name=quot;statequot; expr=quot;'connected'quot;/> <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/> </transition> <transition event=quot;connection.failedquot; state=quot;callingquot;> <exit/> </transition> <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;> <exit/> </transition> </eventprocessor> </ccxml> 57
  • 58. Call router + Twitter <?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?> <ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;> <var name=quot;statequot; expr=quot;'init'quot;/> <var name=quot;incomingcallquot;/> <eventprocessor statevariable=quot;statequot;> <transition event=quot;connection.alertingquot; state=quot;initquot;> <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/> <accept/> </transition> <transition event=quot;connection.connectedquot; state=quot;initquot; cond=quot;event$.connection.remote=='tel:+18315551234'quot;> <assign name=quot;statequot; expr=quot;'rjconnected'quot;/> <dialogstart src=quot;'rj.vxml'quot; </transition> <transition event=quot;connection.connectedquot; state=quot;initquot;> <assign name=quot;statequot; expr=quot;'callconnected'quot;/> <dialogstart src=quot;'caller.vxml'quot; </transition> <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;> <transition name=quot;statequot; expr=quot;'calling'quot;/> <assign event=quot;dialog.exitquot; state=quot;rjconnectedquot;> <createcall dest=quot;'tel:+18315551234'quot;/> <assign name=quot;statequot; expr=quot;'calling'quot;/> </transition> <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;> <createcall dest=quot;event$.values.destquot;/> <assign name=quot;statequot; expr=quot;'calling'quot;/> </transition> dest=quot;event$.values.destquot;/> <createcall </transition> <transition event=quot;connection.connectedquot; state=quot;callingquot;> <assign name=quot;statequot; expr=quot;'connected'quot;/> <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/> </transition> <transition event=quot;connection.failedquot; state=quot;callingquot;> <exit/> </transition> <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;> <exit/> </transition> </eventprocessor> </ccxml> 58
  • 59. Call router + Twitter <?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?> <ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;> <var name=quot;statequot; expr=quot;'init'quot;/> <var name=quot;incomingcallquot;/> <eventprocessor statevariable=quot;statequot;> <transition event=quot;connection.alertingquot; state=quot;initquot;> <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/> <accept/> </transition> <transition event=quot;connection.connectedquot; state=quot;initquot; cond=quot;event$.connection.remote=='tel:+18315551234'quot;> <assign name=quot;statequot; expr=quot;'rjconnected'quot;/> <dialogstart src=quot;'rj.vxml'quot; </transition> <transition event=quot;connection.connectedquot; state=quot;initquot;> <assign name=quot;statequot; expr=quot;'callconnected'quot;/> <dialogstart src=quot;'caller.vxml'quot; </transition> <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;> <assign name=quot;statequot; expr=quot;'calling'quot;/> <createcall dest=quot;'tel:+18315551234'quot;/> </transition> <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;> <assign name=quot;statequot; expr=quot;'calling'quot;/> <createcall dest=quot;event$.values.destquot;/> </transition> <transition event=quot;connection.connectedquot; state=quot;callingquot;> <assign name=quot;statequot; expr=quot;'connected'quot;/> <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/> </transition> <transition event=quot;connection.failedquot; state=quot;callingquot;> <exit/> </transition> <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;> <exit/> </transition> </eventprocessor> </ccxml> 59
  • 60. Call router + Twitter <?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?> <ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;> <var name=quot;statequot; expr=quot;'init'quot;/> <var name=quot;incomingcallquot;/> <eventprocessor statevariable=quot;statequot;> <transition event=quot;connection.alertingquot; state=quot;initquot;> <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/> <accept/> </transition> <transition event=quot;connection.connectedquot; state=quot;initquot; cond=quot;event$.connection.remote=='tel:+18315551234'quot;> <assign name=quot;statequot; expr=quot;'rjconnected'quot;/> <dialogstart src=quot;'rj.vxml'quot; </transition> <transition event=quot;connection.connectedquot; state=quot;initquot;> <assign name=quot;statequot; expr=quot;'callconnected'quot;/> <dialogstart src=quot;'caller.vxml'quot; </transition> <transition event=quot;connection.connectedquot; <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;> state=quot;callingquot;> expr=quot;'calling'quot;/> <assign name=quot;statequot; <createcall dest=quot;'tel:+18315551234'quot;/> </transition> <transition event=quot;dialog.exitquot; expr=quot;'connected'quot;/> <assign name=quot;statequot; state=quot;rjconnectedquot;> <assign name=quot;statequot; expr=quot;'calling'quot;/> <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/> <createcall dest=quot;event$.values.destquot;/> </transition> </transition> <transition event=quot;connection.connectedquot; state=quot;callingquot;> <assign name=quot;statequot; expr=quot;'connected'quot;/> <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/> </transition> <transition event=quot;connection.failedquot; state=quot;callingquot;> <exit/> </transition> <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;> <exit/> </transition> </eventprocessor> </ccxml> 60
  • 61. Call router + Twitter <?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?> <ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;> <var name=quot;statequot; expr=quot;'init'quot;/> <var name=quot;incomingcallquot;/> <eventprocessor statevariable=quot;statequot;> <transition event=quot;connection.alertingquot; state=quot;initquot;> <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/> <accept/> </transition> <transition event=quot;connection.connectedquot; state=quot;initquot; cond=quot;event$.connection.remote=='tel:+18315551234'quot;> <assign name=quot;statequot; expr=quot;'rjconnected'quot;/> <dialogstart src=quot;'rj.vxml'quot; </transition> <transition event=quot;connection.connectedquot; state=quot;initquot;> <assign name=quot;statequot; expr=quot;'callconnected'quot;/> <dialogstart src=quot;'caller.vxml'quot; </transition> <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;> <assign name=quot;statequot; expr=quot;'calling'quot;/> <createcall dest=quot;'tel:+18315551234'quot;/> </transition> <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;> <assign name=quot;statequot; expr=quot;'calling'quot;/> <createcall dest=quot;event$.values.destquot;/> </transition> <transition event=quot;connection.connectedquot; state=quot;callingquot;> <assign name=quot;statequot; expr=quot;'connected'quot;/> <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/> </transition> <transition event=quot;connection.failedquot; state=quot;callingquot;> <exit/> </transition> <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;> <exit/> </transition> </eventprocessor> </ccxml> 61
  • 62. Call router + Twitter <?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?> <ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;> <var name=quot;statequot; expr=quot;'init'quot;/> <var name=quot;incomingcallquot;/> <eventprocessor statevariable=quot;statequot;> <transition event=quot;connection.alertingquot; state=quot;initquot;> <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/> <accept/> </transition> <transition event=quot;connection.connectedquot; state=quot;initquot; cond=quot;event$.connection.remote=='tel:+18315551234'quot;> <assign name=quot;statequot; expr=quot;'rjconnected'quot;/> <dialogstart src=quot;'rj.vxml'quot; </transition> <transition event=quot;connection.connectedquot; state=quot;initquot;> <assign name=quot;statequot; expr=quot;'callconnected'quot;/> <dialogstart src=quot;'caller.vxml'quot; <transition event=quot;connection.failedquot; state=quot;callingquot;> </transition> <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;> <exit/> name=quot;statequot; expr=quot;'calling'quot;/> <assign </transition> dest=quot;'tel:+18315551234'quot;/> <createcall </transition> <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;> <transition name=quot;statequot; expr=quot;'calling'quot;/> <assign event=quot;connection.disconnectedquot; state=quot;connectedquot;> <createcall dest=quot;event$.values.destquot;/> <exit/> </transition> <transition event=quot;connection.connectedquot; state=quot;callingquot;> </transition> <assign name=quot;statequot; expr=quot;'connected'quot;/> <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/> </transition> <transition event=quot;connection.failedquot; state=quot;callingquot;> <exit/> </transition> <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;> <exit/> </transition> </eventprocessor> </ccxml> 62
  • 63. Call router + Twitter <?xml version=quot;1.0quot; encoding=quot;UTF-8quot;?> <ccxml xmlns=quot;http://www.w3.org/2002/09/ccxmlquot; version=quot;1.0quot;> <var name=quot;statequot; expr=quot;'init'quot;/> <var name=quot;incomingcallquot;/> <eventprocessor statevariable=quot;statequot;> <transition event=quot;connection.alertingquot; state=quot;initquot;> <assign name=quot;incomingcallquot; expr=quot;event$.connectionidquot;/> <accept/> </transition> <transition event=quot;connection.connectedquot; state=quot;initquot; cond=quot;event$.connection.remote=='tel:+18315551234'quot;> <assign name=quot;statequot; expr=quot;'rjconnected'quot;/> <dialogstart src=quot;'rj.vxml'quot; </transition> <transition event=quot;connection.connectedquot; state=quot;initquot;> <assign name=quot;statequot; expr=quot;'callconnected'quot;/> <dialogstart src=quot;'caller.vxml'quot; </transition> <transition event=quot;dialog.exitquot; state=quot;callconnectedquot;> <assign name=quot;statequot; expr=quot;'calling'quot;/> <createcall dest=quot;'tel:+18315551234'quot;/> </transition> <transition event=quot;dialog.exitquot; state=quot;rjconnectedquot;> <assign name=quot;statequot; expr=quot;'calling'quot;/> <createcall dest=quot;event$.values.destquot;/> </transition> <transition event=quot;connection.connectedquot; state=quot;callingquot;> <assign name=quot;statequot; expr=quot;'connected'quot;/> <join id1=quot;event$.connectionidquot; id2=quot;incomingcallquot;/> </transition> <transition event=quot;connection.failedquot; state=quot;callingquot;> <exit/> </transition> <transition event=quot;connection.disconnectedquot; state=quot;connectedquot;> <exit/> </transition> </eventprocessor> </ccxml> 63
  • 64. So... How about APIʼs... 64
  • 65. A Favorite of Carriers 65
  • 66. Java 66
  • 67. SIP Servlets > Standard Java based API for writing SIP applications. > 1.0 standardized as JSR-116. > 1.1 just released as JSR-289 > Extends the HTTP Servlet model to support SIP and telephony applications > http://www.sipservlet.com/ > Supported by a large number of application servers including Oracle (BEA), IBM, Sun, Voxeo. 67
  • 68. Request Methods > doInvite(SipServletRequest req); > doAck(SipServletRequest req); > doOptions(SipServletRequest req); > doBye(SipServletRequest req); > doCancel(SipServletRequest req); > doSubscribe(SipServletRequest req); > doNotify(SipServletRequest req); > doMessage(SipServletRequest req); > doInfo(SipServletRequest req); > doPrack(SipServletRequest req); 68
  • 69. Response Methods > doProvisionalResponse(SipServletResponse res); > doSuccessResponse(SipServletResponse res); > doRedirectResponse(SipServletResponse res); > doErrorResponse(SipServletResponse res); 69
  • 70. Basic Request public class BasicSIPServlet extends SipServlet { protected void doInfo(SipServletRequest req) throws ServletException, IOException { req.createResponse(SipServletResponse.SC_TRYING).send(); // do stuff req.createResponse(SipServletResponse.SC_OK).send(); } } 70
  • 71. Accessing SIP Headers protected void doInvite(SipServletRequest req) throws ServletException, IOException { String cpc ; if (req.getHeader(quot;User-Agentquot;).equals(quot;Sonusquot;)) { cpc = req.getHeader(quot;CallPartyquot;); } else if (req.getHeader(quot;User-Agentquot;).equals(quot;ZTEquot;)) { cpc = req.getHeader(quot;CPSquot;); } } 71
  • 72. JSR-309 > Java Media Server API > Based on the CCXML media model > Still in draft stage > Provides dialog resources, conferencing, media routing to Java applications 72
  • 73. Sample Application Overview > Lets try that application again in java... 73
  • 74. start isRJ() yes no prompt for dest play twitter status call dest call rj’s cell end
  • 75. SIP Flow Caller App Dest INVITE - doInvite() 200 OK ACK doAck() INVITE - transferDialog() 200 OK - doSuccessResponse() ACK 75
  • 76. Call router + Twitter public class TwitterSIPServlet extends SipServlet { SipFactory factory; public void init() throws ServletException { super.init(); factory =(SipFactory)getServletContext().getAttribute(quot;javax.servlet.sip.SipFactoryquot;); } protected void doInvite(SipServletRequest req) { if(req.isInitial()){ SipApplicationSession sipApp = factory.createApplicationSession(); TwitterSIPServletSession service = new TwitterSIPServletSession(req.getSession(), factory); sipApp.setAttribute(quot;router-appquot;, service); service.init(req); } } protected void doSuccessResponse(SipServletResponse resp) { resp.createAck().send(); } protected void doAck(SipServletRequest req) { final TwitterSIPServletSession service = (TwitterSIPServletSession) req.getApplicationSession().getAttribute(quot;router- appquot;); service.startDialog(); } protected void doBye(SipServletRequest req) { // Need to send BYE request to the other legs } } 76
  • 77. Call router + Twitter public class TwitterSIPServlet extends SipServlet { SipFactory factory; public void init() throws ServletException { super.init(); factory =(SipFactory)getServletContext().getAttribute(quot;javax.servlet.sip.SipFactoryquot;); } protected void doInvite(SipServletRequest req) { if(req.isInitial()){ SipApplicationSession sipApp = factory.createApplicationSession(); TwitterSIPServletSession service = new TwitterSIPServletSession(req.getSession(), factory); sipApp.setAttribute(quot;router-appquot;, service); service.init(req); } } protected void doSuccessResponse(SipServletResponse resp) { resp.createAck().send(); } protected void doAck(SipServletRequest req) { final TwitterSIPServletSession service = (TwitterSIPServletSession) req.getApplicationSession().getAttribute(quot;router- appquot;); service.startDialog(); } protected void doBye(SipServletRequest req) { // Need to send BYE request to the other legs } } 77
  • 78. Call router + Twitter public class TwitterSIPServlet extends SipServlet { SipFactory factory; public void init() throws ServletException { public class TwitterSIPServlet extends SipServlet { super.init(); factory =(SipFactory)getServletContext().getAttribute(quot;javax.servlet.sip.SipFactoryquot;); SipFactory factory; } protected void doInvite(SipServletRequest req) { if(req.isInitial()){ public void init() sipApp = factory.createApplicationSession(); SipApplicationSession throws ServletException { TwitterSIPServletSession service = new TwitterSIPServletSession(req.getSession(), super.init(); factory); sipApp.setAttribute(quot;router-appquot;, service); } factory = (SipFactory)getServletContext() service.init(req); } .getAttribute(quot;javax.servlet.sip.SipFactoryquot;); } protected void doSuccessResponse(SipServletResponse resp) { resp.createAck().send(); } } protected void doAck(SipServletRequest req) { final TwitterSIPServletSession service = (TwitterSIPServletSession) req.getApplicationSession().getAttribute(quot;router- appquot;); service.startDialog(); } protected void doBye(SipServletRequest req) { // Need to send BYE request to the other legs } } 78
  • 79. Call router + Twitter public class TwitterSIPServlet extends SipServlet { SipFactory factory; public void init() throws ServletException { super.init(); factory =(SipFactory)getServletContext().getAttribute(quot;javax.servlet.sip.SipFactoryquot;); } protected void doInvite(SipServletRequest req) { if(req.isInitial()){ SipApplicationSession sipApp = factory.createApplicationSession(); TwitterSIPServletSession service = new TwitterSIPServletSession(req.getSession(), factory); sipApp.setAttribute(quot;router-appquot;, service); service.init(req); } } protected void doSuccessResponse(SipServletResponse resp) { resp.createAck().send(); } protected void doAck(SipServletRequest req) { final TwitterSIPServletSession service = (TwitterSIPServletSession) req.getApplicationSession().getAttribute(quot;router- appquot;); service.startDialog(); } protected void doBye(SipServletRequest req) { // Need to send BYE request to the other legs } } 79
  • 80. Call router + Twitter public class TwitterSIPServlet extends SipServlet { SipFactory factory; public void init() throws ServletException { super.init(); factory =(SipFactory)getServletContext().getAttribute(quot;javax.servlet.sip.SipFactoryquot;); } protected void doInvite(SipServletRequest req) { protected void doInvite(SipServletRequest req) { if(req.isInitial()){ SipApplicationSession sipApp = factory.createApplicationSession(); if(req.isInitial()){ TwitterSIPServletSession service = new TwitterSIPServletSession(req.getSession(), factory); sipApp.setAttribute(quot;router-appquot;, service); SipApplicationSession sipApp service.init(req); } = factory.createApplicationSession(); } TwitterSIPServletSession service protected void doSuccessResponse(SipServletResponse resp) { } = new TwitterSIPServletSession(req.getSession(), resp.createAck().send(); factory); sipApp.setAttribute(quot;router-appquot;, service); protected void doAck(SipServletRequest req) { service.init(req); final TwitterSIPServletSession service = (TwitterSIPServletSession) req.getApplicationSession().getAttribute(quot;router- } appquot;); service.startDialog(); }} protected void doBye(SipServletRequest req) { // Need to send BYE request to the other legs } } 80
  • 81. Call router + Twitter public class TwitterSIPServlet extends SipServlet { SipFactory factory; public void init() throws ServletException { super.init(); factory =(SipFactory)getServletContext().getAttribute(quot;javax.servlet.sip.SipFactoryquot;); } protected void doInvite(SipServletRequest req) { if(req.isInitial()){ SipApplicationSession sipApp = factory.createApplicationSession(); TwitterSIPServletSession service = new TwitterSIPServletSession(req.getSession(), factory); sipApp.setAttribute(quot;router-appquot;, service); service.init(req); } } protected void doSuccessResponse(SipServletResponse resp) { resp.createAck().send(); } protected void doAck(SipServletRequest req) { final TwitterSIPServletSession service = (TwitterSIPServletSession) req.getApplicationSession().getAttribute(quot;router- appquot;); service.startDialog(); } protected void doBye(SipServletRequest req) { // Need to send BYE request to the other legs } } 81
  • 82. Call router + Twitter public class TwitterSIPServlet extends SipServlet { SipFactory factory; public void init() throws ServletException { super.init(); factory =(SipFactory)getServletContext().getAttribute(quot;javax.servlet.sip.SipFactoryquot;); } protected void doInvite(SipServletRequest req) { if(req.isInitial()){ SipApplicationSession sipApp = factory.createApplicationSession(); TwitterSIPServletSession service = new TwitterSIPServletSession(req.getSession(), factory); protected void doSuccessResponse(SipServletResponse resp) { sipApp.setAttribute(quot;router-appquot;, service); resp.createAck().send(); } service.init(req); }} protected void doSuccessResponse(SipServletResponse resp) { resp.createAck().send(); } protected void doAck(SipServletRequest req) { final TwitterSIPServletSession service = (TwitterSIPServletSession) req.getApplicationSession().getAttribute(quot;router- appquot;); service.startDialog(); } protected void doBye(SipServletRequest req) { // Need to send BYE request to the other legs } } 82
  • 83. Call router + Twitter public class TwitterSIPServlet extends SipServlet { SipFactory factory; public void init() throws ServletException { super.init(); factory =(SipFactory)getServletContext().getAttribute(quot;javax.servlet.sip.SipFactoryquot;); } protected void doInvite(SipServletRequest req) { if(req.isInitial()){ SipApplicationSession sipApp = factory.createApplicationSession(); TwitterSIPServletSession service = new TwitterSIPServletSession(req.getSession(), factory); sipApp.setAttribute(quot;router-appquot;, service); service.init(req); } } protected void doSuccessResponse(SipServletResponse resp) { resp.createAck().send(); } protected void doAck(SipServletRequest req) { final TwitterSIPServletSession service = (TwitterSIPServletSession) req.getApplicationSession().getAttribute(quot;router- appquot;); service.startDialog(); } protected void doBye(SipServletRequest req) { // Need to send BYE request to the other legs } } 83
  • 84. Call router + Twitter public class TwitterSIPServlet extends SipServlet { SipFactory factory; public void init() throws ServletException { super.init(); factory =(SipFactory)getServletContext().getAttribute(quot;javax.servlet.sip.SipFactoryquot;); } protected void doAck(SipServletRequest req) { protected void doInvite(SipServletRequest req) { if(req.isInitial()){ final TwitterSIPServletSession service SipApplicationSession sipApp = factory.createApplicationSession(); TwitterSIPServletSession service = new TwitterSIPServletSession(req.getSession(), factory); = (TwitterSIPServletSession) req.getApplicationSession() sipApp.setAttribute(quot;router-appquot;, service); service.init(req); .getAttribute(quot;router-appquot;); } } service.startDialog(); } resp.createAck().send(); protected void doSuccessResponse(SipServletResponse resp) { } protected void doAck(SipServletRequest req) { final TwitterSIPServletSession service = (TwitterSIPServletSession) req.getApplicationSession().getAttribute(quot;router- appquot;); service.startDialog(); } protected void doBye(SipServletRequest req) { // Need to send BYE request to the other legs } } 84
  • 85. Call router + Twitter public class TwitterSIPServlet extends SipServlet { SipFactory factory; public void init() throws ServletException { super.init(); factory =(SipFactory)getServletContext().getAttribute(quot;javax.servlet.sip.SipFactoryquot;); } protected void doInvite(SipServletRequest req) { if(req.isInitial()){ SipApplicationSession sipApp = factory.createApplicationSession(); TwitterSIPServletSession service = new TwitterSIPServletSession(req.getSession(), factory); sipApp.setAttribute(quot;router-appquot;, service); service.init(req); } } protected void doSuccessResponse(SipServletResponse resp) { resp.createAck().send(); } protected void doAck(SipServletRequest req) { final TwitterSIPServletSession service = (TwitterSIPServletSession) req.getApplicationSession().getAttribute(quot;router- appquot;); service.startDialog(); } protected void doBye(SipServletRequest req) { // Need to send BYE request to the other legs } } 85
  • 86. Call router + Twitter public class TwitterSIPServlet extends SipServlet { SipFactory factory; public void init() throws ServletException { super.init(); factory =(SipFactory)getServletContext().getAttribute(quot;javax.servlet.sip.SipFactoryquot;); } protected void doInvite(SipServletRequest req) { if(req.isInitial()){ SipApplicationSession sipApp = factory.createApplicationSession(); TwitterSIPServletSession service = new TwitterSIPServletSession(req.getSession(), factory); protected void doBye(SipServletRequest req) { sipApp.setAttribute(quot;router-appquot;, service); service.init(req);the frack has cleanup code in // Who } } // slide demo’s anyway? protected }void doSuccessResponse(SipServletResponse resp) { resp.createAck().send(); } protected void doAck(SipServletRequest req) { final TwitterSIPServletSession service = (TwitterSIPServletSession) req.getApplicationSession().getAttribute(quot;router- appquot;); service.startDialog(); } protected void doBye(SipServletRequest req) { // Need to send BYE request to the other legs } } 86
  • 87. Call router + Twitter public class TwitterSIPServlet extends SipServlet { SipFactory factory; public void init() throws ServletException { super.init(); factory =(SipFactory)getServletContext().getAttribute(quot;javax.servlet.sip.SipFactoryquot;); } protected void doInvite(SipServletRequest req) { if(req.isInitial()){ SipApplicationSession sipApp = factory.createApplicationSession(); TwitterSIPServletSession service = new TwitterSIPServletSession(req.getSession(), factory); sipApp.setAttribute(quot;router-appquot;, service); service.init(req); } } protected void doSuccessResponse(SipServletResponse resp) { resp.createAck().send(); } protected void doAck(SipServletRequest req) { final TwitterSIPServletSession service = (TwitterSIPServletSession) req.getApplicationSession().getAttribute(quot;router- appquot;); service.startDialog(); } protected void doBye(SipServletRequest req) { // Need to send BYE request to the other legs } } 87
  • 88. Call router + Twitter public class TwitterSIPServletSession { final SipSession mySipSession; final SipFactory myFactory; MediaGroup myMediaGroup; boolean isRJ = false; public TwitterSIPServletSession(SipSession aSipSession, SipFactory aFactory) { ... } public void init(final SipServletRequest req) { ... } public void startDialog() { ... } class CallerPlayerListener implements MediaEventListener<PlayerEvent> { ... } class RJDialerSignalDetectorListener implements MediaEventListener<SignalDetectorEvent> { ... } void transferDialog(String uri) throws ServletParseException, IOException { ... } } 88
  • 89. Call router + Twitter public class TwitterSIPServletSession { final SipSession mySipSession; final SipFactory myFactory; MediaGroup myMediaGroup; boolean isRJ = false; public TwitterSIPServletSession(SipSession aSipSession, SipFactory aFactory) { ... } public void init(final SipServletRequest req) { ... } public void startDialog() { ... } class CallerPlayerListener implements MediaEventListener<PlayerEvent> { ... } class RJDialerSignalDetectorListener implements MediaEventListener<SignalDetectorEvent> { ... } void transferDialog(String uri) throws ServletParseException, IOException { ... } } 89
  • 90. Call router + Twitter public class TwitterSIPServletSession { final SipSession mySipSession; final SipFactory myFactory; MediaGroup myMediaGroup; boolean isRJ = false; public TwitterSIPServletSession(SipSession aSipSession, SipFactory aFactory) { ... } public void init(final SipServletRequest req) { public class TwitterSIPServletSession ... { } final SipSession mySipSession; public void startDialog() { final SipFactory myFactory; ... } MediaGroup myMediaGroup; boolean isRJ = false; class CallerPlayerListener implements MediaEventListener<PlayerEvent> { ... } public TwitterSIPServletSession(SipSession aSipSession, class RJDialerSignalDetectorListener implements MediaEventListener<SignalDetectorEvent> { ... SipFactory aFactory) { } mySipSession = aSipSession; ... myFactory = aFactory; void transferDialog(String uri) throws ServletParseException, IOException { } } } } 90
  • 91. Call router + Twitter public class TwitterSIPServletSession { final SipSession mySipSession; final SipFactory myFactory; MediaGroup myMediaGroup; boolean isRJ = false; public TwitterSIPServletSession(SipSession aSipSession, SipFactory aFactory) { ... } public void init(final SipServletRequest req) { ... } public void startDialog() { ... } class CallerPlayerListener implements MediaEventListener<PlayerEvent> { ... } class RJDialerSignalDetectorListener implements MediaEventListener<SignalDetectorEvent> { ... } void transferDialog(String uri) throws ServletParseException, IOException { ... } } 91
  • 92. Call router + Twitter public class TwitterSIPServletSession { final SipSession mySipSession; final SipFactory myFactory; MediaGroup myMediaGroup; boolean isRJ = false; public TwitterSIPServletSession(SipSession aSipSession, SipFactory aFactory) { ... } public void init(final SipServletRequest req) throws ServletException { MediaSession myMediaSession = MediaSessionFactory.createMediaSession(); public void init(final SipServletRequest req) { ... } NetworkConnection myNetworkConnection = public void startDialog() { myMediaSession.createContainer(NetworkConnectionConfig.c_Basic); ... } myMediaGroup = myMediaSession.createContainer(MediaGroupConfig.c_PlayerSignalDetector); class CallerPlayerListener implements MediaEventListener<PlayerEvent> { ... } MediaEventListener<NetworkConnectionEvent> myNetworkConnectionListener = new MediaEventListener<NetworkConnectionEvent>() { class RJDialerSignalDetectorListener implements MediaEventListener<SignalDetectorEvent> { ... .... } }; myNetworkConnection.addListener(myNetworkConnectionListener); void transferDialog(String uri) throws ServletParseException, IOException { ... } myNetworkConnection.modify(quot;quot;, new String(req.getRawContent())); } } 92
  • 93. Call router + Twitter public class TwitterSIPServletSession { final SipSession mySipSession; final SipFactory myFactory; MediaGroup myMediaGroup; boolean isRJ = false; public TwitterSIPServletSession(SipSession aSipSession, SipFactory aFactory) { ... } MediaEventListener<NetworkConnectionEvent> myNetworkConnectionListener = new MediaEventListener<NetworkConnectionEvent>() { public void init(final SipServletRequest req) { ... public void onEvent(NetworkConnectionEvent anEvent) { } if (NetworkConnectionConstants.ev_Modify.equals(anEvent.getEventID())) { public void (req.getFrom().getURI().getUser().equals(quot;8312392883quot;)) { startDialog() { ... if } isRJ = true; myMediaGroup.getSignalDetector().addListener( new RJDialerSignalDetectorListener()); class CallerPlayerListener implements MediaEventListener<PlayerEvent> { ... } else { } myMediaGroup.getSignalDetector().addListener( new CallerPlayerListener()); class RJDialerSignalDetectorListener implements MediaEventListener<SignalDetectorEvent> { ... } } myMediaGroup.join(Direction.DUPLEX, myNetworkConnection); String sdpAnswer = myNetworkConnection.getRawLocalSessionDescription(); void transferDialog(String uri) throws ServletParseException, IOException { ... SipServletMessage msg = req.createResponse(200, quot;OKquot;); } msg.setContent(sdpAnswer.getBytes(), quot;application/sdpquot;); } msg.send(); } } }; 93
  • 94. Call router + Twitter public class TwitterSIPServletSession { final SipSession mySipSession; final SipFactory myFactory; MediaGroup myMediaGroup; boolean isRJ = false; public TwitterSIPServletSession(SipSession aSipSession, SipFactory aFactory) { ... } public void init(final SipServletRequest req) { ... } public void startDialog() { ... } class CallerPlayerListener implements MediaEventListener<PlayerEvent> { ... } class RJDialerSignalDetectorListener implements MediaEventListener<SignalDetectorEvent> { ... } void transferDialog(String uri) throws ServletParseException, IOException { ... } } 94
  • 95. Call router + Twitter public class TwitterSIPServletSession { final SipSession mySipSession; final SipFactory myFactory; MediaGroup myMediaGroup; public void startDialog() { boolean isRJ = false; if (isRJ) { Parameters collectOptions = mediaSessionFactory.createParameters(); public TwitterSIPServletSession(SipSession aSipSession, SipFactory aFactory) { ... prompt = URI.create(quot;data:application/ssml+xml,quot;+ URI } quot;<?xml version=quot;1.0quot;?>quot;+ public void init(final SipServletRequest req) { ... quot;<speak>quot;+ } quot;Welcome RJ. Please enter the phone number you wish to reach.quot;+ quot;</speak>quot;); public void startDialog() { collectOptions.put(SignalDetectorConstants.p_Prompt, prompt); ... } mg.getSignalDetector().receiveSignals(10, null, RTC.bargeIn, collectOptions); } else { class CallerPlayerListener twitter_apiMediaEventListener<PlayerEvent> { net.unto.twitter.Api implements ... = new net.unto.twitter.Api(quot;zscgeekquot;, quot;passwordquot;); } URI prompt = URI.create(quot;data:application/ssml+xml,quot;+ class RJDialerSignalDetectorListener quot;<?xml version=quot;1.0quot;?>quot;+ implements MediaEventListener<SignalDetectorEvent> { ... quot;<speak>quot;+ } quot;Thank you for calling RJ. We will connect you now.quot;+ quot;His twitter status is:quot;+ void transferDialog(String uri) throws ServletParseException, IOException { ... twitter_api.getStatus()+ } quot;</speak>quot;); } myMediaGroup.getPlayer().play(prompt, null, null); } } 95
  • 96. Call router + Twitter public class TwitterSIPServletSession { final SipSession mySipSession; final SipFactory myFactory; MediaGroup myMediaGroup; boolean isRJ = false; public TwitterSIPServletSession(SipSession aSipSession, SipFactory aFactory) { ... } public void init(final SipServletRequest req) { ... } public void startDialog() { ... } class CallerPlayerListener implements MediaEventListener<PlayerEvent> { ... } class RJDialerSignalDetectorListener implements MediaEventListener<SignalDetectorEvent> { ... } void transferDialog(String uri) throws ServletParseException, IOException { ... } } 96
  • 97. Call router + Twitter public class TwitterSIPServletSession { final SipSession mySipSession; final SipFactory myFactory; MediaGroup myMediaGroup; boolean isRJ = false; public TwitterSIPServletSession(SipSession aSipSession, SipFactory aFactory) { ... } public void init(final SipServletRequest req) { ... } public void startDialog() { ... class CallerPlayerListener implements MediaEventListener<PlayerEvent> { } public void onEvent(PlayerEvent anEvent) { class CallerPlayerListenerquot;+anEvent.getSignalString()); log(quot;Collected: implements MediaEventListener<PlayerEvent> { ... } MediaSession mediaSession = anEvent.getSource().getMediaSession().release(); class RJDialerSignalDetectorListener transferDialog(quot;sip:+18315551234@gateway:5060quot;); implements MediaEventListener<SignalDetectorEvent> { ... } } } void transferDialog(String uri) throws ServletParseException, IOException { ... } } 97
  • 98. Call router + Twitter public class TwitterSIPServletSession { final SipSession mySipSession; final SipFactory myFactory; MediaGroup myMediaGroup; boolean isRJ = false; public TwitterSIPServletSession(SipSession aSipSession, SipFactory aFactory) { ... } public void init(final SipServletRequest req) { ... } public void startDialog() { ... } class CallerPlayerListener implements MediaEventListener<PlayerEvent> { ... } class RJDialerSignalDetectorListener implements MediaEventListener<SignalDetectorEvent> { ... } void transferDialog(String uri) throws ServletParseException, IOException { ... } } 98
  • 99. Call router + Twitter public class TwitterSIPServletSession { final SipSession mySipSession; final SipFactory myFactory; MediaGroup myMediaGroup; boolean isRJ = false; public TwitterSIPServletSession(SipSession aSipSession, SipFactory aFactory) { ... } public void init(final SipServletRequest req) { ... } class RJDialerSignalDetectorListener implements MediaEventListener<SignalDetectorEvent> { public void startDialog() { ... } public void onEvent(SignalDetectorEvent anEvent) { log(quot;Collected: quot;+anEvent.getSignalString()); class CallerPlayerListener implements = MediaSession mediaSession MediaEventListener<PlayerEvent> { ... } anEvent.getSource().getMediaSession().release(); transferDialog(quot;sip:quot; + anEvent.getSignalString() class RJDialerSignalDetectorListener + quot;@gateway:5060quot;); implements MediaEventListener<SignalDetectorEvent> { ... } } } void transferDialog(String uri) throws ServletParseException, IOException { ... } } 99
  • 100. Call router + Twitter public class TwitterSIPServletSession { final SipSession mySipSession; final SipFactory myFactory; MediaGroup myMediaGroup; boolean isRJ = false; public TwitterSIPServletSession(SipSession aSipSession, SipFactory aFactory) { ... } public void init(final SipServletRequest req) { ... } public void startDialog() { ... } class CallerPlayerListener implements MediaEventListener<PlayerEvent> { ... } class RJDialerSignalDetectorListener implements MediaEventListener<SignalDetectorEvent> { ... } void transferDialog(String uri) throws ServletParseException, IOException { ... } } 100
  • 101. Call router + Twitter public class TwitterSIPServletSession { final SipSession mySipSession; final SipFactory myFactory; MediaGroup myMediaGroup; boolean isRJ = false; public TwitterSIPServletSession(SipSession aSipSession, SipFactory aFactory) { ... } public void init(final SipServletRequest req) { ... } void transferDialog(String uri) { public void startDialog() request = SipServletRequest { ... } myFactory.createRequest(mySipSession.getApplicationSession(), quot;INVITEquot;, quot;sip:addressbook@sip-as-uri:5060quot;, class CallerPlayerListener implements MediaEventListener<PlayerEvent> { ... } uri); request.send(); class RJDialerSignalDetectorListener } implements MediaEventListener<SignalDetectorEvent> { ... } void transferDialog(String uri) throws ServletParseException, IOException { ... } } 101
  • 102. Call router + Twitter public class TwitterSIPServletSession { final SipSession mySipSession; final SipFactory myFactory; MediaGroup myMediaGroup; boolean isRJ = false; public TwitterSIPServletSession(SipSession aSipSession, SipFactory aFactory) { ... } public void init(final SipServletRequest req) { ... } public void startDialog() { ... } class CallerPlayerListener implements MediaEventListener<PlayerEvent> { ... } class RJDialerSignalDetectorListener implements MediaEventListener<SignalDetectorEvent> { ... } void transferDialog(String uri) throws ServletParseException, IOException { ... } } 102
  • 103. Made it to the finish line! 103
  • 104. So. We Have Java... 104
  • 105. But is it Simple? 105
  • 106. Is it cool? 106
  • 107. Is It Web 2.0? 107
  • 109. So... 109
  • 110. Tropo.com 110
  • 111. answer(); say(quot;Hello, world!quot;); hangup(); Tropo is Simple 111
  • 112. Ruby Telephony in YOUR Language (thanks to the magic of JSR223) 112
  • 113. •! answer •! redirect •! ask •! reject •! say •! log •! record •! wait •! call •! default •! transfer •! hangup Simple to Learn 113
  • 114. •Hosted service •Accessible via Phone, SIP, Skype etc •Inbound and Outbound calling •Free for developers •No setup costs •Five minutes from sign-up to live deployment + = GO Simple to Deploy 114
  • 115. What are the Ingredients? 115