拨号计划配置与呼叫路由
📖 返回主文档
XML 拨号计划配置、呼叫路由逻辑和拨号计划变量的综合指南。
相关文档
核心文档
呼叫处理流程
- 🔢 号码转换 - E.164 规范化(发生在拨号计划之前)
- 👥 Sh 接口 - 为拨号计划变量检索的用户数据
- 📡 SS7 MAP - 拨号计划变量中的 MSRN/HLR 数据
- 💳 在线计费 - 呼叫流程中的 OCS 授权
服务实现
监控
拨号计划配置 / 呼叫路由
TAS 使用与标准电信 XML 拨号计划格式兼容的 XML 拨号计划,变量由 TAS 填充。 这意味着您可以根据需要定义自己的拨号计划,包含运营商的业务逻辑,但拥有所有所需的数据,如存储库数据、SS7 路由信息、IMPI / IMPU 身份、拨号计划规范化等。
拨号计划写入 priv/templates,形式如下:
mo_dialplan.xml- 移动发起呼叫拨号计划mo_emergency_dialplan.xml- 移动发起紧急呼叫拨号计划mt_dialplan.xml- 移动终止呼叫拨号计划
您可以从 Web UI 内部查看拨号计划。

在 XML 被解析之前,TAS 设置了各种变量,这些变量在呼叫开始时以其当前值打印到日志中,在定义自己的呼叫逻辑时非常有帮助。
FreeSWITCH XML 拨号计划基础
OmniTAS 使用与 FreeSWITCH 项目相同的 XML 呼叫路由系统,允许灵活的呼叫路由以满足您的需求。
本节解释核心概念并提供实际示例。
基本结构
拨号计划由 扩展 组成,包含 条件 和 操作:
<extension name="description-of-what-this-does">
<condition field="${variable}" expression="regex-pattern">
<action application="app_name" data="parameters"/>
<anti-action application="app_name" data="parameters"/>
</condition>
</extension>
扩展 按顺序从上到下进行评估。当条件匹配时,其操作执行。
条件和正则匹配
条件测试变量与正则表达式。如果正则匹配,则执行操作;如果不匹配,则执行反操作。
基本精确匹配:
<condition field="${tas_destination_number}" expression="2222">
<action application="log" data="INFO Calling voicemail access number"/>
</condition>
多个号码匹配:
<condition field="${tas_destination_number}" expression="^(2222|3444|3445)$">
<action application="log" data="INFO Calling special service"/>
</condition>
带捕获组的模式匹配:
<condition field="${tas_destination_number}" expression="^1(8[0-9]{9})$">
<!-- 匹配 1 后跟 8 和 9 个数字 -->
<action application="log" data="INFO Matched toll-free: $1"/>
<action application="bridge" data="sofia/gateway/trunk/${tas_destination_number}"/>
</condition>
前缀匹配:
<condition field="${tas_destination_number}" expression="^00">
<!-- 匹配以 00 开头的任何号码(国际) -->
<action application="log" data="INFO International call detected"/>
</condition>
范围匹配:
<condition field="${msisdn}" expression="^5551241[0-9]{4}$">
<!-- 匹配 55512410000 到 55512419999 -->
<action application="log" data="INFO Subscriber in range"/>
</condition>
操作与反操作
操作 在条件匹配时执行。反操作 在条件不匹配时执行。
<condition field="${cli_withheld}" expression="true">
<!-- 如果 CLI 被隐藏则执行 -->
<action application="set" data="effective_caller_id_number=anonymous"/>
<action application="set" data="origination_privacy=hide_number"/>
<!-- 如果 CLI 未被隐藏则执行 -->
<anti-action application="log" data="DEBUG CLI is normal"/>
<anti-action application="set" data="effective_caller_id_number=${msisdn}"/>
</condition>
continue="true" 属性
默认情况下,当扩展的条件匹配时,拨号计划停止处理后续扩展。continue="true" 属性允许处理继续到下一个扩展。
没有 continue(默认行为):
<extension name="First-Check">
<condition field="${tas_destination_number}" expression="^(.*)$">
<action application="log" data="INFO Processing call"/>
</condition>
</extension>
<extension name="Never-Reached">
<!-- 这永远不会执行,因为上一个扩展匹配 -->
<condition field="${tas_destination_number}" expression="^(.*)$">
<action application="log" data="INFO This won't print"/>
</condition>
</extension>
使用 continue="true":
<extension name="Print-Vars" continue="true">
<condition field="${tas_destination_number}" expression="^(.*)$">
<action application="info" data=""/>
</condition>
</extension>
<extension name="Check-Balance" continue="true">
<condition field="${hangup_case}" expression="OUTGOING_CALL_BARRED">
<action application="log" data="ERROR Insufficient balance"/>
<action application="hangup" data="${hangup_case}"/>
</condition>
</extension>
<extension name="Route-Call">
<!-- 这个扩展仍然会被评估 -->
<condition field="${tas_destination_number}" expression="^(.*)$">
<action application="bridge" data="sofia/gateway/trunk/${tas_destination_number}"/>
</condition>
</extension>
使用 continue="true" 用于:
- 日志/调试扩展
- 设置适用于多种场景的变量
- 不路由呼叫的验证检查
常见应用
呼叫控制
answer - 接听呼叫(发送 200 OK)
<action application="answer" data=""/>
hangup - 以特定原因终止呼叫
<action application="hangup" data="NORMAL_CLEARING"/>
<action application="hangup" data="USER_BUSY"/>
<action application="hangup" data="NO_ANSWER"/>
bridge - 将呼叫连接到另一个目的地
<!-- 桥接到外部网关 -->
<action application="bridge" data="sofia/gateway/trunk/+12125551234"/>
<!-- 桥接到具有编解码器优先级的内部分机 -->
<action application="bridge" data="{absolute_codec_string=AMR-WB,AMR,PCMA}sofia/internal/sip:user@domain.com"/>
<!-- 带超时的桥接 -->
<action application="bridge" data="{originate_timeout=30}sofia/gateway/trunk/${tas_destination_number}"/>
变量和通道数据
set - 设置通道变量
<action application="set" data="my_variable=my_value"/>
<action application="set" data="sip_h_X-Custom-Header=CustomValue"/>
<action application="set" data="effective_caller_id_number=anonymous"/>
unset - 移除通道变量
<action application="unset" data="sip_h_P-Asserted-Identity"/>
export - 设置变量并导出到 B-leg(桥接呼叫)
<action application="export" data="sip_h_X-Account-Code=ABC123"/>
媒体和提示
playback - 播放音频文件
<action application="playback" data="/sounds/en/us/callie/misc/8000/out_of_credit.wav"/>
<action application="playback" data="$${base_dir}/sounds/custom_prompt.wav"/>
sleep - 暂停指定毫秒
<action application="sleep" data="1000"/> <!-- 暂停 1 秒 -->
echo - 将音频回显给呼叫者(测试)
<action application="echo" data=""/>
conference - 将呼叫放入会议
<action application="conference" data="room-${destination_number}@wideband"/>
语音邮件
voicemail - 访问语音邮件系统
<!-- 为邮箱留语音邮件 -->
<action application="voicemail" data="default default ${msisdn}"/>
<!-- 使用授权检查语音邮件 -->
<action application="voicemail" data="check auth default default ${msisdn}"/>
日志和调试
log - 写入日志文件
<action application="log" data="INFO Processing call from ${msisdn}"/>
<action application="log" data="DEBUG Destination: ${tas_destination_number}"/>
<action application="log" data="ERROR Call failed with cause: ${hangup_cause}"/>
info - 将所有通道变量转储到日志
<action application="info" data=""/>
杂项应用
say - 文本转语音号码读取
<action application="say" data="en number iterated ${tas_destination_number}"/>
send_dtmf - 发送 DTMF 音调
<action application="send_dtmf" data="1234#"/>
实际示例
紧急服务路由:
<extension name="Emergency-911">
<condition field="${tas_destination_number}" expression="^(911|112)$">
<action application="log" data="ALERT Emergency call from ${msisdn}"/>
<action application="answer" data=""/>
<action application="playback" data="/sounds/emergency_services_transfer.wav"/>
<action application="bridge" data="sofia/gateway/emergency_gw/${tas_destination_number}"/>
</condition>
</extension>
基于余额的条件路由:
<extension name="Check-Credit">
<condition field="${hangup_case}" expression="OUTGOING_CALL_BARRED">
<action application="answer" data=""/>
<action application="playback" data="/sounds/out_of_credit.wav"/>
<action application="hangup" data="CALL_REJECTED"/>
</condition>
</extension>
On-Net 与 Off-Net 路由:
<extension name="Route-Decision">
<condition field="${on_net_status}" expression="true">
<!-- On-net: 通过 TAS 路由 -->
<action application="log" data="INFO Routing to on-net subscriber"/>
<action application="bridge" data="sofia/internal/+${tas_destination_number}@10.179.3.60"/>
<anti-action application="log" data="INFO Routing off-net"/>
<anti-action application="bridge" data="sofia/gateway/trunk/+${tas_destination_number}"/>
</condition>
</extension>
匿名来电 ID 处理:
<extension name="CLI-Privacy" continue="true">
<condition field="${cli_withheld}" expression="true">
<action application="set" data="effective_caller_id_name=anonymous"/>
<action application="set" data="effective_caller_id_number=anonymous"/>
<action application="set" data="origination_privacy=hide_number"/>
</condition>
</extension>
无人接听时的语音邮件:
<extension name="Try-Bridge-Then-VM">
<condition field="${tas_destination_number}" expression="^(555124115\d{2})$">
<action application="set" data="call_timeout=30"/>
<action application="bridge" data="sofia/internal/${tas_destination_number}@domain.com"/>
<!-- 如果桥接失败,转到语音邮件 -->
<action application="log" data="INFO Bridge failed, routing to voicemail"/>
<action application="answer" data=""/>
<action application="voicemail" data="default default ${tas_destination_number}"/>
</condition>
</extension>
号码范围路由:
<extension name="Local-Numbers">
<condition field="${tas_destination_number}" expression="^([2-9]\d{2})$">
<!-- 3 位本地分机 200-999 -->
<action application="log" data="INFO Local extension: $1"/>
<action application="bridge" data="sofia/internal/$1@pbx.local"/>
</condition>
</extension>
<extension name="National-Numbers">
<condition field="${tas_destination_number}" expression="^555\d{7}$">
<!-- 国家移动号码 -->
<action application="log" data="INFO National mobile call"/>
<action application="bridge" data="sofia/gateway/national_trunk/${tas_destination_number}"/>
</condition>
</extension>
<extension name="International">
<condition field="${tas_destination_number}" expression="^00\d+$">
<!-- 以 00 开头的国际呼叫 -->
<action application="log" data="INFO International call"/>
<action application="bridge" data="sofia/gateway/intl_trunk/${tas_destination_number}"/>
</condition>
</extension>
进一步文档
有关每个应用程序的完整详细信息:
- FreeSWITCH 拨号计划文档: https://freeswitch.org/confluence/display/FREESWITCH/Dialplan
- FreeSWITCH mod_dptools: https://freeswitch.org/confluence/display/FREESWITCH/mod_dptools (完整应用程序参考)
- 正则表达式参考: https://freeswitch.org/confluence/display/FREESWITCH/Regular+Expression
- 通道变量: https://freeswitch.org/confluence/display/FREESWITCH/Channel+Variables
FreeSWITCH 维基包含每个拨号计划应用程序的详细文档,包括所有参数和用例。
拨号计划变量
TAS 在 XML 拨号计划逻辑中设置的变量:
常见变量(所有呼叫类型)
初始设置:
destination_number- 转换后的目的号码tas_destination_number- 转换后的目的号码effective_caller_id_number- 转换后的源号码
紧急呼叫
hangup_case- "none"ims_private_identity- 私有用户身份ims_public_identity- 公共用户身份msisdn- 订阅者号码(去掉 +)imsi- 来自私有身份的 IMSIims_domain- 来自私有身份的域
MT 呼叫(移动终止)
ims_private_identity- 私有用户身份ims_public_identity- 公共用户身份msisdn- 订阅者号码(去掉 +)imsi- 来自私有身份的 IMSIims_domain- 来自私有身份的域call_forward_all_destination- CFA 目的地或 "none"call_forward_not_reachable_destination- CFNRc 目的地scscf_address- S-CSCF 地址或 "none"scscf_domain- S-CSCF 域或 "none"no_reply_timer- 无回复超时hangup_case- "none" 或 "UNALLOCATED_NUMBER"msrn- 来自 PRN 的 MSRN(如果漫游)或来自 SRI 的转发号码(如果呼叫转移处于活动状态)tas_destination_number- 路由目的地覆盖(设置为 MSRN 或转发号码)
MO 呼叫(移动发起)
hangup_case- "none"、"OUTGOING_CALL_BARRED" 或 "UNALLOCATED_NUMBER"ims_private_identity- 私有用户身份ims_public_identity- 公共用户身份msisdn- 订阅者号码(去掉 +)imsi- ���自私有身份的 IMSIims_domain- 来自私有身份的域allocated_time- OCS 分配的时间(如果启用在线计费)cli_withheld- "true" 或 "false" 字符串on_net_status- "true" 或 "false" 字符串(目的地是否在网内)msrn- 漫游订阅者的 MSRN(如果适用)tas_destination_number- MSRN 覆盖(如果漫游)
紧急呼叫
紧急呼叫通过 emergency_call_codes 配置参数进行控制,并在呼叫授权期间自动检测。
配置
在您的 TAS 配置文件中配置紧急呼叫代码:
配置参数:
emergency_call_codes:要检测的紧急服务号码列表- 常见代码: "911"(美国)、"112"(欧盟)、"000"(澳大利亚)、"999"(英国)、"sos"
- 这些代码在 SIP 紧急 URN(例如,
<urn:service:sos>)之外进行检查 - 系统对目的号码执行 精确匹配 比较
示例配置值:
- 美国部署:
["911", "933"]- 911 用于紧急情况,933 用于测试 - 欧洲部署:
["112", "999"] - 澳大利亚部署:
["000", "106"]- 000 用于紧急情况,106 用于文本中继 - 多区域:
["911", "112", "000", "sos"]
紧急检测工作原理
系统检查两个条件:
- SIP URI 紧急服务 URN:检测
<urn:service:sos>或任何包含 "service:sos" 的 URI - 目的号码匹配:将
Caller-Destination-Number与配置的emergency_call_codes进行比较
如果 任一条件 为真,则呼叫被分类为紧急。
处理流程
呼叫流程详细信息:
- 呼叫到达 TAS
- 授权模块检查目的地与紧急模式
- 如果检测到紧急情况:
- 呼叫类型设置为
:emergency - 使用
mo_emergency_dialplan.xml模板 - OCS 授权通常被绕过
- 呼叫路由到 PSAP 网关
- 呼叫类型设置为
- 指标记录为
call_type: emergency标签
拨号计划路由
在 priv/templates/mo_emergency_dialplan.xml 中定义紧急呼叫的路由。此模板确定如何根据您的市场需求将呼叫路由到您的 PSAP(公共安全应答点)网关或 SIP URI。
示例紧急拨号计划:
<extension name="Emergency-SOS">
<condition field="${destination_number}" expression="^(911|912|913|sos)$">
<action application="log" data="ALERT Emergency call from ${msisdn}"/>
<action application="answer" data=""/>
<action application="bridge" data="sofia/gateway/psap_gw/${destination_number}"/>
</condition>
</extension>
最佳实践
- 始终在紧急代码列表中包含 "sos" 以确保 SIP URN 兼容性
- 包括您管辖区内的所有本地紧急号码(例如,911、112、000、999)
- 定期测试紧急路由,使用呼叫模拟器
- 绕过 OCS 以确保紧急呼叫始终连接(通过
skipped_regex配置) - 配置 PSAP 网关,确保高可用性和冗余
- 监控紧急呼叫指标 以确保系统可靠性
On-Net 移动发起呼叫到 On-Net 移动终止订阅者
当订阅者呼叫您网络上的另一位订阅者(在网呼叫)时,正确的方法是将 MO 呼叫路由回 TAS 进行 MT 处理。这确保被叫方接收到完整的 MT 呼叫处理,包括呼叫转移、语音邮件、漫游的 MSRN 路由以及所有其他订阅者服务。
为什么将 MO 路由到 MT?
没有 MT 处理(直接路由):
- 被叫方的呼叫转移设置被忽略
- 无法在无人接听时转移到语音邮件
- 无法为漫游订阅者进行 MSRN 路由
- 缺少订阅者服务逻辑
有 MT 处理(路由回 TAS):
- 完整的呼叫转移支持(CFU、CFB、CFNRy、CFNRc)
- 忙/无人接听时的语音邮件
- 漫游 CS 订阅者的 MSRN 路由
- 完整的订阅者服务体验
- 对双方的正确呼叫状态跟踪
实施
MO 拨号计划检查目的地是否在网(由您的 TAS 提供),如果是,则将呼叫路由回 TAS 本身。TAS 将其视为新的 MT 呼叫,并通过 mt_dialplan.xml 模板处理。
示例拨号计划片段:
<extension name="On-Net-Route">
<condition field="${on_net_status}" expression="true">
<action application="log" data="DEBUG On-Net MO call - Routing back into TAS" />
<!-- 清理内部路由的头部 -->
<action application="set" data="sip_copy_multipart=false"/>
<action application="set" data="sip_h_Request-Disposition=no-fork"/>
<!-- 路由回 TAS(变为 MT 呼叫) -->
<action application="bridge"
data="{absolute_codec_string='AMR-WB,AMR,PCMA,PCMU',originate_retries=1,originate_timeout=60,sip_invite_call_id=${sip_call_id}}sofia/internal/${tas_destination_number}@${sip_local_network_addr}" />
<action application="hangup" data="" />
</condition>
</extension>
关键参数:
${sip_local_network_addr}- TAS IP 地址(例如,10.179.3.60)${tas_destination_number}- ���叫方的 MSISDNsip_invite_call_id=${sip_call_id}- 保留呼叫 ID 以便跟踪sip_copy_multipart=false- 防止多部分消息复制sip_h_Request-Disposition=no-fork- 确保顺序处理
呼叫流程:
重要配置:
- TAS IP(例如,
10.179.3.60)必须在您的allowed_sbc_source_ips配置列表中 - 这允许 TAS 从自身接收呼叫以进行 MT 处理
- 如果没有此项,TAS 将拒绝来自未授权源的呼叫
MSRN 用于 2G/3G 漫游订阅者的使用
��订阅者在 2G/3G 电路交换(CS)网络中漫游时,TAS 必须获取 MSRN(移动台漫游号码)以将来电路由到订阅者的当前位置。本节解释 MSRN 检索和路由的工作原理。
什么是 MSRN?
MSRN(移动台漫游号码) 是由访问网络的 VLR(访客位置寄存器)分配的临时路由号码,用于将呼叫路由到漫游订阅者。它充当指向订阅者在 CS 网络中当前位置的临时目的号码。
MSRN 检索流程
TAS 通过 SS7 MAP(移动应用部分)协议使用两步流程检索 MSRN 数据:
实施细节
第一步:发送路由信息(SRI)
TAS 通过 SS7 MAP 查询 HLR 以获取被叫订阅者的路由信息。
SRI 响应场景:
-
SRI 中直接包含 MSRN - 漫游订阅者的 MSRN 已可用
- 响应包括:MSISDN、GMSC、IMSI 和 MSRN
- 示例 MSRN:
61412345678(澳大利亚移动号码格式)
-
IMSI + VLR 号码 - 订阅者在 CS 网络中注册(需要 PRN)
- 响应包括:MSISDN、GMSC、IMSI 和 MSC/VLR 号码
- 表明订阅者在 CS 网络中,但必须请求 MSRN
-
仅 IMSI(无 VLR) - 订阅者不在 CS 网络中(仅 IMS/PS)
- 响应包括:MSISDN、GMSC、IMSI
- 表明订阅者注册在 IMS/4G 中,而不在 CS 网络中
-
呼叫转发处于活动状态 - SRI 返回转发信息
- 响应包括转发原因(无条件、忙、无人接听、不可达)
- 响应包括转发到的号码
第二步:提供漫游号码(PRN)- 如果需要
如果 SRI 返回 IMSI + VLR,但没有 MSRN,TAS 将向 VLR 发送 PRN 请求以获取 MSRN。
VLR 从其池中���配一个临时 MSRN,并将其返回给 TAS。此 MSRN 仅在此特定呼叫设置期间有效。
示例 PRN 响应: MSRN 61412345678
拨号计划变量: msrn
一旦通过 SS7 MAP 检索到 MSRN,它将作为拨号计划变量设置,可以在 MT 拨号计划中使用。
变量: ${msrn}
- 类型: 字符串(不带前导 + 的 E.164 号码)
- 示例:
"61412345678"(澳大利亚移动格式) - 用法: 将呼叫路由到 CS 漫游订阅者
- 由: 在 MT 呼叫处理期间的 HLR 数据检索过程设置
在 mt_dialplan.xml 中路由到 MSRN
MSRN 变量在 MT 拨号计划模板中用于将呼叫路由到漫游订阅者。
拨号计划逻辑:
- 检查 MSRN:扩展检查
msrn变量是否设置(包含数字) - 设置超时参数:
- 进度超时:接收早期媒体的 10 秒
- 桥接应答超时:使用订阅者配置的无人接听计时器
- 桥接到 MSRN:通过 CS 网关将呼叫路由到 MSRN
- 使用
ignore_early_media=ring_ready以获得一致的响铃 - 编解码器优先级:AMR(移动)、PCMA/PCMU(固定线路)
- 网关:
sofia/gateway/CS_Gateway/+${msrn}
- 使用
- 失败时的回退:如果桥接失败,则路由到呼叫转发目的地
示例拨号计划片段:
<extension name="Route-to-CS-MSRN" continue="false">
<condition field="msrn" expression="^(\d+)$">
<!-- 配置超时 -->
<action application="set" data="progress_timeout=10" />
<action application="set" data="bridge_answer_timeout=${no_reply_timer}" />
<!-- 通过 CS 网关桥接到 MSRN -->
<action application="bridge"
data="{ignore_early_media=ring_ready,absolute_codec_string='AMR,PCMA,PCMU',continue_on_fail=true,originate_retries=1,originate_timeout=60}sofia/gateway/CS_Gateway/+${msrn}" />
<!-- 回退到语音邮件/呼叫转发 -->
<action application="bridge"
data="sofia/internal/${call_forward_not_reachable_destination}@${local_ip_v4}" />
</condition>
</extension>
关键点
- MSRN 是临时的 - 仅在呼叫设置期间有效
- 仅用于 CS 网络 - MSRN 用于 2G/3G 漫游,而不用于 VoLTE/IMS 漫游
- 在 MT 流程中的优先级 - MSRN 检查发生在标准 IMS 路由之前
- 回退到转发 - 如果 MSRN 桥接失败,则路由到呼叫转发目的地
- HLR 优先于 Sh - HLR 中的 MSRN 优先于 Sh 订阅者数据
配置
必须在 TAS 配置中启用 SS7 MAP 集成:
所需设置:
- enabled:设置为
true以启用 SS7 MAP 查询 - http_map_server_url_base:您的 SS7 MAP 网关的 URL(例如,
"http://10.1.1.100:5001") - gmsc:用于 SRI/PRN 请求的网关 MSC 号码(例如,
"61400000000") - timeout_ms:查询超时(默认:5000 毫秒)
请参见 SS7 MAP 文档 以获取完整的配置详细信息。
呼叫转发数据使用
呼叫转发设置决定了当主要目的地不可用时呼叫如何路由。TAS 从两个来源检索呼叫转发数据:Sh 接口(HSS)和 SS7 MAP(HLR),HLR 数据优先。
呼叫转发类型
系统支持四种类型的呼叫转发:
| 转发类型 | 变量 | 活动时 |
|---|---|---|
| 无条件呼叫转发 (CFU) | call_forward_all_destination | 始终立即转发所有呼叫 |
| 忙时呼叫转发 (CFB) | call_forward_not_reachable_destination | 订阅者线路忙 |
| 无人接听呼叫转发 (CFNRy) | call_forward_not_reachable_destination | 订阅者在超时内未接听 |
| 不可达呼叫转发 (CFNRc) | call_forward_not_reachable_destination | 订阅者不可达/离线 |
数据来源
1. Sh 接口(HSS)
静态配置 存储在 HSS 订阅者配置文件中。
TAS 在呼叫处理期间通过 Sh 接口从 HSS 检索呼叫转发设置。这些是为订阅者配置的默认设置。
示例检索数据:
call_forward_all_destination:CFU 目的地(例如,"61412345678")call_forward_not_reachable_destination:CFB/CFNRy/CFNRc 目的地(例如,"61487654321")no_reply_timer:触发 CFNRy 的秒数(例如,"20")
2. SS7 MAP(HLR)
实时数据 来自 HLR,可能与 HSS 不同,如果订阅者通过 USSD/MMI 代码(例如,拨打 *21* 代码)更改了设置。
TAS 在呼叫设置期间通过 SS7 MAP 查询 HLR 以获取当前/活动的转发设置。
HLR 转发响应包括:
- forwarded_to_number:转发的目的号码(例如,
"61412345678") - reason:转发类型(无条件、忙、无人接听、不可达)
- notification flags:是否通知呼叫方、转发方等。
映射到拨号计划变量:
- 如果原因是 无条件 → 设置
call_forward_all_destination - 如果原因是 忙、无人接听或不可达 → 设置
call_forward_not_reachable_destination
变量合并优先级
HLR 数据覆盖 Sh 数据 当两者都存在时。
TAS 在 MT 呼叫处理期间从两个来源检索订阅者数据:
- 首先,通过 Sh 接口从 HSS 检索静态配置
- 然后,通过 SS7 MAP 查询 HLR 以获取实时设置
- 合并数据,HLR 值优先于 Sh 值
这确保了即使 HSS 尚未更新,最近的���阅者更改(通过 USSD 代码)也会被尊重。
拨号计划变量
在 MT 呼叫中可用:
| 变量 | 类型 | 示例 | 描述 |
|---|---|---|---|
call_forward_all_destination | 字符串 | "61412345678" | CFU 目的号码 |
call_forward_not_reachable_destination | 字符串 | "61487654321" | CFB/CFNRy/CFNRc 目的号码 |
no_reply_timer | 字符串 | "20" | CFNRy 的超时时间(秒) |
默认值:
- 如果未配置:
"none"(字符串) - 检查存在性:使用正则表达式
^(?!none$).*匹配任何值,除了 "none"
在 mt_dialplan.xml 中的呼叫转发
示例 1:无条件呼叫转发 (CFU)
立即将所有来电路由到转发目的地。转发目的地通常是一个非网号码,因此使用外部网关。
使用的网关: sofia/gateway/ExternalSIPGateway(您的 PSTN/互联网网关)
模板示例:
<extension name="Check-Call-Forward-All">
<condition field="${call_forward_all_destination}" expression="^(?!none$).*">
<action application="log" data="INFO Call Forward All Set to redirect to ${call_forward_all_destination}" />
<!-- 设置历史信息头以进行呼叫转发 -->
<action application="set" data="sip_h_History-Info=<sip:${destination_number}@${ims_domain}>;index=1.1" />
<!-- 标记呼叫 ID 以指示呼叫转发类型 -->
<action application="set" data="sip_call_id=${sip_call_id};CALL_FORWARD_UNCONDITIONAL" />
<!-- 桥接到非网转发目的地 -->
<action application="bridge"
data="{absolute_codec_string='AMR-WB,AMR,PCMA,PCMU',originate_retries=1,originate_timeout=60}sofia/gateway/ExternalSIPGateway/+${call_forward_all_destination}" />
</condition>
</extension>
关键点:
- 使用外部网关,因为转发通常是到非网号码
- 用
;CALL_FORWARD_UNCONDITIONAL标记呼叫 ID 以便跟踪 - 设置
History-Info头以识别原始被叫号码 - 示例:订阅者
61412345678将 CFU 转发到61487654321- 所有呼叫立即转发
示例 2:无人接听/不可达呼叫转发
在桥接到主要目的地失败时作为回退使用(订阅者未接听、忙或不可达)。
示例拨号计划片段:
<!-- 在桥接到 MSRN 或 IMS 失败后... -->
<action application="log" data="INFO Failed to bridge Call - Routing to Call Forward No-Answer Destination" />
<!-- 设置历史信息以指示转发 -->
<action application="set" data="sip_h_History-Info=<sip:${destination_number}@${ims_domain}>;index=1.1" />
<!-- 路由到转发目的地 -->
<action application="bridge"
data="{absolute_codec_string='AMR,PCMU,PCMA',originate_timeout=65}sofia/gateway/ExternalSIPGateway/${call_forward_not_reachable_destination}" />
示例场景:
- 订阅者
61412345678将 CFNRy 转发到语音邮件号码61487654321 - 来电尝试联系订阅者
- 20 秒后无人接听(no_reply_timer)
- 呼叫转发到
61487654321,同时保留原始目的地的 History-Info 头
History-Info 头
History-Info SIP 头跟踪呼叫转发:
<action application="set" data="sip_h_History-Info=<sip:${destination_number}@${ims_domain}>;index=1.1" />
目的:
- 指示呼叫原本是针对
${destination_number} - 允许下游系统识别转发呼叫
- 被语音邮件系统用于存储到正确的邮箱
语音邮件路由中的示例:
<extension name="Voicemail Route" continue="false">
<condition field="${tas_destination_number}" expression="^(555121|555122)$">
<!-- 从历史信息中提取电话号码 -->
<action application="set" data="history_info_value=${sip_i_history_info}"/>
<action application="log" data="DEBUG Called Voicemail Deposit Number for ${history_info_value}" />
<!-- 将语音邮件存储到原始被叫方,而不是语音邮件号码 -->
<action application="voicemail" data="default default ${history_info_value}"/>
</condition>
</extension>
工作原理:
- 语音邮件服务号码:
555121、555122(通用短代码) - 当呼叫转发到语音邮件时,History-Info 包含原始目的地
- 语音邮件系统从 History-Info 头中提取原始号码
- 语音邮件存储到原始被叫方的邮箱,而不是语音邮件服务号码
最佳实践
- 始终检查 "none" - 使用正则表达式
^(?!none$).*避免路由到字面字符串 "none" - 设置历史信息 - 在转发时始终设置以进行适当的呼叫跟踪
- 使用 continue_on_fail - 允许在主要路由失败时回退到转发
- 调整 CLI 格式 - 国家与国际前缀格式化(参见来电 ID 部分)
- 测试转发循环 - 确保转发目的地不会创建路由循环
来电 ID(CLI)管理
TAS 在整个呼叫流程中管理来电线识别(CLI)的呈现和格式,处理隐私请求、前缀规范化和网络特定格式要求。
CLI 变量
拨号计划中的核心 CLI 变量:
| 变量 | 用法 | 示例 |
|---|---|---|
msisdn | 订阅者的号码(无 +) | "61412345678" |
effective_caller_id_number | 显示的来电号码 | "+61412345678" 或 "anonymous" |
effective_caller_id_name | 显示的来电姓名 | "+61412345678" 或 "anonymous" |
origination_caller_id_number | 外发腿的 CLI | "+61412345678" |
caller_id_number | 标准 FreeSWITCH CLI 变量 | "+61412345678" |
sip_from_user | SIP From 头部用户部分 | "0412345678" 或 "+61412345678" |
cli_withheld | 隐私标志 | "true" 或 "false"(字符串) |
origination_privacy | 隐私设置 | "hide_number" |
CLI 隐私(隐藏/匿名)
检测方法
TAS 通过三种方法检测 CLI 隐私请求:
1. 拨号号码中的阻止前缀
订阅者在目的号码之前拨打前缀以阻止其来电 ID。
常见前缀:
*67- 北美标准#31#- 欧洲/GSM 标准1831- 替代格式
TAS 检查拨号号码是否以任何配置的阻止 CLI 前缀开头。如果检测到,则将 cli_withheld 变量设置为 "true"。
示例: 订阅者拨打 *67555 1234 - 检测到 *67 前缀并移除,呼叫继续到 5551234,CLI 被隐藏。
2. From 头中的匿名
用户设备(UE)在 SIP From 头中将来电姓名设置为 "anonymous"。
TAS 检查 Caller-Orig-Caller-ID-Name 字段(不区分大小写)是否包含字符串 "anonymous"。如果找到,则将 cli_withheld 设置为 "true"。
3. SIP 隐私头
S-CSCF 可能在 SIP INVITE 中设置 Privacy: id 头,拨号计划会尊重这些设置。
拨号计划实施
拨号计划检查 cli_withheld 变量,并相应地设置所有与 CLI 相关的变量。
示例拨号计划片段:
<extension name="Manage-Caller-ID" continue="true">
<condition field="${cli_withheld}" expression="true">
<!-- CLI 被隐藏 - 设置为匿名 -->
<action application="log" data="DEBUG CLI withheld detected" />
<action application="set" data="effective_caller_id_name=anonymous" />
<action application="set" data="effective_caller_id_number=anonymous" />
<action application="set" data="origination_caller_id_number=anonymous" />
<action application="set" data="origination_privacy=hide_number" />
<!-- CLI 未被隐藏 - 使用正常的 MSISDN -->
<anti-action application="log" data="DEBUG CLI is normal (not withheld)" />
<anti-action application="set" data="effective_caller_id_number=${msisdn}" />
</condition>
</extension>
注意: 此扩展使用 continue="true",因此即使设置了 CLI,呼叫处理仍继续到路由扩展。
CLI 格式:国家与国际
不同的目的地可能根据您的网络要求需要不同的 CLI 格式。
示例:国家格式
对于国内呼叫,您可能需要呈现没有国家代码的 CLI。
示例拨号计划片段(澳大利亚移动网络):
<extension name="Outgoing-Call-CLI-National" continue="true">
<condition field="${msisdn}" expression="^61(.*)$">
<action application="log" data="Setting source CLI to $1 for national" />
<action application="set" data="effective_caller_id_number=$1"/> <!-- 0412345678 -->
<action application="set" data="effective_caller_id_name=$1"/>
<action application="set" data="sip_from_user=$1"/>
<action application="set" data="sip_cid_type=pid"/>
</condition>
</extension>
工作原理:
- 正则表达式
^61(.*)$捕获国家代码61之后的所有内容 - 输入:
msisdn="61412345678"→ 输出:$1="412345678"或"0412345678" - 在国内呼叫中以国家格式呈现 CLI
示例:国际格式
对于国际呼叫,以完整的 E.164 格式呈现 CLI,并带有 + 前缀。
示例拨号计划片段:
<extension name="Outgoing-Call-CLI-International" continue="true">
<condition field="${tas_destination_number}" expression="^61(.*)$">
<action application="log" data="Call is to national" />
<!-- 反操作在目的地不是国家时运行 -->
<anti-action application="log" data="Setting source CLI for international" />
<anti-action application="set" data="effective_caller_id_number=+${msisdn}"/> <!-- +61412345678 -->
<anti-action application="set" data="effective_caller_id_name=+${msisdn}"/>
<anti-action application="set" data="sip_from_user=+${msisdn}"/>
<anti-action application="set" data="sip_cid_type=pid"/>
</condition>
</extension>
工作原理:
- 条件检查目的地是否以国家前缀开头(例如,澳大利亚的
61) <anti-action>在条件不匹配时执行(国际呼叫)- 为国际呼叫添加
+前缀以获得完整的 E.164 格式
呼叫转发时的 CLI 格式
在路由到呼叫转发目的地时,您可能需要根据是转发到网内还是非网号码调整 CLI 格式。
示例:调整转发目的地的 CLI 前缀
<!-- 如果需要,调整 CLI 格式 -->
<action application="set" data="effective_caller_id_number=${effective_caller_id_number:3}"/>
<action application="set" data="effective_caller_id_name=${effective_caller_id_name:3}"/>
字符串切片: ${variable:N} 移除前 N 个字符
- 输入:
effective_caller_id_number="+61412345678"与:3→ 输出:"412345678" - 输入:
effective_caller_id_number="+61412345678"与:1→ 输出:"61412345678"
用例:
- 删���
+以进行国家转发:使用:1 - 删除国家代码以进行本地格式:使用适当的偏移量(
+61为:3,+1为:2等)
SIP P-Asserted-Identity (PAI)
sip_cid_type=pid 设置控制如何呈现来电 ID:
<action application="set" data="sip_cid_type=pid"/>
效果:
- 设置 SIP
P-Asserted-Identity头部,包含来电信息 - 用于 IMS 网络的受信网络来电 ID 断言
- IMS 网络的标准
移除专有头
为了防止泄露内部网络信息,拨号计划应在将呼叫路由到非网之前移除专有或内部头。
示例:在外部路由之前清理头
<action application="set" data="sip_copy_multipart=false"/>
<action application="set" data="sip_copy_custom_headers=false"/>
<action application="unset" data="sip_h_P-Internal-Correlation-ID"/>
<action application="unset" data="sip_h_P-Access-Network-Info"/>
<!-- 根据需要添加更多供应商特定或内部头 -->
目的:
- 防止内部路由数据到达外部网络
- 移除供应商特定的专有头
- 隐私和安全最佳实践
- 减少 SIP 消息大小
常见需要移除的头:
- 内部关联/跟踪 ID
- 访问网络信息(可能泄露网络拓扑)
- 供应商特定的 P 头
- 仅供内部使用的自定义应用头
最佳实践
- 在 CLI 扩展中使用
continue="true"- 允许多个 CLI 格式规则 - 设置
sip_cid_type=pid- IMS 网络合规所需 - 测试 CLI 隐藏 - 验证
*67和#31#前缀是否有效 - 根据目的地格式化 - 国家与国际 CLI 格式化
- 移除专有头 - 防止内部数据泄露
- 优雅处理匿名 - 显示和路由应与匿名 CLI 一起工作
桥接到网关
TAS 使用 FreeSWITCH 的 bridge 应用程序将呼叫桥接到外部网关(IMS 核心、PSTN 等),并仔细配置编解码器协商、超时处理和重试逻辑的参数。
网关配置
网关被配置为 SIP 中继到外部系统。TAS 使用单一 SIP 接口处理所有流量,为不同目的地定义不同的网关。
示例网关配置:
<gateway name="CS_Gateway">
<param name="proxy" value="10.1.1.100:5060"/>
<param name="register" value="false"/>
<param name="caller-id-in-from" value="true"/>
<param name="extension-in-contact" value="true"/>
</gateway>
请参见 配置指南 以获取完整的网关设置。
桥接语法
呼叫通过以下语法桥接到网关:
基本语法:
<action application="bridge" data="sofia/gateway/GATEWAY_NAME/DESTINATION_NUMBER" />
带参数:
<action application="bridge" data="{param1=value1,param2=value2}sofia/gateway/GATEWAY_NAME/DESTINATION_NUMBER" />
其中 GATEWAY_NAME 是您在配置中定义的网关名称(例如,IMS_Core、PSTN_Primary、International_Gateway)。
桥接参数
编解码器选择
absolute_codec_string - 优先编解码器列表以进行协商:
<action application="bridge" data="{absolute_codec_string='AMR,PCMA,PCMU'}sofia/gateway/IMS_Gateway/+${msisdn}" />
编解码器优先级顺序:
- AMR(自适应多速率) - 移动优化,优先用于蜂窝
- PCMA(G.711 a-law) - 欧洲/国际固定线路标准
- PCMU(G.711 μ-law) - 北美固定线路标准
模板使用: priv/templates/mt_dialplan.xml:80,mo_dialplan.xml:124,mo_dialplan.xml:202
超时配置
originate_timeout - 等待应答的最大秒数(包括响铃):
<action application="set" data="originate_timeout=60"/>
<action application="bridge" data="{originate_timeout=60}sofia/gateway/CS_Gateway/+${msisdn}" />
progress_timeout - 等待 180/183(早期媒体/响铃)的秒数:
<action application="set" data="progress_timeout=10" />
bridge_answer_timeout - 在响铃开始后等待 200 OK 的秒数:
<action application="set" data="bridge_answer_timeout=${no_reply_timer}" />
leg_progress_timeout - 每条腿的进度超时:
<action application="set" data="leg_progress_timeout=${no_reply_timer}" />
模板示例: priv/templates/mt_dialplan.xml:73-76
<action application="set" data="progress_timeout=10" />
<!-- 我们在 INVITE 和 200 OK 之间等待多长时间(包括响铃) -->
<action application="set" data="bridge_answer_timeout=${no_reply_timer}" />
<action application="set" data="leg_progress_timeout=${no_reply_timer}" />
变量: ${no_reply_timer} 来自订阅者数据(通常为 20-30 秒)
重试和失败处理
originate_retries - 重试尝试的次数:
<action application="bridge" data="{originate_retries=1}sofia/gateway/CS_Gateway/+${msisdn}" />
continue_on_fail - 在桥接失败后继续拨号计划执行:
<action application="set" data="continue_on_fail=true" />
<action application="bridge" data="{continue_on_fail=true}sofia/gateway/CS_Gateway/+${msisdn}" />
<!-- 如果桥接失败,后续操作执行 -->
<action application="log" data="INFO Bridge failed - routing to voicemail" />
hangup_after_bridge - 当 B-leg 挂断时挂断 A-leg:
<action application="set" data="hangup_after_bridge=true"/>
早期媒体处理
ignore_early_media - 控制早期媒体行为:
<action application="set" data="ignore_early_media=ring_ready" />
<action application="bridge" data="{ignore_early_media=ring_ready}sofia/gateway/CS_Gateway/+${msisdn}" />
选项:
ring_ready- 生成本地响铃,忽略远程早期媒体true- 完全忽略早期媒体false(默认) - 通过早期媒体(公告、音调)
为什么使用 ring_ready? - 防止呼叫者听到来自远程网络的公告或音调
模板示例: priv/templates/mt_dialplan.xml:78-79
<action application="set" data="ignore_early_media=ring_ready" />
<action application="bridge" data="{ignore_early_media=ring_ready,...}sofia/gateway/CS_Gateway/+${msrn}" />
网内与非网呼叫者处理:
<extension name="Route-to-IMS-Sub-Early-Media" continue="true">
<condition field="${on_net_caller}" expression="true">
<!-- 网内呼叫者 - 使用 ring_ready -->
<action application="log" data="INFO On-net caller ${effective_caller_id_number} - using ignore_early_media=ring_ready"/>
<action application="set" data="ignore_early_media=ring_ready"/>
<!-- 非网呼叫者 - 提供即时响铃 -->
<anti-action application="log" data="INFO Off-net caller ${effective_caller_id_number} - setting instant ringback"/>
<anti-action application="set" data="instant_ringback=true"/>
<anti-action application="set" data="ringback=${fr-ring}"/>
<anti-action application="set" data="transfer_ringback=${fr-ring}"/>
</condition>
</extension>
注意: ${on_net_caller} 变量根据您的网络的订阅者编号计划设置。您还可以使用正则表达式模式来匹配您的特定号码范围。
来电 ID 参数
sip_cid_type=pid - 使用 P-Asserted-Identity 进行来电 ID:
<action application="set" data="sip_cid_type=pid" />
<action application="bridge" data="{sip_cid_type=pid}sofia/gateway/CS_Gateway/+${msisdn}" />
常见桥接模式
模式 1:通过 IMS 域路由到 IMS 订阅者
将 MT 呼叫路由到 IMS 订阅者,通过 IMS 域发送(S-CSCF 将解析并路由)。
模板示例:
<extension name="Route-to-IMS-Sub" continue="false">
<condition field="destination_number" expression="^(.*)$">
<action application="set" data="continue_on_fail=true" />
<action application="set" data="hangup_after_bridge=true"/>
<action application="set" data="progress_timeout=10" />
<!-- 我们在 INVITE 和 200 OK 之间等待多长时间(包括响铃) -->
<action application="set" data="bridge_answer_timeout=${no_reply_timer}" />
<action application="set" data="leg_progress_timeout=${no_reply_timer}" />
<!-- 将呼叫发送到 IMS 域(S-CSCF 解析) -->
<action application="set" data="ignore_early_media=ring_ready" />
<action application="set" data="sip_cid_type=pid" />
<action application="bridge"
data="{absolute_codec_string='AMR-WB,AMR,PCMA,PCMU',ignore_early_media=ring_ready,continue_on_fail=true,sip_cid_type=pid,originate_retries=1,originate_timeout=${no_reply_timer},sip_invite_call_id=${sip_call_id}}sofia/internal/${msisdn}@${ims_domain}" />
<!-- 如果桥接失败,提供呼叫转发 -->
<action application="log" data="INFO Failed to bridge Call - Routing to Call Forward No-Answer Destination" />
<action application="set" data="sip_h_History-Info=<sip:${destination_number}@${ims_domain}>;index=1.1" />
<action application="set" data="sip_h_Diversion=<sip:${destination_number:2}@${ims_domain}>;reason=busy" />
<!-- 路由到非网网关进行呼叫转发 -->
<action application="bridge"
data="{absolute_codec_string='AMR-WB,AMR,PCMU,PCMA',originate_timeout=65,originate_retries=0}sofia/gateway/ExternalSIPGateway/${call_forward_not_reachable_destination}" />
</condition>
</extension>
关键点:
- 路由到
${msisdn}@${ims_domain}(例如,5551234567@ims.mnc380.mcc313.3gppnetwork.org) - IMS 核心(S-CSCF/I-CSCF)处理最终路由到订阅者
ignore_early_media=ring_ready提供一致的响铃- 失败时使用外部网关进行非网呼叫转发
- 设置
History-Info和Diversion头以进行呼叫转发跟踪
模式 2:路由到 MSRN(CS 漫游)
通过 CS 网络路由到漫游订阅者:
模板: priv/templates/mt_dialplan.xml:67-80
<extension name="Route-to-CS-MSRN" continue="false">
<condition field="msrn" expression="^(\d+)$">
<action application="set" data="continue_on_fail=true" />
<action application="set" data="hangup_after_bridge=true"/>
<action application="set" data="progress_timeout=10" />
<action application="set" data="bridge_answer_timeout=${no_reply_timer}" />
<action application="set" data="leg_progress_timeout=${no_reply_timer}" />
<!-- 将呼叫发送到 MSRN 通过网关 -->
<action application="set" data="ignore_early_media=ring_ready" />
<action application="set" data="sip_cid_type=pid" />
<action application="bridge"
data="{ignore_early_media=ring_ready,absolute_codec_string='AMR,PCMA,PCMU',continue_on_fail=true,sip_cid_type=pid,originate_retries=1,originate_timeout=60}sofia/gateway/CS_Gateway/+${msrn}" />
</condition>
</extension>
模式 3:网内路由(MO 到 MT 通过 TAS)
当订阅者呼叫另一位网内订阅者时,呼叫必须路由回 TAS 进行完整的 MT 处理。此模式对于确保网内呼叫获得与外部 MT 呼叫相同的服务处理至关重要。
为什么需要此模式:
如果不路由回 TAS,网内呼叫将完全绕过 MT 处理,意味着:
- 呼叫转移设置将不被尊重
- 无法在无人接听时转移到语音邮件
- 漫游订阅者的 MSRN 路由将失败
- 跳过订阅者服务逻辑
- 呼叫跟踪和 CDR 将不完整
通过将 MO 呼叫路由回 TAS 作为新的 MT 呼叫,被叫订阅者获得完整的服务处理。
模板示例:
<extension name="On-Net-Route">
<condition field="${on_net_status}" expression="true">
<action application="log" data="DEBUG On-Net MO call - Routing back into TAS" />
<!-- 清理内部路由的头部 -->
<action application="set" data="sip_copy_multipart=false"/>
<action application="set" data="sip_h_Request-Disposition=no-fork"/>
<!-- 路由回 TAS(变为 MT 呼叫) -->
<action application="bridge"
data="{absolute_codec_string='AMR-WB,AMR,PCMA,PCMU',originate_retries=1,originate_timeout=60,sip_invite_call_id=${sip_call_id}}sofia/internal/${tas_destination_number}@${sip_local_network_addr}" />
<action application="hangup" data="" />
</condition>
</extension>
工作原理:
- MO 呼叫到达:订阅者 A 呼叫订阅者 B(均在网内)
- 检查网内状态:TAS 确定目的地在网内,通过
${on_net_status}变量 - 路由到 TAS:桥接到
sofia/internal/${tas_destination_number}@${sip_local_network_addr}- 使用 TAS 自身的 IP 地址作为目的地
- 保留原始呼叫 ID 以便跟踪
- MT 处理:TAS 将呼叫视为新的 MT 呼叫,并处理
mt_dialplan.xml- 检查呼叫转移设置(CFU、CFB、CFNRy、CFNRc)
- 查询 MSRN 如果订阅者在漫游中
- 适当的路由到 IMS 域或转发
- 完整服务:被叫订阅者获得完整的 MT 处理
关键点:
- 路由到
${sip_local_network_addr}(TAS IP 地址,例如10.179.3.60) - 呼叫作为新的 MT 呼叫重新处理到目的订阅者
- 使用
sip_invite_call_id参数保留呼叫 ID 以便进行端到端跟踪 - 启用所有 MT 特性:呼叫转移、语音邮件、MSRN 路由、订阅者服务
- 对双方进行正确的呼叫状态跟踪和 CDR 生成
- 网内呼叫获得与外部 MT 呼叫相同的服务处理
- TAS IP 必须在
allowed_sbc_source_ips配置列表中
变量: ${on_net_status} 在目的号码由您的 TAS 提供时设置为 "true"。这在 MO 呼叫授权期间通过检查目的 MSISDN 是否存在于您的订阅者数据库中确定。
模式 4:非网路由(MO 到 PSTN/外部)
将 MO 呼叫路由到外部 PSTN、互联或其他外部网络通过网关。
使用的网关: sofia/gateway/ExternalSIPGateway 或 sofia/gateway/PSTN_Gateway
模板示例:
<extension name="Outgoing-Call-Off-Net">
<condition field="${tas_destination_number}" expression="^(.*)$">
<action application="log" data="Sending call off-net" />
<!-- 在外部路由之前清理头 -->
<action application="set" data="sip_copy_multipart=false"/>
<!-- 设置呼叫事件钩子以进行 CDR/计费 -->
<action application="set" data='api_body=caller=${msisdn}&called=${tas_destination_number}&call-id=${sip_i_call_id}&action=answer'/>
<action application="set" data='api_on_answer=curl http://localhost:8080/call_event content-type application/x-www-form-urlencoded post ${api_body}'/>
<action application="set" data='api_body=caller=${msisdn}&called=${tas_destination_number}&call-id=${sip_i_call_id}&action=hangup'/>
<action application="set" data='api_hangup_hook=curl http://localhost:8080/call_event content-type application/x-www-form-urlencoded post ${api_body}'/>
<!-- 为受信网络设置 P-Asserted-Identity -->
<action application="set" data="sip_h_Request-Disposition=no-fork"/>
<action application="set" data="sip_h_P-Asserted-Identity=<sip:${msisdn}@${ims_domain}>"/>
<action application="set" data="hangup_after_bridge=true"/>
<action application="set" data="continue_on_fail=true"/>
<!-- 桥接到外部 PSTN/互联网网关 -->
<action application="set" data="used_gateway=ExternalSIPGateway"/>
<action application="bridge"
data="{absolute_codec_string='AMR-WB,AMR,PCMA,PCMU',originate_retries=1,originate_timeout=60,sip_invite_call_id=${sip_call_id}}sofia/gateway/ExternalSIPGateway/${tas_destination_number}" />
<!-- 如果桥接失败,提供错误处理 -->
<action application="answer" data="" />
<action application="log" data="INFO Bridge failed with SIP code ${last_bridge_proto_specific_hangup_cause}"/>
<action application="sleep" data="500"/>
<action application="transfer" data="${last_bridge_proto_specific_hangup_cause}"/>
</condition>
</extension>
关键点:
- 使用
sofia/gateway/ExternalSIPGateway进行外部路由 - 在受信互联网上为来电 ID 设置
P-Asserted-Identity - 呼叫事件钩子用于 CDR/计费跟踪
continue_on_fail=true允许错误处理- 失败时根据 SIP 代码转移到错误公告
常见的非网网关:
ExternalSIPGateway- 主要 PSTN 中继/互联BackupSIPGateway- 备用 PSTN 中继(用于故障转移)International_GW- 国际呼叫网关Emergency_GW- 紧急服务网关
网关路由策略
所有呼叫都通过网关路由。了解在不同呼叫场景中使用哪个网关对于正确的呼叫路由至关重要: