FreePBX Ring Group failover: Send SMS to caller on missed call (Ring Group no-answer) but call keeps restarting in a loop

I am trying to implement a Ring Group failover scenario in FreePBX where, if a caller’s call is missed (no one answers the Ring Group), the system should send an SMS to the caller instead of voicemail.

What I want to achieve

  • When a caller calls my main number

  • The call goes to a Ring Group

  • If no agent answers the call

  • I want to send an SMS to the caller saying something like:

“We are sorry we missed your call, but we are either working with a client or stepped away from the office…”

The SMS content/template is handled by my own SMS server.
From FreePBX/Asterisk, I only want to:

  • Capture the CallerID (caller number)

  • Send it to my SMS API

  • Let the SMS application send the message using a default template

Current Setup

Call Flow

  1. Inbound call arrives on DID
    +15550001111 (dummy)

  2. Call is routed to Ring Group 8889

  3. Ring Group rings extension 1000 for 5 seconds

  4. If nobody answers, Ring Group No Answer Destination is set to a Custom Destination

  5. Custom Destination target:

Gosub(sms-api-8889,s,1)

Dialplan (simplified)

[sms-api-8889] exten => s,1,NoOp(=== Missed Call SMS ===) same => n,Set(SRC=${FILTER(0-9,${CALLERID(num)})}) same => n,AGI(send_missedcall_sms.php,${SRC}) same => n,Hangup()

AGI Script

  • send_missedcall_sms.php

  • Receives the caller number

  • Sends it to my SMS API endpoint

  • SMS server sends the message using a default template

  • API returns 200 OK

The SMS part works perfectly.

Problem I Am Facing

After the SMS is sent:

  • The call does not fully stop

  • A new inbound call attempt starts again

  • Ring Group rings again

  • No answer → SMS is sent again

  • Call starts again

  • This continues in a loop

From the logs, I can see multiple inbound channels, for example:

PJSIP/Twilio-0000000f
PJSIP/Twilio-00000011
PJSIP/Twilio-00000013

And the SMS log confirms multiple sends:

REQUEST dest=15550002222
RESPONSE http_code=200

REQUEST dest=15550002222
RESPONSE http_code=200

REQUEST dest=15550002222
RESPONSE http_code=200

Each SMS corresponds to a new inbound call attempt, not the same call looping internally.

How to fix this issue.

I believe that the trunk is retrying the call because Asterisk has effectively abandoned it. Before calling Hangup, you could call Busy or Congestion, see Dialplan Applications - Asterisk Documentation

but IMO you should Answer the call and play a message, with content similar to the SMS.

This is my code and it’s called via the Ring Group Failover destination –>custom destination

[sms-api-8889]
exten => s,1,NoOp(=== SMS API HIT START (AGI) ===)

; --------- guard: donot run in the same call ----------
same => n,GotoIf($[“${SMS_SENT}”=“1”]?done)
same => n,Set(SMS_SENT=1)

; callerid normalize
same => n,Set(SRC=${CALLERID(num)})
same => n,Set(SRC=${FILTER(0-9,${SRC})})
same => n,NoOp(CallerID digits: ${SRC})

; AGI call
same => n,AGI(send_missedcall_sms.php,${SRC})

same => n(done),NoOp(=== SMS API HIT END (AGI) ===)
same => n,Hangup()

You need to set up what the caller will hear (message, busy signal, SIT, etc.)

Or, if it is important that the provider not treat the call as answered, you need to pass a value to Hangup which will cause the the upstream system to consider the call to have failed permanently. This might involve lying, if they are particularly keen on getting the call through.

The values available can be found by searching for ISDN cause codes, but note that, as well as the ISDN code, in the Reason header, the SIP status line will include the nearest SIP code, which might not have the same meaning, to the provider.