《FreeSWITCH: VoIP实战》:拨号计划- Dialplan

转载自:http://www.ctiforum.com/news/guandian/331500.html

拨号计划是 FreeSWITCH 中至关重要的一部分。它的主要作用就是对电话进行路由(从这一点上来说,相当于一个路由表)。说的简明一点,就是当一个用户拨号时,对用户所拨的号码进行分析,进而决定下一步该做什么。当然,实际上,它所能做的比你想象的要强大的多。

  我们在第二章中已经提到过修改过拨号计划,单从配置文件看,还算比较简单直观。实际上,它的概念也不是很复杂。如果你理解正则表达式,那你应该能看懂系统系统自带的大部分的配置。但是,在实际应用中,有许多问题还是常常令初学者感到疑惑。主要的问题是,要理解 Dialplan,还需要了解 FS 是怎样工作的(第五章),API 与 APP 的区别等。

  通过本章,我们除了要了解 Dialplan 的基本概念和运作方式,还要以理论与实践相结合的方式来进行学习,使用初学者能快速上手,有经验的人也能学到新的维护和调试技巧。

  XML Dialplan

  Dialplan 是 FreeSWITCH 中一个抽象的部分,它可以支持多种不同的格式,如类似 Asterisk 的格式(由 mod_dialplan_asterisk提供)。但在实际使用中,用的最多的还是 XML 格式。下面,我们就先讨论这种格式。

  配置文件的结构

  拨号计划的配置文件在 conf/dialplan 中,在前面的章节中我们讲过,它们是在 freeswitch.xml 中,由 <X-PRE-PROCESS cmd="include" data="dialplan/*.xml"/> 装入的。

  拨号计划由多个 Context (上下文/环境)组成。每个 Context 中有多个 Extension (分支,在简单的 PBX 中也可以认为是分机号,但很显然,Extension 涵盖的内容远比分机号多)。所以,Context 就是多个 Extension 的逻辑集合,它相当于一个分组,一个 Context 中的 Extension 与其它 Context 中的 Extension 在逻辑上是隔离的。

  下面是 Dialplan 的完整结构:

<?xml version="1.0"?>
<document type="freeswitch/xml">
  <section name="dialplan" description="Regex/XML Dialplan">
    <context name="default">
         <extension name="Test Extension">
         </extension>
    </context>
  </section>
</document>

  Extension 相当于路由表中的表项,其中,每一个 Extension 都有一个 name 属性。它可以是任何合法的字符串,本身对呼叫流程没有任何影响,但取一个好听的名字,有助于你在查看 Log 时发现它。

  在 Extension 中可以对一些 condition (条件)进行判断,如果满足测试条件所指定的表达式,则执行相对应的 action (动作)。

例如,我们将下列 Extension 配置加入到 conf/dialplan/default.xml 中。并作为第一个 Extension。

<extension name="My Echo Test">
  <condition field="destination_number" expression="^echo|1234$">
    <action application="echo" data=""/>
  </condition>
</extension>

  FreeSWITCH 安装时,提供了很多例子,为了避免与提供的例子冲突,强列建议在学习时把自己写的 Extension 写在最前面。当然我说的最前面并不是 default.xml 的第一行,而是放到第一个 Extension 的位置,就是以下语句的后面(你通常能在第13-14行找到它们):

<include>
  <context name="default">

  用你喜欢的编译器编辑好并存盘后,在 FreeSWITCH 命令行上(Console 或 fs_cli)执行 reloadxml 或按 F6键,使 FreeSWITCH 重新读入你修改过的配置文件。并按 F8 键将 log 级别设置为 DEBUG,以看到详细日志.然后,将软电话注册上,并拨叫 1234 或 echo (大部分软电话都能呼叫字母,如Zoiper,Xlite可以使用空格键切换数字和字母)。

你将会看到很多 Log, 注意如下的行:

Processing Seven <1000>->1234 in context default
parsing [default->My Echo Test] continue=false
Regex (PASS) [Echo Test] destination_number(1234) =~ /^echo|1234$/ break=on-false
Action echo()

  在我的终端上,上面的第一行是以绿色显示的。当然,为了排版方便,我省去了 Log 中的日期以及其它不关键的一些信息。

  第一行,Processing 说明是在处理 Dialplan,Seven 是我的的 SIP 名字,1000 是我的分机号, 1234 是我所拨叫的号码,这里,我直接拨叫了 1234。它完整意思是说,呼叫已经达到路由阶段,要从 XML Dialplan 中查找路由,该呼叫来自 Seven,分机号是1000,它所呼叫的被叫号码是 1234 (或 echo,如果你拨叫 echo 的话)。

  第二行,呼叫进入 parsing (解析XML) 阶段,它首先找到 XML 中的一个 Context,这里是 default(它是在 user directory 中定义的,看第五章。user directory 中有一项 , 说明,如果 1000 这个用户发起呼叫,则它的 context 就是 default,所以要从 XML Dialplan 中的 default 这个 Context 查起)。它首先找到的第一个 Extension 的 name 是 My Echo Test(还记得吧?我们我们把它放到了 Dialplan 的最前面)。continue=false 的意思我们后面再讲。

  第三行,由于该 Extension 中有一个 Condition,它的测试条件是 destination_number,也就是被叫号码,所以, FreeSWITCH 测试被叫号码(这里是 1234)是否与配置文件中的正则表达式相匹配。 ^echo|1234$ 是正则表达式,它匹配 echo 或 1234。所以这里匹配成功,Log 中显示 Regex (PASS)。 当然既然匹配成功了,它就开始执行动作 echo(它是一个 APP),所以你就听到了自己的声音。

  这是最简单的路由查找。前面我已经说了,系统自带了一些 Dialplan 的例子,也许在第二章你已经测试过了。下面,我们试一下系统自带的 echo 的例子。这次,我呼叫的是 9196。在 Log 中,还是从绿色的行开始看:

Processing Seven <1000>->9196 in context default
parsing [default->My Echo Test] continue=false
Regex (FAIL) [Echo Test] destination_number(9196) =~ /^echo|1234$/ break=on-false
parsing [default->unloop] continue=false
Regex (PASS) [unloop] ${unroll_loops}(true) =~ /^true$/ break=on-false
Regex (FAIL) [unloop] ${sip_looped_call}() =~ /^true$/ break=on-false
parsing [default->tod_example] continue=true
Date/Time Match (FAIL) [tod_example] break=on-false
parsing [default->holiday_example] continue=true
Date/Time Match (FAIL) [holiday_example] break=on-false
parsing [default->global-intercept] continue=false
Regex (FAIL) [global-intercept] destination_number(9196) =~ /^886$/ break=on-false
parsing [default->group-intercept] continue=false
Regex (FAIL) [group-intercept] destination_number(9196) =~ /^\*8$/ break=on-false
parsing [default->intercept-ext] continue=false
Regex (FAIL) [intercept-ext] destination_number(9196) =~ /^\*\*(\d+)$/ break=on-false
parsing [default->redial] continue=false
Regex (FAIL) [redial] destination_number(9196) =~ /^(redial|870)$/ break=on-false
parsing [default->global] continue=true
Regex (FAIL) [global] ${call_debug}(false) =~ /^true$/ break=never

parsing [default->fax_receive] continue=false
Regex (FAIL) [fax_receive] destination_number(9196) =~ /^9178$/ break=on-false
parsing [default->fax_transmit] continue=false
Regex (FAIL) [fax_transmit] destination_number(9196) =~ /^9179$/ break=on-false
parsing [default->ringback_180] continue=false
Regex (FAIL) [ringback_180] destination_number(9196) =~ /^9180$/ break=on-false
parsing [default->ringback_183_uk_ring] continue=false
Regex (FAIL) [ringback_183_uk_ring] destination_number(9196) =~ /^9181$/ break=on-false
parsing [default->ringback_183_music_ring] continue=false
Regex (FAIL) [ringback_183_music_ring] destination_number(9196) =~ /^9182$/ break=on-false
parsing [default->ringback_post_answer_uk_ring] continue=false
Regex (FAIL) [ringback_post_answer_uk_ring] destination_number(9196) =~ /^9183$/ break=on-false
parsing [default->ringback_post_answer_music] continue=false
Regex (FAIL) [ringback_post_answer_music] destination_number(9196) =~ /^9184$/ break=on-false
parsing [default->ClueCon] continue=false
Regex (FAIL) [ClueCon] destination_number(9196) =~ /^9191$/ break=on-false
parsing [default->show_info] continue=false
Regex (FAIL) [show_info] destination_number(9196) =~ /^9192$/ break=on-false
parsing [default->video_record] continue=false
Regex (FAIL) [video_record] destination_number(9196) =~ /^9193$/ break=on-false
parsing [default->video_playback] continue=false
Regex (FAIL) [video_playback] destination_number(9196) =~ /^9194$/ break=on-false
parsing [default->delay_echo] continue=false
Regex (FAIL) [delay_echo] destination_number(9196) =~ /^9195$/ break=on-false
parsing [default->echo] continue=false
Regex (PASS) [echo] destination_number(9196) =~ /^9196$/ break=on-false
Action answer()
Action echo()


### 回答1: 《FreeSWITCH: VOIP实战》是一本非常好的技术书籍,它详细介绍了如何使用FreeSWITCH构建高可用性、高性能的VoIP解决方案。该书的作者是Anthony Minessale、Darren Schreiber和Michael S. Collins。 本书的目的是教读者学会使用FreeSWITCH构建功能丰富、灵活可扩展的电话系统。该书从基础概念开始,包括了FreeSWITCH的架构、模块、配置和调优等方面的内容。接着,书中介绍了如何使用FreeSWITCH来实现常见的电话功能,例如IVR、语音信箱、音频会议、呼叫中心、呼叫转移和呼叫路由等。 此外,本书还涵盖了FreeSWITCH的高级功能,例如多租户支持、安全性、彩铃、录音和统计数据收集等。书中还提供了大量的示例代码和配置文件,读者可以参考并直接应用到实际项目中。 总的来说,《FreeSWITCH: VOIP实战》是一本非常有用的技术书籍,它涵盖了FreeSWITCH的方方面面,非常适合VOIP开发人员、系统管理员和网络工程师阅读。在阅读完本书后,读者将能够熟练地使用FreeSWITCH构建高性能、高可用性的VOIP系统,从而为企业提供更好的通讯服务。 ### 回答2: 《FreeSWITCH: VoIP实战》PDF是一本介绍FreeSWITCH开源软件的VoIP技术书籍。它由Anthony Minessale、Darren Schreiber和Michael S. Collins所著。本书的读者目标是想要深入了解FreeSWITCH工作原理和使用方法的VoIP从业人员。 本书首先介绍了VoIP的基础知识和一些常用的协议和标准。接着,书中详细讲解了FreeSWITCH架构和组件,如何安装、配置和管理FreeSWITCH,以及如何使用FreeSWITCH实现呼叫控制、音频处理、录音等功能。此外,该书还介绍了FreeSWITCH的高级应用,如群组呼叫、多方会议、IVR等。 《FreeSWITCH: VoIP实战》PDF的亮点在于其深入浅出的讲解方式和丰富的案例分析。书中许多实例都是作者亲身经历的,能够帮助读者更好地理解FreeSWITCH的工作原理和解决实际问题的方法。此外,该书还在最后一章中介绍了一些FreeSWITCH的扩展和集成,如何与Asterisk、Kamailio等软交换平台交互,以及如何使用WebRTC实现浏览器间的实时音频通话等。 总之,如果您是一名VoIP从业人员,希望深入了解FreeSWITCH技术并应用于实际项目中,那么《FreeSWITCH: VoIP实战》PDF无疑是一本值得阅读的书籍。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值