Administrator
发布于 2026-11-13 / 1 阅读
0
0

FreeSWITCH Configuration Lab 16 | Subscribe to Call Events over ESL

English
中文

Have 7101 call 7102. Answer at 7102, exchange a short phrase, and hang up. In a nearby terminal, look for answer, bridge, and hangup-complete events. Compare the channel UUIDs for both legs. The previous lab inspected CDRs on disk. This one observes the changes as they happen. Use a private FreeSWITCH test node where both SIP extensions already register and can call each other. The examples refer to v1.11.3.

Configure the local Event Socket listener

Use inbound ESL: fs_cli connects to FreeSWITCH. In outbound mode, FreeSWITCH connects to an application from the dialplan. This lab needs no dialplan change.

Use an existing console to run global_getvar conf_dir. If the console is unavailable, check the service launch arguments or installation layout. Back up autoload_configs/event_socket.conf.xml and replace it with the following on the lab node. Check that the installed mod_event_socket is listed in autoload_configs/modules.conf.xml as <load module="mod_event_socket"/>. Inventory any existing ESL clients before changing their listener.

<configuration name="event_socket.conf" description="Local ESL">
  <settings>
    <!-- 监听范围仅限本机 IPv4 回环地址。 -->
    <param name="listen-ip" value="127.0.0.1"/>
    <param name="listen-port" value="8021"/>
    <!-- 使用本机生成的独立强密码替换占位符。 -->
    <param name="password" value="REPLACE_WITH_LOCAL_SECRET"/>
    <!-- 在认证前检查来源地址,关闭 NAT 端口映射。 -->
    <param name="apply-inbound-acl" value="loopback.auto"/>
    <param name="nat-map" value="false"/>
  </settings>
</configuration>

The listener binds to IPv4 loopback at 127.0.0.1, TCP port 8021. Run the client on the same host or in the same container network namespace. The vanilla file explicitly uses ::, which has a wider listening scope. Confirm the actual bind after the change. SIP registration and RTP retain their existing settings.

Replace the password placeholder with a separately generated strong secret, such as a long random alphanumeric string from a password manager. Restrict read access to both configuration files. ESL authentication grants broad access. Event subscription is the use made by this lab. The loopback.auto ACL checks the source before authentication and is also the v1.11.3 fallback when no inbound ACL is specified. For cross-host collection, a local process can forward selected fields over a controlled internal interface. Setting nat-map=false disables a mapping request for this listener.

If binding fails, stop-on-bind-error in v1.11.3 controls whether the listener exits the startup path or retries. Check for a port conflict in the system listener table and logs. The optional debug setting increases module logging and can be reset after diagnosis.

Connect and subscribe with fs_cli

Under your test account, add a separate profile to ~/.fs_cli_conf, creating the file if needed. Set mode 600. Put the same real secret in the client profile and server XML. The password then stays out of the command line and terminal history.

[esl-lab]
host => 127.0.0.1
port => 8021
password => REPLACE_WITH_LOCAL_SECRET

Restart the isolated node via its service manager with no live calls. A restart interrupts active calls and ESL clients. Keep an OS console available for a maintenance change. reloadxml alone will not rebind the running socket. These commands assume a Linux systemd installation. Use the actual unit name on the node.

# 服务单元名按测试机的安装方式调整。
sudo systemctl restart freeswitch
# 查看监听地址,再验证客户端配置能用。
sudo ss -lntp 'sport = :8021'
fs_cli -x 'status' esl-lab

Check for 127.0.0.1:8021 in the listener output, then confirm that status returns FreeSWITCH runtime information. Open an interactive fs_cli esl-lab session and enter the following commands.

/nolog
/event plain CHANNEL_ANSWER CHANNEL_BRIDGE CHANNEL_HANGUP_COMPLETE

/nolog stops the server log stream on this connection. The event subscription uses plain headers. Application clients can also request JSON or XML. A raw client must read the outer headers and then the exact byte count in Content-Length. TCP supplies a stream. A read may deliver part of a frame or several frames. An ESL library can handle framing for the application.

Compare the events from 7101 and 7102

Wait for subscription success, dial from 7101, and answer at 7102. After exchanging audio, hang up. Read the Unique-ID in CHANNEL_ANSWER. On CHANNEL_BRIDGE, check Bridge-A-Unique-ID, Bridge-B-Unique-ID, or Other-Leg-Unique-ID when present. The answer and bridge describe different stages. Look up the leg's Hangup-Cause in CHANNEL_HANGUP_COMPLETE. Event-Date-Timestamp counts microseconds since the Unix epoch.

On a second call, let 7101 cancel while 7102 rings. Check hangup events for the channels actually created. A straightforward pre-answer cancellation should leave no evidence of a bridge between those two legs. If an IVR answered the inbound leg first, that leg can still have an answer event. 7101 and 7102 are SIP extensions. Queue agent, tier, and dispatch activity require queue events such as callcenter::info. After identifying a UUID, /filter Unique-ID <channel-uuid> narrows the view to that leg. Remove the filter before comparing both legs.

The subscription delivers live events after setup. After a disconnection, reconnect and resubscribe, then check live channel state and persisted CDRs for gaps. Account for multiple legs when counting business calls. These are expected results checked against public templates and source. No FreeSWITCH instance was used to run the lab.

Troubleshoot and restore

  • Connection refused. Check the module and actual listening address with ss, then inspect port ownership and service logs. A container's loopback listener is local to that namespace.
  • Rejected after connecting. Distinguish source ACL rejection from failed authentication. Check the source for the former and the chosen profile and password for the latter.
  • Status works and events are missing. Use an interactive session, confirm subscription success, and place a fresh call. Clear an old single-leg filter or open a new session.
  • Events cannot be matched to a CDR. Join hangup-complete Unique-ID to the CSV uuid column before grouping by business ID. Keep necessary fields and redact data before sharing traces.

Cancel subscriptions and exit when finished. To roll back, restore the backed-up server file and original client profile, restart with calls drained, and verify that original clients reconnect and subscribe again.

/noevents
/exit

Sources


评论