正文

SIP的RFC中文文档(RFC3261)(9)2005-12-30 00:17:00

【评论】 【打印】 【字体: 】 本文链接:http://blog.pfan.cn/ddtme/9069.html

分享到:

9 取消一个请求(Cancel)

前边几节讲述了对所有方法的处理请求和处理应答的UA的通用处理过程。在本节中,我们讨论一个通用的方法,CANCELCANCEL请求,就像名字所说的,是用来取消客户端发起的上一个请求的。特别是,它请求UAS去终止上一个请求并且对上一个请求产生一个错误的应答。CANCELUAS已经给出终结应答的请求无效。所以,CANCEL请求的最大用处是取消需要服务器长时间处理的请求。也就是说,CANCEL最常用来处理取消INVITE请求,因为INVITE通常需要花费很长时间来产生一个终结应答。在这种使用中,UAS接收到对一个INVITE请求的CANCEL请求,当这个INVITE还没有得到终结应答的时候,UAS停止振铃,并且给INVITE请求一个错误的应答(487)。

CANCEL可以由proxy或者UAC发起。15节讲述了在何种情况下,UACCANCEL一个INVITE请求,在16.10节讲述了proxyCANCEL的使用。

一个有状态的proxy需要对CANCEL进行响应,而不是简单的转发从下行流中接收到的一个应答。基于这个原因,CANCEL是一个点对点hop-by-hop)的请求,也就是说,CANCEL需要每一个有状态的proxy节点进行处理和应答

9.1 客户行为(Client Behavior)

CANCEL请求不应该取消除了INVITE之外的请求。因为除了INVITE之外的请求的响应都是立即响应的,所以,发送CANCEL来取消一个非INVITE请求总是形成一种赛跑的局面(就是说,cancel先到还是被取消的请求先到)。

下列步骤用于创建一个CANCEL请求。在CANCEL请求中的Request-URI , Call-ID , To , Cseq的数字部分,From这些头域都必须和被取消的请求头域一样,包含这些头域的tags. 客户端创建的CANCEL必须只有一个Via头域值,这个头域值和被取消的请求的最上一个Via头域值相同。这些头域的值和请求的值相同可以让CANCEL请求和被取消的请求相匹配(9.2节描述了如何匹配)。在Cseq请求头域的method部分必须是一个CANCEL方法。这个让这个CANCEL请求被当作自己的事务而被正确的鉴别和处理(参见17节)。

如果被取消的请求包含一个Route头域,CANCEL请求也必须包含这个Route头域的值。这个是让无状态的proxy能够正确路由CANCEL请求。

CANCEL头域必须不能包含任何Require或者Proxy-Require头域。

一旦CANCEL请求被创建了,客户端应当检查是否收到了这个CANCEL请求取消的原始请求的任何应答(临时的或者终结的应答)。如果没有任何临时应答收到,这个CANCEL请求一定不能发送,直到客户端等到了第一个临时应答。如果原始请求已经收到一个终结应答,这个CANCEL也不应当发送,因为CANCEL请求对已经产生了终结应答的请求没有任何作用。当客户端决定发送一个CANCEL,它会为这个CANCEL创建一个客户transaction,并且通过目的地址、端口、传输层来发送CANCEL请求。这个CANCEL中的目标地址、端口和传输层必须和原始请求一样。

如果允许在接收应答之前发送CANCEL请求,那么服务端必须支持在接收原始请求之前接收到CANCEL请求。

注意,原始请求的事务和CANCEL请求的事务都是互相独立的。也就是说,UAC判定一个请求的取消不能依赖原始请求的一个487(请求终止)应答,遵循RFC2543协议,UAS不会产生这样一个应答。如果原始请求经过了64*T1T117.1.1.1节定义)秒还没有应答,客户端应当认为原始请求已经取消,并且应当销毁对应原始请求的客户端事务。

9.2 服务端行为(Server Behavior)

CANCEL请求要求服务端的TU取消相关的事务(transaction)。TU根据接收到的CANCEL请求,并且假定请求的方法不是CANCEL或者ACK,并且用17.2.3节描述的事务匹配方法来匹配事务,这样TU就可以决定那个事务需要被取消了,被匹配的事务就是需要被取消的事务。

服务端对CANCEL请求的处理依赖于服务器的类型。一个无状态的proxy会转发这个请求,一个有状态的proxy可能会响应这个请求,并且自己再产生一些CANCEL请求,UAS会响应这个CANCEL请求。16.10节讲述了proxy怎样处理CANCEL请求。

UAS收到CANCEL请求,首先按照8.2节的UAS通用处理方法进行处理。不过,既然CANCEL请求是基于点对点hopbyhop)的,也是不能再提交的,他们不能由服务器为了获得Authorization头域中正确的认证而反复尝试。注意,因此CANCEL请求也不能包含Require头域。

如果根据上边的步骤,UAS不能找到与CANCEL请求相匹配的事务,它应该给CANCEL一个481应答(调用的Leg/Transaction不存在 会话/事务不存在)。如果对应原始请求的事务存在,那么UAS在接收到CANCEL请求的处理就依赖于是否已经给这个原始请求发出了终结应答。如果已经发出了,不会对CANCEL请求对应的原始请求做任何处理,不会更改任何会话状态,不会对原始请求的应答做任何处理。如果UAS没有发出对原始请求的终结应答,它会依赖于CANCEL所取消的原始请求方法。如果原始请求方法是INVITEUAS应当立刻响应INVITE一个487(请求终止)。本协议中,对CANCEL取消的其它本协议中定义的方法没有约定。

不管原先请求的方法是什么,只要CANCEL匹配一个事务,UAS就响应CANCEL请求一个200OK)应答。这个应答根据8.2.6节约定构造。注意,给CANCEL应答的To tag和给原始请求的应答的To tag应该是一样的。对CANCEL的应答会通过服务端transaction来传送。

阅读(6331) | 评论(2)


版权声明:编程爱好者网站为此博客服务提供商,如本文牵涉到版权问题,编程爱好者网站不承担相关责任,如有版权问题请直接与本文作者联系解决。谢谢!

评论

loading...
您需要登录后才能评论,请 登录 或者 注册