Next Available SIP Channel

I’ve got multiple SIP channels for each of my phone numbers. I’d to be able to define a set of outgoing channels and dial out on the next available one (or if possible, load balance between them). If the remote party hangs up, I don’t want it to start trying another line either.

How would I do this? I’m sure there is something to detect ‘CHANNEL UNAVAILABLE’ and try another line. Or maybe Asterisk already has something built in to load balance SIP trunks.

How about I ask this. Would people recommend that I use GROUP() to check use of the lines, or would it be better to use Dialplan errors.


By the way I have 4 trunks.

Never mind, seems I found the answer to my own question. It’s not exactly what I like (seems more complex than it should be in Asterisk 1.4) but oh well.


; ARG1 is the number you want to call
; This macro tries all our outgoing channels in the order and call volume I want
exten => s,1,set(TRIES=0) ;
; here we list the outgoing lines specified as TRYn = NNtype/name
; where TRYn is TRY1 to TRYn and NN is maximum number of calls I want to allow on the channel
exten => s,n,set(TRY1=01SIP/fishing) ; max of 1 simultaneous call
exten => s,n,set(TRY2=03IAX2/seattle) ; max of 3 simultaneous calls
exten => s,n,set(TRY3=03IAX2/newyork)
exten => s,n,set(TRY4=01SIP/sipdiscount)
exten => s,n,set(TRY5=01SIP/internetcalls)
exten => s,n,set(TRY6=01Zap/3)
exten => s,n,set(TRY7=01Zap/1)
exten => s,n,set(TRY8=01Zap/2)
exten => s,n(nextone),set(TRIES=$<<${TRIES} + 1>>]) ; increment TRIES by 1

exten => s,n,set(DIALSTRING=${TRY${TRIES}}) ; assign TRYn to DIALSTRING
exten => s,n,gotoif($<<"${DIALSTRING}" = “”>>?donehere) ; see if we’ve run out of things to try
exten => s,n,gotoif($<<${GROUP_COUNT(${DIALSTRING:2})} >= ${DIALSTRING:0:2}>>?nextone) ; see if we’ve used up the allowed calls on this channel
exten => s,n,ChanIsAvail(${DIALSTRING:2}) ; see if we can make a call on this channel
exten => s,n,gotoif($<<${AVAILSTATUS} = 0>>?:nextone)
exten => s,n,set(GROUP()=${DIALSTRING:2}) ; assign the current GROUP to the contents of DIALSTRING
exten => s,n,dial(${DIALSTRING:2}/${ARG1},j) ; dial the phone
exten => s,n,hangup()
exten => s,n(donehere),congestion() ; we only get here if everything failed