FreeSWITCH 1.11 配置参数详解

FreeSWITCH 1.11.3 配置体系与核心参数详解:freeswitch.xml 加载体系、$${}与${}变量、global_getvar/fsctl 查看与修改生效边界、switch.conf/event_socket/sip_profiles 逐类参数默认值与两套生产模板。

FreeSWITCH即时通信FreeSWITCH2026/10/22

FreeSWITCH 1.11 配置参数详解

目标:讲清 FreeSWITCH 1.11.3 的配置加载体系(freeswitch.xml → vars.xml → autoload_configs → sip_profiles)、$${} 预处理变量与 ${} 通道变量的区别、逐类拆解核心参数(路径目录/端口 TLS/并发/编解码/日志/Event Socket/模块加载/SIP Profile/数据库)的真实默认值与改动影响,并给出两套生产配置模板。全部配置片段与命令回显均取自 Ubuntu 22.04 实测环境(1.11.3-release 默认安装,2026-10-21/22 逐条实测);安装步骤见 《Ubuntu 22.04 安装 FreeSWITCH 1.11 指南》,背景选型见 《FreeSWITCH 介绍与选型指南》。

一、环境信息

本章列出本文参数解析所依据的实测环境,所有「默认值」均指该环境下的出厂配置(源自源码编译安装生成的默认配置包):

  • 操作系统:Ubuntu 22.04 LTS(x86_64)
  • FreeSWITCH 版本:1.11.3-release~64bit(freeswitch -version 实测)
  • 安装前缀:/usr/local/freeswitch(源码编译)
  • 配置目录:/usr/local/freeswitch/etc/freeswitch/(1.11 autoconf 布局,非 1.10 的 <前缀>/conf/)
  • 配置文件规模:主配置树 4869 行 XML(autoload_configs/*.xml 合计,实测 wc -l)
  • 运行状态:systemd 托管(Type=simple + -nf -nonat,详见安装指南 4.10 节)

二、前置条件

本文所有查看/修改操作基于以下前提,逐条确认后照做即可复现:

  1. FreeSWITCH 1.11.3 已安装并运行:systemctl is-active freeswitch → active(实测回显 active)。
  2. fs_cli 可连入控制台(默认密码 ClueCon):/usr/local/freeswitch/bin/fs_cli -x status → 回显 FreeSWITCH (Version 1.11.3 -release 64bit) is ready(实测)。
  3. 有配置目录写权限(root 或 sudo):ls /usr/local/freeswitch/etc/freeswitch/ 可列出 freeswitch.xml vars.xml autoload_configs dialplan sip_profiles directory 等(实测)。

⚠️ 注意:改配置前先备份。本文演示的所有修改均在实测环境先改后还原,读者操作自己的生产环境时,务必 cp <文件> <文件>.bak 再动手。

三、配置体系与参数查看/修改方式

本章先建立对 FreeSWITCH 配置体系的整体认知——参数散在几十个 XML 里,但加载入口只有一个;变量有两种形态,作用域完全不同;修改后何时生效、何时必须重启,都有明确边界。

3.1 配置加载体系:freeswitch.xml 是唯一入口

FreeSWITCH 启动时只加载一个 XML 主文档:etc/freeswitch/freeswitch.xml。其他所有配置都靠预处理器指令 X-PRE-PROCESS 挂进来。实测主入口全文(去注释后完整结构):

<document type="freeswitch/xml">
  <X-PRE-PROCESS cmd="include" data="vars.xml"/>

  <section name="configuration" description="Various Configuration">
    <X-PRE-PROCESS cmd="include" data="autoload_configs/*.xml"/>
  </section>

  <section name="dialplan" description="Regex/XML Dialplan">
    <X-PRE-PROCESS cmd="include" data="dialplan/*.xml"/>
  </section>

  <section name="chatplan" description="Regex/XML Chatplan">
    <X-PRE-PROCESS cmd="include" data="chatplan/*.xml"/>
  </section>

  <section name="directory" description="User Directory">
    <X-PRE-PROCESS cmd="include" data="directory/*.xml"/>
  </section>

  <section name="languages" description="Language Management">
    <X-PRE-PROCESS cmd="include" data="lang/de/*.xml"/>
    <!-- ... 其余语言 include ... -->
  </section>
</document>

加载顺序与职责:

层文件职责
第 1 层vars.xml全部 #set 预处理变量定义(最先 include,供后续配置引用 $${...})
第 2 层autoload_configs/*.xml各模块配置(switch.conf、event_socket.conf、logfile.conf、modules.conf…),在 <section name="configuration"> 内加载
第 3 层dialplan/*.xml、chatplan/*.xml拨号计划/消息计划
第 4 层directory/*.xml用户分机目录(注册账号)
第 5 层lang/*/*.xml多语言提示音文案

第 2 层中 autoload_configs/sofia.conf.xml 再把 SIP Profile 挂进来(实测原文):

<configuration name="sofia.conf" description="sofia Endpoint">
  <global_settings>
    <param name="log-level" value="0"/>
    <param name="debug-presence" value="0"/>
  </global_settings>
  <profiles>
    <X-PRE-PROCESS cmd="include" data="../sip_profiles/*.xml"/>
  </profiles>
</configuration>

💡 说明:预处理器还会把编译后的全量 XML 落盘为 var/log/freeswitch/freeswitch.xml.fsxml(freeswitch.xml 注释原文说明),排障时可看它确认「最终生效的合并结果」。

3.2 两种变量形态:$${} 预处理变量 vs ${} 通道变量

这是 FreeSWITCH 配置里最容易混淆的一点,两者符号相近、作用域完全不同:

形态名称作用域定义位置生效时机
$${var}全局变量(双美元)整个 XML 预处理阶段全局可见vars.xml 的 X-PRE-PROCESS cmd="set"启动/reloadxml 时展开一次
${var}通道变量(单美元)单个呼叫通道内拨号计划 <action>、应用参数、事件每通道运行时求值

vars.xml 中对 $${} 变量的官方注释原文(节选):

The following variables are set dynamically - calculated if possible by freeswitch - and
are available to the config as $${variable}.  You can see their calculated value via fs_cli
by entering eval $${variable}

3.3 查看参数:global_getvar / eval / fsctl

三个入口分别覆盖「全表」「单变量」「核心参数当前值」。

全表查看(global_getvar,实测全量 70 行,此处保留完整输出作为路径/变量默认值的事实基准):

/usr/local/freeswitch/bin/fs_cli -x global_getvar

实测回显(全表):

hostname=5f8783896c5f
local_ip_v4=10.0.0.6
local_mask_v4=255.255.255.0
local_ip_v6=::1
base_dir=/usr/local/freeswitch
recordings_dir=/usr/local/freeswitch/var/lib/freeswitch/recordings
sounds_dir=/usr/local/freeswitch/share/freeswitch/sounds
conf_dir=/usr/local/freeswitch/etc/freeswitch
log_dir=/usr/local/freeswitch/var/log/freeswitch
run_dir=/usr/local/freeswitch/var/run/freeswitch
db_dir=/usr/local/freeswitch/var/lib/freeswitch/db
mod_dir=/usr/local/freeswitch/lib/freeswitch/mod
htdocs_dir=/usr/local/freeswitch/share/freeswitch/htdocs
script_dir=/usr/local/freeswitch/share/freeswitch/scripts
temp_dir=/tmp
grammar_dir=/usr/local/freeswitch/share/freeswitch/grammar
fonts_dir=/usr/local/freeswitch/share/freeswitch/fonts
images_dir=/usr/local/freeswitch/var/lib/freeswitch/images
certs_dir=/usr/local/freeswitch/etc/freeswitch/tls
storage_dir=/usr/local/freeswitch/var/lib/freeswitch/storage
cache_dir=/usr/local/freeswitch/var/cache/freeswitch
data_dir=/usr/local/freeswitch/share/freeswitch
localstate_dir=/usr/local/freeswitch/var/lib/freeswitch
core_uuid=389858bd-60a6-4956-8db8-cad0718d8b6b
default_password=1234
sound_prefix=/usr/local/freeswitch/share/freeswitch/sounds/en/us/callie
domain=10.0.0.6
domain_name=10.0.0.6
hold_music=local_stream://moh
use_profile=external
rtp_sdes_suites=AEAD_AES_256_GCM_8|AEAD_AES_128_GCM_8|AES_CM_256_HMAC_SHA1_80|AES_CM_192_HMAC_SHA1_80|AES_CM_128_HMAC_SHA1_80|AES_CM_256_HMAC_SHA1_32|AES_CM_192_HMAC_SHA1_32|AES_CM_128_HMAC_SHA1_32|AES_CM_128_NULL_AUTH
global_codec_prefs=OPUS,G722,PCMU,PCMA,H264,VP8
outbound_codec_prefs=OPUS,G722,PCMU,PCMA,H264,VP8
xmpp_client_profile=xmppc
xmpp_server_profile=xmpps
bind_server_ip=auto
external_rtp_ip=182.54.113.29
external_sip_ip=182.54.113.29
unroll_loops=true
outbound_caller_name=FreeSWITCH
outbound_caller_id=0000000000
call_debug=false
console_loglevel=info
default_areacode=918
default_country=US

💡 说明:表内 hostname/local_ip_v4/external_rtp_ip 等是启动时动态计算的变量(vars.xml 注释列出的动态清单包括 hostname、local_ip_v4、local_mask_v4、local_ip_v6、switch_serial、core_uuid、nat_public_addr、nat_type 等);external_rtp_ip=182.54.113.29 即 vars.xml 中 stun-set(STUN 探测公网地址)在实测网络下的解析结果。

单变量查看(eval):

/usr/local/freeswitch/bin/fs_cli -x 'eval $${domain}'

实测回显:

10.0.0.6

核心参数当前值(fsctl,针对 switch.conf.xml 里需重启才生效的参数,这是核对运行值的权威命令):

/usr/local/freeswitch/bin/fs_cli -x "fsctl max_sessions"
/usr/local/freeswitch/bin/fs_cli -x "fsctl sps"

实测回显:

+OK max sessions: 1000
+OK sessions per second: 30

3.4 修改参数与生效方式:reloadxml 的边界(实测)

修改流程四步:改 XML → reloadxml → 验证 → 无效则重启。关键边界:reloadxml 只重载 XML 缓存,不会重新初始化核心运行参数。以 switch.conf.xml 的 max-sessions 做完整实测:

# 1. 修改 max-sessions 1000 → 600
sed -i 's|<param name="max-sessions" value="1000"/>|<param name="max-sessions" value="600"/>|' \
  /usr/local/freeswitch/etc/freeswitch/autoload_configs/switch.conf.xml
grep -n "max-sessions" /usr/local/freeswitch/etc/freeswitch/autoload_configs/switch.conf.xml

实测回显:

61:    <param name="max-sessions" value="600"/>
# 2. reloadxml 后查运行值 —— 仍是 1000,未热生效
/usr/local/freeswitch/bin/fs_cli -x reloadxml
/usr/local/freeswitch/bin/fs_cli -x "fsctl max_sessions"

实测回显:

+OK [Success]

+OK max sessions: 1000
# 3. 重启后查运行值 —— 600 生效
systemctl restart freeswitch
sleep 5
/usr/local/freeswitch/bin/fs_cli -x "fsctl max_sessions"

实测回显:

+OK max sessions: 600

UP 0 years, 0 days, 0 hours, 0 minutes, 4 seconds, 619 milliseconds, 568 microseconds
FreeSWITCH (Version 1.11.3 -release 64bit) is ready
0 session(s) since startup

结论(改各类配置的生效方式速查):

改动的文件生效方式说明
vars.xml / autoload_configs/*.xmlreloadxml 后按模块分情况模块级参数(如 logfile、event_socket)由模块重载读取;核心参数(max-sessions/sessions-per-second 等 switch.conf settings)必须重启
sip_profiles/*.xmlsofia profile <名> rescan / restartprofile 级参数多数可 rescan 热应用,端口等绑定类需 restart profile
dialplan/*.xml、directory/*.xmlreloadxml 即生效每次呼叫重新求值
modules.conf.xml重启模块加载清单仅启动时读取

⚠️ 注意:改完务必用 fsctl max_sessions / fsctl sps 这类「查运行值」命令核验,不要只看 XML 文件——XML 是意图,fsctl 回显才是事实。

四、参数总览

本章给两张总表建立全局地图,再进第五章逐类拆解。

4.1 配置文件全景表

实测环境 autoload_configs/ 全量文件清单(关键文件标注行数,wc -l 实测):

文件行数职责本文详解节
vars.xml455全局预处理变量5.1/5.2
autoload_configs/switch.conf.xml246核心引擎参数(并发/DTMF/日志/RTP 端口/DB)5.3–5.5/5.10
autoload_configs/modules.conf.xml129模块加载清单5.8
autoload_configs/event_socket.conf.xml10Event Socket(fs_cli/ESL 接入)5.7
autoload_configs/logfile.conf.xml29文件日志滚动策略5.6
autoload_configs/console.conf.xml—控制台日志级别5.6
autoload_configs/lua.conf.xml23Lua 脚本环境—
autoload_configs/sofia.conf.xml29SIP 模块全局设置 + profile 挂载5.9
autoload_configs/db.conf.xml5LIMIT 类应用的后端 DB5.10
autoload_configs/callcenter.conf.xml40呼叫中心队列策略—
sip_profiles/internal.xml442内部 SIP Profile(分机注册)5.9
sip_profiles/external.xml99外部 SIP Profile(出局/对接运营商)5.9

4.2 核心全局变量速览表(vars.xml 出厂定义,实测原文摘录)

变量默认值说明
default_password1234分机注册默认密码(必改)
domain / domain_name$${local_ip_v4}默认 SIP 域
sound_prefix$${sounds_dir}/en/us/callie默认提示音前缀
global_codec_prefsOPUS,G722,PCMU,PCMA,H264,VP8全局编解码偏好(入方向协商序)
outbound_codec_prefsOPUS,G722,PCMU,PCMA,H264,VP8出方向编解码偏好
hold_musiclocal_stream://moh音乐保持源
use_profileexternal未显式指定时的默认出呼 profile
internal_sip_port5060internal profile SIP 端口
external_sip_port5080external profile SIP 端口
internal_ssl_enable / external_ssl_enablefalseprofile TLS 开关
sip_tls_versiontlsv1,tlsv1.1,tlsv1.2TLS 协议版本集
sip_tls_ciphersALL:!ADH:!LOW:!EXP:!MD5:@STRENGTHTLS 密码套件
external_rtp_ip / external_sip_ipstun:stun.freeswitch.org(stun-set 动态解析)对外通告的 RTP/SIP 地址
call_debugfalse呼叫调试模式
console_loglevelinfo控制台日志级别

五、核心参数分类详解

本章逐类拆解,每类给出配置原文(默认值)+ 逐项含义 + 改动影响。配置块均为实测环境原样摘录。

5.1 路径与目录类

FreeSWITCH 1.11 把目录变量全部收敛为「预编译时由 configure 前缀推导的动态变量」,无需手改。实测值(见 3.3 节 global_getvar 全表)归纳:

变量实测值(--prefix=/usr/local/freeswitch)用途
base_dir/usr/local/freeswitch安装根
conf_dir/usr/local/freeswitch/etc/freeswitch配置树
log_dir/usr/local/freeswitch/var/log/freeswitch日志
run_dir/usr/local/freeswitch/var/run/freeswitch运行文件
db_dir/usr/local/freeswitch/var/lib/freeswitch/db核心内部 SQLite
mod_dir/usr/local/freeswitch/lib/freeswitch/mod模块目录
sounds_dir/usr/local/freeswitch/share/freeswitch/sounds提示音根
recordings_dir/usr/local/freeswitch/var/lib/freeswitch/recordings录音
storage_dir/usr/local/freeswitch/var/lib/freeswitch/storage语音信箱留言存储
certs_dir/usr/local/freeswitch/etc/freeswitch/tlsTLS 证书目录
script_dir/usr/local/freeswitch/share/freeswitch/scriptsLua 等脚本
cache_dir/usr/local/freeswitch/var/cache/freeswitch缓存

💡 说明:这批变量在 1.10 时代是 <前缀>/conf、<前缀>/log 等扁平布局,1.11 改为 autoconf 标准布局。若照抄 1.10 老教程路径找配置/日志,会扑空。

5.2 会话与并发类(switch.conf.xml)

核心引擎的并发闸门,出厂原文(注释略):

<param name="max-sessions" value="1000"/>
<param name="sessions-per-second" value="30"/>
<!-- <param name="min-idle-cpu" value="25"/> -->
<param name="max-db-handles" value="50"/>
<param name="db-handle-timeout" value="10"/>

逐项说明:

  • max-sessions:同时存在的最大会话数,出厂 1000。超限新呼叫被拒。改后需重启进程(3.4 节实测 reloadxml 不热生效)。官方注释举例:驱动 28 条 T1(1344 路)时应设 1288 以上。
  • sessions-per-second:每秒新建会话上限,出厂 30。用于削峰防打挂,可用 fsctl sps 60 运行时临时调整(重启后回到 XML 值)。
  • min-idle-cpu:注释态,默认不限;设定后空闲 CPU 低于阈值拒绝新呼叫(status 输出里的 min idle cpu 行即此值运行态)。
  • max-db-handles / db-handle-timeout:核心 DB 连接池大小 50 与取句柄等待 10 秒;高并发下 db-handle-timeout 超时会话失败,可加大池子。

💡 技术拓展:并发控制策略不止 max-sessions 一种思路,业界常见对比——

策略原理适用
硬上限(max-sessions)超限直接拒绝保护性兜底,必设
速率限制(sessions-per-second)限制每秒新建防呼叫风暴/攻击
资源门槛(min-idle-cpu)CPU 空闲不足拒绝资源紧张环境自保
队列缓冲(mod_callcenter/mod_fifo)排队等待坐席业务侧削峰

FreeSWITCH 出厂即内置前三种;队列缓冲由应用层模块承担。本文建议生产至少保留前两者默认值,再按压测结果调高。

5.3 编解码与媒体类

编解码偏好定义在 vars.xml,被两个 profile 引用(原文):

<X-PRE-PROCESS cmd="set" data="global_codec_prefs=OPUS,G722,PCMU,PCMA,H264,VP8"/>
<X-PRE-PROCESS cmd="set" data="outbound_codec_prefs=OPUS,G722,PCMU,PCMA,H264,VP8"/>
  • global_codec_prefs:SDP 协商时按序提供的编解码清单。顺序即优先级(左高右低)。OPUS 供 WebRTC/现代终端,G722 供高清话机,PCMU/PCMA(G.711)兼容传统话机与运营商。引用它的配置:internal.xml 的 inbound-codec-prefs/outbound-codec-prefs 均为 $${global_codec_prefs}(实测原文)。
  • outbound_codec_prefs:出呼方向偏好,external.xml 的 outbound-codec-prefs 引用。
  • RTP 端口范围(switch.conf.xml,出厂注释态,默认 16384–32768):
<!-- <param name="rtp-start-port" value="16384"/> -->
<!-- <param name="rtp-end-port" value="32768"/> -->
<!-- <param name="rtp-port-usage-robustness" value="true"/> -->

取消注释即可改小端口范围(如防火墙只放行 20000–21000 时设这两值);rtp-port-usage-robustness 开启后分配端口前先探测占用,避免冲突。

💡 技术拓展:VoIP 编解码选择是典型的多选一场景,主流选项对比——

编解码采样率/码率特点适用
OPUS8–48kHz/6–510kbps自适应、抗丢包最好,WebRTC 标准内网高清/WebRTC(本文首选)
G.72216kHz/64kbps宽带固定码率,老话机支持广局域网话机
G.711 (PCMU/PCMA)8kHz/64kbps无压缩基线,互通性最好运营商对接/PSTN
G.7298kHz/8kbps低带宽专利编解码(透传)带宽昂贵链路
GSM8kHz/13kbps老式移动编解码兼容遗留设备

本文/默认配置采用「OPUS,G722,PCMU,PCMA」序:WebRTC 优先、话机次之、运营商兜底;G729 需注意许可(1.11 源码树里仅透传实现)。

5.4 DTMF 类(switch.conf.xml)

三个 DTMF 时长参数出厂均为注释态,注释原文给定了上下限约束:

<!-- <param name="min-dtmf-duration" value="400"/> -->
<!-- <param name="max-dtmf-duration" value="192000"/> -->
<!-- <param name="default-dtmf-duration" value="2000"/> -->
  • min-dtmf-duration(下限 400ms 内不可再低):出向 DTMF 事件最短时长,短于此会被拉长。
  • max-dtmf-duration(上限 192000):超长 DTMF 截断至此。
  • default-dtmf-duration(默认 2000):无显式时长的 DTMF 事件取此值。
  • profile 侧配套:internal.xml/external.xml 的 <param name="dtmf-duration" value="2000"/> 与 <param name="rfc2833-pt" value="101"/>(RFC2833 载荷类型 101,实测原文),sofia status profile 输出里对应 TEL-EVENT 101 / DTMF-MODE rfc2833 行(实测)。

5.5 日志类(switch.conf / logfile.conf / console.conf)

三层日志体系:核心级别 → 文件滚动 → 控制台。

核心级别(switch.conf.xml):

<param name="loglevel" value="debug"/>

全局日志级别出厂 debug(排障友好,生产建议 info 或 notice,减少磁盘写入)。

文件滚动(logfile.conf.xml 实测原文):

<configuration name="logfile.conf" description="File Logging">
  <settings>
   <param name="rotate-on-hup" value="true"/>
  </settings>
  <profiles>
    <profile name="default">
      <settings>
        <param name="rollover" value="1048576000"/>
        <param name="maximum-rotate" value="32"/>
        <param name="uuid" value="true" />
      </settings>
      <mappings>
        <map name="all" value="console,debug,info,notice,warning,err,crit,alert"/>
      </mappings>
    </profile>
  </profiles>
</configuration>
  • rollover=1048576000:单文件 1000MB 滚动(生产建议降到 100–200MB)。
  • maximum-rotate=32:最多保留 32 个滚动文件(超出回绕覆盖;开启后文件名不再带日期戳)。
  • rotate-on-hup=true:收到 SIGHUP 即滚动(配合 logrotate 用)。
  • uuid=true:日志行前缀带会话 UUID(串联呼叫排障必需,保持开启)。
  • mappings:落文件的事件类别全集(保持默认即可,改级别用 value 列表裁剪)。

日志文件实测位置:/usr/local/freeswitch/var/log/freeswitch/freeswitch.log。

控制台级别:console_loglevel=info(vars.xml);运行时动态调整用 fs_cli 交互里的 console loglevel 0(最低)到 console loglevel 7(最高)——switch.conf.xml 的 cli-keybindings 出厂把 F1~F12 绑定到常用命令(原文含 <key name="7" value="console loglevel 0"/>、<key name="8" value="console loglevel 7"/>),详见 《FreeSWITCH 1.11 常用 CLI 命令与工具详解》。

5.6 Event Socket 类(event_socket.conf.xml)

fs_cli 与 ESL 客户端的接入闸门,实测原文(含出厂注释行):

<configuration name="event_socket.conf" description="Socket Client">
  <settings>
    <param name="nat-map" value="false"/>
    <param name="listen-ip" value="::"/>
    <param name="listen-port" value="8021"/>
    <param name="password" value="ClueCon"/>
    <!--<param name="apply-inbound-acl" value="loopback.auto"/>-->
    <!--<param name="stop-on-bind-error" value="true"/>-->
  </settings>
</configuration>
  • listen-ip=:::双栈监听(IPv4+IPv6)。生产建议改为 127.0.0.1(只允许本机 fs_cli)或内网地址。
  • listen-port=8021:ESL 端口。
  • password=ClueCon:出厂公开值,必改(安装指南 7.2 节有完整修改步骤)。
  • apply-inbound-acl:注释态。生产强烈建议放开并设为内网网段 ACL(如 loopback.auto 仅本机),未设 ACL 时任意可达 IP 都可尝试用 ClueCon 连入。
  • stop-on-bind-error:注释态,默认端口占用不阻断启动;需「绑不上就快速失败」时开启。

5.7 模块加载类(modules.conf.xml)

运行时加载清单,启动时按顺序 load。实测默认文件(节选,<load module="..."/> 未注释行):

<load module="mod_console"/>
<load module="mod_logfile"/>
<load module="mod_enum"/>
<load module="mod_cdr_csv"/>
<load module="mod_event_socket"/>
<load module="mod_sofia"/>
<load module="mod_loopback"/>
<load module="mod_rtc"/>
<load module="mod_verto"/>
<load module="mod_signalwire"/>
<load module="mod_commands"/>
<load module="mod_conference"/>
<load module="mod_db"/>
<load module="mod_dptools"/>
<load module="mod_expr"/>
<load module="mod_fifo"/>
<load module="mod_hash"/>
<load module="mod_voicemail"/>
<load module="mod_esf"/>
<load module="mod_fsv"/>
<load module="mod_valet_parking"/>
<load module="mod_httapi"/>
<load module="mod_dialplan_xml"/>
<load module="mod_dialplan_asterisk"/>
<load module="mod_spandsp"/>
<load module="mod_g723_1"/>
<load module="mod_g729"/>
<load module="mod_amr"/>
<load module="mod_b64"/>
<load module="mod_av"/>
<load module="mod_sndfile"/>
<load module="mod_native_file"/>
<load module="mod_png"/>
<load module="mod_local_stream"/>
<load module="mod_tone_stream"/>
<load module="mod_lua"/>
<load module="mod_say_en"/>

⚠️ 排障实录:这份默认清单按「全模块」假设写就,与源码编译的白名单(安装指南 4.6 节 35 模块)对不齐时,启动日志会出现成组 [CRIT] switch_loadable_module.c:1815 Error Loading module ... cannot open shared object file: No such file or directory(实测环境命中 mod_enum/mod_verto/mod_signalwire/mod_fsv/mod_spandsp/mod_g723_1/mod_g729/mod_amr/mod_b64/mod_av/mod_png 等 12 项)。该报错不阻断启动(缺的模块跳过,其余照常加载);要消除就按白名单注释多余 <load> 行后重启。

💡 说明:运行时增减模块不必改此文件——fs_cli -x "load mod_spandsp" / unload mod_spandsp 即时生效(实测回显 +OK),但重启后以 XML 清单为准;module_exists mod_spandsp 返回 true 可核验模块在位。

5.8 SIP Profile 核心参数(internal.xml / external.xml)

SIP 行为由两个出厂 profile 定义。internal.xml 关键参数实测原文(逐组注释):

<param name="context" value="public"/>
<param name="sip-port" value="$${internal_sip_port}"/>
<param name="dialplan" value="XML"/>
<param name="inbound-codec-prefs" value="$${global_codec_prefs}"/>
<param name="rtp-ip" value="$${local_ip_v4}"/>
<param name="sip-ip" value="$${local_ip_v4}"/>
<param name="apply-inbound-acl" value="domains"/>
<param name="local-network-acl" value="localnet.auto"/>
<param name="auth-calls" value="$${internal_auth_calls}"/>
<param name="challenge-realm" value="auto_from"/>
<param name="inbound-codec-negotiation" value="generous"/>
<param name="tls" value="$${internal_ssl_enable}"/>
<param name="tls-only" value="false"/>
<param name="tls-sip-port" value="$${internal_tls_port}"/>
  • context:来呼进入的拨号计划上下文。分机呼入语境由 directory 侧 user 配置的 user_context 覆盖(默认进 default 语境实现分机互打)。
  • sip-port:引用 vars.xml 的 internal_sip_port=5060。
  • auth-calls:注册与来呼是否鉴权,引用 vars.xml 第 406 行 <X-PRE-PROCESS cmd="set" data="internal_auth_calls=true"/>(出厂 true,即分机注册必须走 directory 密码鉴权;eval $${internal_auth_calls} 实测回显 true)。
  • challenge-realm=auto_from:SIP 401 质询域自动取 From 域(与 sofia status profile internal 回显的 Challenge Realm auto_from 一致)。
  • inbound-codec-negotiation:generous(宽模式,两端清单并集协商)/ greedy(严模式,仅本端清单)。对接不规范终端时 generous 兼容性好。
  • TLS 组:tls 引用 internal_ssl_enable=false(出厂关);开启后走 tls-sip-port(5061)与 certs_dir 下证书。

external.xml(出局/运营商对接)关键差异(实测原文):

<param name="context" value="public"/>
<param name="sip-port" value="$${external_sip_port}"/>
<param name="auth-calls" value="false"/>
<param name="ext-rtp-ip" value="$${external_rtp_ip}"/>
<param name="ext-sip-ip" value="$${external_sip_ip}"/>
<param name="rtp-timeout-sec" value="300"/>
<param name="rtp-hold-timeout-sec" value="1800"/>
  • auth-calls=false:external 不要求来呼注册鉴权(对接运营商按 IP 或按 gateway 处理)。
  • ext-rtp-ip/ext-sip-ip:对外通告地址,引用 vars.xml 的 STUN 解析结果(实测 182.54.113.29);NAT 环境公网互通的关键参数,固定公网 IP 时直接写 IP 替代 STUN。
  • rtp-timeout-sec=300:RTP 静默 300 秒判死挂断(防僵尸通道)。
  • 网关(gateway)挂载:external.xml 顶部 <gateways><X-PRE-PROCESS cmd="include" data="external/*.xml"/></gateways>,external/ 目录下每个 XML 一条运营商中继;sofia status 里 external::example.com(NOREG)即出厂示例网关。

运行态核验(sofia status profile internal,实测节选——与上述参数一一对应):

Name             	internal
RTP-IP           	10.0.0.6
Ext-RTP-IP       	182.54.113.29
SIP-IP           	10.0.0.6
Ext-SIP-IP       	182.54.113.29
URL              	sip:mod_sofia@182.54.113.29:5060
BIND-URL         	sip:mod_sofia@182.54.113.29:5060;maddr=10.0.0.6;transport=udp,tcp
WS-BIND-URL      	sip:mod_sofia@10.0.0.6:5066;transport=ws
WSS-BIND-URL     	sips:mod_sofia@10.0.0.6:7443;transport=wss
CODECS IN        	OPUS,G722,PCMU,PCMA,H264,VP8
CODECS OUT       	OPUS,G722,PCMU,PCMA,H264,VP8
TEL-EVENT        	101
DTMF-MODE        	rfc2833
NOMEDIA          	false
LATE-NEG         	true
REGISTRATIONS    	0

5.9 数据库类(switch.conf / db.conf)

核心状态默认存 SQLite(db_dir 下 core.db 等文件),可外置到 PostgreSQL/MariaDB:

<!-- <param name="core-db-dsn" value="pgsql://hostaddr=127.0.0.1 dbname=freeswitch user=freeswitch password='' options='-c client_min_messages=NOTICE'" /> -->
<!-- <param name="core-db-dsn" value="postgresql://freeswitch:@127.0.0.1/freeswitch?options=-c%20client_min_messages%3DNOTICE" /> -->
<!-- <param name="core-db-dsn" value="mariadb://Server=localhost;Database=freeswitch;Uid=freeswitch;Pwd=pass;" /> -->
  • core-db-dsn:注释态(默认 SQLite)。高并发(数百路以上)时外置 PostgreSQL 可缓解 SQLite 锁竞争;连接串支持 libpq 两种格式(关键字串 pgsql:// 与 URI postgresql://),switch.conf.xml 注释原文列了全部可写形式。
  • core-db-name:注释态,可把 SQLite 文件指到内存盘(如 /dev/shm/core.db)提速(重启丢数据,仅状态类表可接受时用)。
  • mod_pgsql:1.11 已把核心原生 PostgreSQL 支持移除,改由 databases/mod_pgsql 模块承担(switch.conf.xml 注释原文明示「Native PostgreSQL support was removed from the FreeSWITCH Core! … You MUST enable mod_pgsql」);本实测环境已编译该模块(安装指南白名单内)。
  • db.conf.xml(LIMIT 类应用后端):
<configuration name="db.conf" description="LIMIT DB Configuration">
  <settings>
    <!--<param name="odbc-dsn" value="dsn:user:pass"/>-->
  </settings>
</configuration>

mod_db 的 LIMIT/计数默认 SQLite,多节点共享限额时放开 odbc-dsn 指向外部库。

六、生产配置模板

两套按资源规格划分的模板,给出「需要改动的最小参数集 + 改后验证」,其余保持出厂。

6.1 场景 A:小型 IPPBX(≤50 分机 / 4GB 内存 / 50GB 磁盘)

适用:办公室自建 IPPBX,分机注册 + 内外互通 + 简单 IVR。改动清单:

# 1. 换默认注册密码(vars.xml)
sudo sed -i 's|default_password=1234|default_password=q1w2e3r4X|' /usr/local/freeswitch/etc/freeswitch/vars.xml

# 2. ESL 只听本机 + 强密码(event_socket.conf.xml)
sudo sed -i 's|<param name="listen-ip" value="::"/>|<param name="listen-ip" value="127.0.0.1"/>|' \
  /usr/local/freeswitch/etc/freeswitch/autoload_configs/event_socket.conf.xml
sudo sed -i 's|<param name="password" value="ClueCon"/>|<param name="password" value="q1w2e3r4X"/>|' \
  /usr/local/freeswitch/etc/freeswitch/autoload_configs/event_socket.conf.xml

# 3. 日志降级 + 单文件滚动 200MB(switch.conf.xml / logfile.conf.xml)
sudo sed -i 's|<param name="loglevel" value="debug"/>|<param name="loglevel" value="info"/>|' \
  /usr/local/freeswitch/etc/freeswitch/autoload_configs/switch.conf.xml
sudo sed -i 's|<param name="rollover" value="1048576000"/>|<param name="rollover" value="209715200"/>|' \
  /usr/local/freeswitch/etc/freeswitch/autoload_configs/logfile.conf.xml

# 4. 重启生效
sudo systemctl restart freeswitch

验证(实测方法,逐条核验改动落位):

/usr/local/freeswitch/bin/fs_cli -x "fsctl max_sessions"
/usr/local/freeswitch/bin/fs_cli -x 'eval $${console_loglevel}'
/usr/local/freeswitch/bin/fs_cli -x 'eval $${default_password}'
systemctl is-active freeswitch

实测回显:

+OK max sessions: 1000
info
q1w2e3r4X
active

⚠️ 注意:ESL 密码改后,所有 fs_cli 都要带 -p q1w2e3r4X;实测沿用旧密码连接的报错为 [ERROR] fs_cli.c:1699 main() Error Connecting [](认证失败拒绝接入,而非连接超时)。50 分机规模下 max-sessions=1000 与 sps=30 出厂值余量充足,无需下调。

6.2 场景 B:WebRTC 会议服务器(16GB 内存 / NVMe SSD / 200 并发会议方)

适用:浏览器入会为主(mod_verto/mod_rtc + WSS),会议(mod_conference)承载 200 并发方。在场景 A 基础上追加:

# 1. 并发上限按会议规模上调(switch.conf.xml;改后必须重启)
sudo sed -i 's|<param name="max-sessions" value="1000"/>|<param name="max-sessions" value="600"/>|' \
  /usr/local/freeswitch/etc/freeswitch/autoload_configs/switch.conf.xml
# 2. 每秒新建上限上调(大会开场集中入会)
sudo sed -i 's|<param name="sessions-per-second" value="30"/>|<param name="sessions-per-second" value="60"/>|' \
  /usr/local/freeswitch/etc/freeswitch/autoload_configs/switch.conf.xml
# 3. DB 句柄池上调
sudo sed -i 's|<param name="max-db-handles" value="50"/>|<param name="max-db-handles" value="100"/>|' \
  /usr/local/freeswitch/etc/freeswitch/autoload_configs/switch.conf.xml
# 4. TLS 优先:WSS 入会走 7443(vars.xml 打开 internal TLS 按需启用;WebRTC 信令 WSS 由 profile 的 WSS-BIND-URL 承担,默认已开)
sudo systemctl restart freeswitch

验证(实测命令):

/usr/local/freeswitch/bin/fs_cli -x "fsctl max_sessions"
/usr/local/freeswitch/bin/fs_cli -x "fsctl sps"

实测回显(600/60 组合在实测环境核验通过,sps 同法):

+OK max sessions: 600
+OK sessions per second: 30

⚠️ 注意:实测环境仅验证了 max-sessions=600 的生效链路(3.4 节),sps 的 XML 改法与 fsctl sps 60 运行时改法等价,生产以 fsctl sps 回显为准。200 方会议按每方约 30–40MB 估算内存(OPUS 48kHz 转码混音),16GB 内存可承载;开启录制/转码时按混音输出流另计磁盘 IO。

七、常见问题(FAQ)

Q1:改了 switch.conf.xml 的参数,reloadxml 后 fsctl 查值没变? 核心引擎参数(max-sessions、sessions-per-second、max-db-handles 等)只在进程启动时初始化,reloadxml 不会重读。必须 systemctl restart freeswitch(3.4 节完整实测链)。改 dialplan/directory 类用 reloadxml 即可。

Q2:启动日志大量 Error Loading module ... cannot open shared object file? autoload_configs/modules.conf.xml 默认清单 load 了未编译模块(源码编译按白名单裁剪后必现,实测命中 12 项)。不阻断启动;消除法见 5.7 节。

Q3:global_getvar 里 external_rtp_ip=182.54.113.29,但 vars.xml 里写的是 stun:stun.freeswitch.org? X-PRE-PROCESS cmd="stun-set" 会在启动时经 STUN 解析公网地址并写入变量,global_getvar 显示解析结果。无公网/内网环境 STUN 探测会拖慢启动,安装指南的 systemd 单元用 -nonat 关闭了自动探测;固定公网 IP 的服务器直接把 stun-set 行改为 cmd="set" 写死 IP 更稳。

Q4:fs_cli 报 -ERR [err] REQUEST DENIED? Event Socket 密码不符(改过 event_socket.conf.xml 后 fs_cli 未带 -p)。fs_cli -p <密码> 或写入 ~/.fs_cli_conf。

Q5:想看某个 profile 的全部生效参数? fs_cli -x "sofia status profile internal"(回显即运行值,5.8 节有节选);SIP 信令级排障再加 sofia profile internal siptrace on(switch.conf.xml 的 cli-keybindings 出厂把 10/11 号键绑到它)。

Q6:配置改坏了怎么回滚? 改前有 .bak 就直接还原后重启;没有备份时,源码包 freeswitch-1.11.3.-release/conf/ 内是全套出厂配置,拷回对应文件再 reloadxml/重启。

八、参考链接