在很久以前,我写过一篇关于等待音乐的文章。通过这么设置之后,用户可以可以在通话过程中按Hold键,这样对方就可以听到等待音乐。而且我们都知道这个音乐是从客户端发送到服务器上,然后再传给对方的。这样的client-side MoH在实际的操作中存在这么两个小问题:

第一:在客户端点击了Hold之后,配置不是很高的电脑上可能会出现一段时间的假死,大概在4秒只之后,对方才会听到音乐。估计这段时间内应该是本地启动什么播放模块,然后再发送这个音乐的流媒体到服务器。

第二:如果用户是通过Edge登录拨打电话的话,在网络情况不是很好的情况下,对端所听到的音乐音质下降得厉害

 

今天我们来看看Server-side的MoH是如何实现的。目前Lync还没有自己的Server Side的功能,只能借助于外部设备。现在借助于NET的UX 1000,我们看看MoH整个过程是如何来实现的。在这里的呼叫流程是Lync把所有的呼叫发送给UX 1000,然后UX 1000再把呼叫发送给PSTN,最终达到用户端。

 

我们先看看UX 1000上如何设置MoH

首先检查UX 1000上是否加载了音乐文件,通过下图我们看到现在系统里面并没有文件。

image

然后我们到媒体配置,选择上载一个音乐文件

image

选择一个之前弄好的WAV文件,这个文件大小还是有要求的(UX 1000最大为1M,UX2000为4M),在格式方面需要文件的采样率为8KHz的单声道WAV文件。

image

然后再回到DSP信息处检查,这个时候就显示loaded了。

image

下面就是为针对Lync的SIP 中继打开MoH功能,我们看到在这里可以打开,也可以关闭。我们足额则Always Enabled就好了。

image

 

一切都OK了,使用Lync用户拨打一个3001测试看看。接通之后,然后点击下图所示的图标,这个时候对方立马就可以听到音乐的。

 

image

而Lync客户端也会如下一样显示,如果要恢复呼叫,只要点击Resume Call就OK。

image

 

到这里MoH就已经实现了,而且我们发现,现在一点击hold,对方马上就听到音乐,没有任何的延迟,而且客户端也不会有任何的假死。同时这个音质就非常好,和用户所在的网络没有任何关系。

但是我们当然不满足这点了,我们想看看在用户点击了Hold之后,到底Lync发送了什么消息给网关。

 什么?Lync居然发送了一个INVITE给网关?确实是这样一个包,不过我们注意到在SDP里面有这么一句话a=inactive,这句就是告诉网关,现在Lync客户端要进入inactive状态了,请不要发送任何的RTP过来,Lync客户端也不会发送任何的RTP给网关。在网关收到这个INVITE之后,它就开始给对方播放音乐了

INVITE sip:192.168.1.223:5060;transport=TCP SIP/2.0
FROM: <sip:+216@lync2010.ucdemo.net;user=phone>;epid=225A1702DD;tag=901872914a
TO: <sip:3001@192.168.1.223;user=phone>;tag=c0a801df-32
CSEQ: 177 INVITE
CALL-ID: 7b914bb2-4361-4b83-a33c-20bfb3f03eb2
MAX-FORWARDS: 70
VIA: SIP/2.0/TCP 192.168.1.82:49880;branch=z9hG4bK543e4d6f
CONTACT: <sip:Lync2010.ucdemo.net:5068;transport=Tcp;maddr=192.168.1.82;ms-opaque=49ed7dd110f0a17a>
CONTENT-LENGTH: 278
SUPPORTED: 100rel
USER-AGENT: RTCC/4.0.0.0 MediationServer
CONTENT-TYPE: application/sdp

v=0
o=- 14 2 IN IP4 192.168.1.82
s=session
c=IN IP4 192.168.1.82
b=CT:1000
t=0 0
m=audio 50932 RTP/AVP 101 13 0
c=IN IP4 192.168.1.82
a=rtcp:50933
a=label:Audio
a=inactive
a=rtpmap:101 telephone-event/8000
a=fmtp:101 0-16
a=rtpmap:13 CN/8000
a=rtpmap:0 PCMU/8000

 

如果用户点击了Resume之后,我们则会看到如下的数据包,其中的SDP变成了a=sendrecv,这个表明现在客户端是出于活动状态,又可以接受,又可以发送,网关在收到这个信息之后,就停止播放音乐,重新把两个端点的语音通道建立起来。

INVITE sip:192.168.1.223:5060;transport=TCP SIP/2.0
FROM: <sip:+216@lync2010.ucdemo.net;user=phone>;epid=225A1702DD;tag=901872914a
TO: <sip:3001@192.168.1.223;user=phone>;tag=c0a801df-32
CSEQ: 178 INVITE
CALL-ID: 7b914bb2-4361-4b83-a33c-20bfb3f03eb2
MAX-FORWARDS: 70
VIA: SIP/2.0/TCP 192.168.1.82:49880;branch=z9hG4bKb33556
CONTACT: <sip:Lync2010.ucdemo.net:5068;transport=Tcp;maddr=192.168.1.82;ms-opaque=49ed7dd110f0a17a>
CONTENT-LENGTH: 278
SUPPORTED: 100rel
USER-AGENT: RTCC/4.0.0.0 MediationServer
CONTENT-TYPE: application/sdp

v=0
o=- 14 3 IN IP4 192.168.1.82
s=session
c=IN IP4 192.168.1.82
b=CT:1000
t=0 0
m=audio 50932 RTP/AVP 101 13 0
c=IN IP4 192.168.1.82
a=rtcp:50933
a=label:Audio
a=sendrecv
a=rtpmap:101 telephone-event/8000
a=fmtp:101 0-16
a=rtpmap:13 CN/8000
a=rtpmap:0 PCMU/8000

 

如果我们采用的是Lync自己的Client-side MoH,通过抓包,我们会发现Lync送过来的INVITE的里面的SDP为a=sendonly,这个则是表明,现在的Lync客户端是只发不收的,它只会把MoH的音乐传出来,而不会接受网关发过的媒体消息。

另外需要注意一点的是,如果Server side的MoH和客户端的MoH都设置的话,服务器端的设置会把客户端的设置覆盖。所以建议如果你启用了Server side的MoH,

可以如下的命令取消客户端的MoH。

image