Hi everyone,
I’m running into a critical issue with Asterisk ARI that I haven’t been able to solve despite extensive debugging.
Setup:
- Asterisk 20.11 on CentOS 9
- Using ARI with a Python client (via
asterisk-ari
lib) - A callbot system that handles simultaneous calls
- Calls are managed in Stasis with recording, playback, and spying channels
Problem:
After ~10 to 20 minutes of normal operation under load, my ARI app starts failing to retrieve channels using:
client.channels.get(channelId=...)
This happens right after receiving a StasisStart
event for that same channel. I log the channel ID from StasisStart
, then immediately try to retrieve the channel to attach it to my internal state — and I get a 404 from the ARI API:
404 Client Error: Not Found for url: http://localhost:8088/ari/channels/<channel_id>
Even more confusing: the channel doesn’t appear in client.channels.list()
, as if it never existed, even though StasisStart
was just received.
This starts happening consistently after several minutes of high activity. Until then, everything works perfectly.
Observations:
- WebSocket seems still open — I never receive a disconnect event.
- My
client.run(apps="app_dialer")
loop is in a background thread with auto-retry if it crashes (but I never see a crash). - I increased the
ulimit -n
to 524288, so it’s not a file descriptor exhaustion. - Logging shows ~300 channels when this happens. Mostly
Snoop/
channels, somePJSIP/
. - I even tried adding up to 5 seconds of delay before retrieving the channel from ARI after
StasisStart
, in case it was a race condition — it didn’t help.
Questions:
- Is there a hard ARI or Asterisk limit on channels or events per WebSocket client?
- Could some internal ARI channel registry be getting corrupted?
- Could “orphaned” Snoop channels be exhausting something internally?
- Any workaround that avoids losing control of in-progress calls?
My Dial Plan
[incoming]
exten => _X.,1,NoOp(Appel entrant reçu)
same => n,Answer()
same => n,Set(FULL_RECORD_PATH=/var/spool/asterisk/recording/full_call/${UNIQUEID}.wav)
same => n,MixMonitor(${FULL_RECORD_PATH})
same => n,Set(TALK_DETECT(set)=)
same => n,Stasis(app_dialer)
same => n,Hangup()
Any guidance or ideas would be greatly appreciated
Thanks in advance!