如果在Asterisk中同时呼叫转移,如何获得已回答号码/已回答CLID?

时间:2013-12-23 07:19:57

标签: sip asterisk telephony billing

我有一个问题,已有20个小时的话题,但无法解决。 我无法对呼叫计费的情况,因为在Asterisk中同时呼叫转移的情况下,我无法获得已回答号码的确切CLID。 $ {CDR(src)},$ {CDR(dst)}在这里没有帮助。

我从PSTN +79000000000致电DID +78120000000并致电我们的Asterisk。在星号上,通过相同的中继线将呼叫转发到另一个PSTN +74950000000并在那里应答。在CDR完成通话后,我们可以看到:

src: 79000000000
dst: 78120000000

并且没有关于最后78120000000的信息 - > 74950000000电话

在调用Dial应用程序之前,我可以使用CDR变量存储74950000000:

Set(CDR(fwd)=74950000000);
Dial(SIP/78120000000/74950000000);

然后在CDR完成通话后我们可以看到:

src: 79000000000
dst: 78120000000
fwd: 74950000000

这没关系,因为我可以在拨号前限制最长通话时间,并在挂断后对通话计费。一切都归功于已知的fwd。

sip.conf

[78120000000]
name=78120000000
type=peer
host=sip.provider.com

extensions.ael

context sequential {
   _.=> {
       Set(CDR(fwd)=74950000000);
       Dial(SIP/78120000000/74950000000);
       Hangup();
    }
    h => {
       Set(BILL_THE_CALL=${ODBC_BILL_THE_CALL()});
       // billing is easily executed thanks to logged fwd in CDR
    }
  }

但是在同时呼叫转发的情况下,这是不可能的:

  context simultaneous {
   _.=> {
       // can't set fwd before call completion, because don't know 
       // if my_cell_phone or softphone will answer
       // my_cell_phone costs 5 cents/min, softfone is free of charge
       Dial(SIP/78120000000/74950000000&SIP/softphone);
       Hangup();
   }
   h => {
       Set(BILL_THE_CALL=${ODBC_BILL_THE_CALL()});
       // billing is impossible because fwd is not logged to CDR
   }
 }

在CDR中的呼叫完成时,我们可以看到相同的情况,如顺序情况,没有fwd:

src: 79000000000
dst: 78120000000

并且没有关于最后78120000000的信息 - > 74950000000或软电话

那么,你知道如何获得已回答的用户名,回答号码,回答CLID,以便能够对通话收费吗?

http://www.voip-info.org/wiki/view/Asterisk+variables

http://www.voip-info.org/wiki/view/Asterisk+func+channel

等。链接对我没有任何帮助。

在通话中我也可以申请

sip show channel faf7767642

并查看包含我的前辈号码的频道用户名,起源uri等,但是我无法通过拨号方案从那里获取它们。但是当我打电话时:

NoOp(${CHANNEL(username)});
它没有显示任何内容。有什么想法吗?不敢相信我错过了一些明显的东西。 谢谢!

1 个答案:

答案 0 :(得分:0)

是的,感谢在Dial()命令期间执行M(x)执行,并在该宏-x上下文中使用Set(GLOBAL(var)= $ {CHANNEL(peername)})。

context macro-give-me-answered-clid {
    _. => {
        Set(GLOBAL(simultaneous_call_answered_peer)=${CHANNEL(peername)});
    }
}

context simultaneous {
   _.=> {
     // can't set fwd before call completion, because don't know 
     // if my_cell_phone or softphone will answer
     // my_cell_phone costs 5 cents/min, softfone is free of charge
     Dial(SIP/78120000000/74950000000&SIP/softphone,,M(give-me-answered-clid));
     Hangup();
   }

   h => {
     Set(CDR(fwd)=${simultaneous_call_answered_peer})
     Set(BILL_THE_CALL=${ODBC_BILL_THE_CALL()});
     // billing is ok because fwd is now logged to CDR
   }
} 

也许不是很好,也许是愚蠢的,但是工作,我现在很高兴。 非常感谢你的帮助,artheops!

至于开发没有专业技能的复杂解决方案,那是一个完美的Guy Ritchie对此的回答:

  

变得聪明的唯一方法是打出更聪明的对手。

(c)左轮手枪,2005年。这是获得专家的唯一途径。