参考:RFC4028
目标:
为了控制通过re-INVITE和UPDATE方法进行周期性的会话(session)刷新,以判别会话两端是否存活,增加了两个头域:Session-Expires(会话的生命期)和Min-SE(会话时钟的最小值)。
介绍:
SIP(RFC3261)没有提供已存在会话保持激活的机制,虽然可以终端可以使用某些方式了解会话是否存活,但proxy却无法做到这一点。Re-INVITE和UPDATE方法就基于此进行的,这些刷新请求的周期是通过协商来确定的。当在规定的周期内没有新的刷新请求到来,即认为该会话结束。
运作:
1)首先,UAC在INVITE方法中的Supported头域中加入timer标签,表示支持该RFC;
2)当请求通过proxies时,它们在请求中加入或修改已存在的Session-Expires和Min-SE头域;(其中Min-SE头域中的值只能增加不能减少,Session-Expires头域的值只能减少不能增加,但不能少于Min-SE头域中的值);
3)当Proxy无法接受请求中的Session-Expires值时(小于Min-SE值),Proxy会回复422,UAC会继续发起请求,但会携带422中的Min-SE头域;
4)当请求到达UAS时,UAS会在2**的应答中Session-Expires头域中填写最后的结果,且会携带参数refresher(指示当前的UAC或UAS谁来进行刷新)。2**的回复,Proxy无法修改Session-Expires头域。
5)此后在协商的Session-Expires时间内,UA会发起新的刷新请求,如果刷新失败(发起者收不到回应或收到408、481,接受者收不到请求),则发送BYE消息。
当通话一旦开始即发送刷新请求。一般来说,如果支持该RFC的话,最后刷新一般使用UPDATE方法。
UAC行为:
产生初始会话刷新请求
支持session timer时必须在所有的请求中的Supported头域中加入timer标签。
UAC可能包括Min-SE或Session-Expires头域。
处理2**应答
如果2**应答中包含的Require头域中包含timer值,UAC必须寻找并处理Session-Expires头域。
如果应答中的Require头域包含timer值,则Session-Expires头域必须存在。如果Require中不存在timer且Session-Expires头域不存在,说明UAS不支持session timer扩展。如果此时UAC仍希望继续进行刷新,则自己只能主动发起会话刷新请求。
如果2**应答中不包含Session-Expires头域,则终止会话刷新请求。
处理422应答
当收到422请求是,请求者可以继续发送回话刷新请求,其中的Call-ID, To和From头域值和之前的相同,但Cseq头域值应比之前的大1.
发送后继会话刷新请求:
初始会话刷新请求中的Suppported、Require和Proxy-require头域必须存在与后继的会话刷新请求中。
如果在一个对话中,UAC收到422回应或收到带有Min-SE头域的会话刷新请求,则应在会话刷新请求中带有Min-SE头域。如果在对话外收到一个422回应,则应在INVITE请求中带有Min-SE头域。
Min-SE头域中的值应该为所有422回应中的最大的Min-SE值或在同一个对话中收到的会话刷新请求中的Min-SE头域值。
在一个对话中,一个会话刷新请求需包含Session-Expires头域,值为最大的Min-SE头域值(默认为90s)或当前会话间隙。
如果该会话刷新请求非初始化者,建议填写refresher参数。
UAS行为:
当会话刷新请求中的Supported头域包含timer,且Session-expires头域值小于UAS自身的Min-SE值,则发送422应答,该应答必须包含Min-SE头域。
如果UAS接受会话刷新请求,则拷贝请求中的Session-Expires头域值到2**应答中。当然,UAS可以修改该值,但只需减少不能增加。
UAS必须在2**应答中的Session-Expires头域中包含refresher参数。
如果2**中的Session-Expires头域中的refresher参数为uac,则UAS应在Require头域中加入timer值。
UAC和UAS都应保存session timer的状态,包括会话间隙、会话超时和刷新者。
如果2**应答中不包含Session-Expires头域,则说明会话刷新结束。
如果UAS必须刷新会话,则必须计算会话超时时间。会话超时时间为发送2**应答的时间加上对话间隙。
对话刷新:
如果不主动刷新对话端在对话超时到来时并未收到对话刷新请求,则应发送BYE来结束会话。