Der Dialplan – extensions.conf

Die Datei "extensions.conf" ist eine der am häufigsten verwendeten und wichtigsten Konfigurationsdateien in der Asterisk PBX - sie enthält den Dialplan. Was ist der Dialplan? Der Dialplan, oder wir sagen "das Herz des Asterisk-Systems", definiert, wie die Asterisk PBX eingehende und ausgehende Anrufe verarbeiten wird, sie enthält auch alle Nebenstellennummern. Der Dialplan ist in Abschnitte unterteilt, die als Kontexte bezeichnet werden. Jeder Kontext besteht aus mehr als einer Erweiterung. Was ist eine Erweiterung? Die Erweiterung ist die Telefonnummer, es können Zahlen, Briefe oder beides sein. Jede Erweiterung hat eine Priorität und eine Anwendung. Mit Hilfe von Kontexten können wir unseren Dialplan organisieren.

Änderungen am Dialplan werden der Asterisk-PBX dadurch bekannt gemacht, indem man in die Asterisk-CLI wechselt

# asterisk -rvvvv

und den Dailplan neulädt,

dailplan reload

oder direkt auf der Linux-Konsole

# asterisk -rx „dailplan reload“

absetzt.

[general]
--> Einige Einstellungen stehen hier
[globals]
--> Definitionen einiger globaler Variablen stehen hier
[context1]
-->Extension 1, Priority 1, Anwendung
-->Extension 1, Priority 2, Anwendung
--> Extension Helpdesk, Priority 1, Anwendung
...
[context2]
--> extension 999, priority 1, application
--> extension 999, priority 1, application

Konkreter sieht das so aus.

[general]
static=yes
writeprotect=yes
autofallthrough=yes
extenpatternmatchnew=no
clearglobalvars=no
userscontext=unspecified

  • static=yes
    writeprotect=yes

    Es wird auf alle automatischen Änderungen am Dialplan verzichtet.

  • autofallthrough=yes
    Das ist die Default-Einstellung, die hier explizit auflistet wird. Sobald ein Dialplan für eine Extension abgelaufen ist, dann macht die Asterisk-PBX in jedem Fall ein Hangup und kappt somit die Verbindung. Das ist durchaus sicher.

  • extenpatternmatchnew=no
    Das ist ein neues Feature für sehr große Dialpläne mit mehr als 50 Endpoints. Es kann in der CLI mit "dialplan set extenpatternmatchnew true" oder "dialplan set extenpatternmatchnew false" gesetzt werden, bzw. auf der Linux-Konsole mit asterisk -rx „dialplan set extenpatternmatchnew true/false“.

  • clearglobalvars=no
    Hierdurch werden globale Variablen beibehalten, wenn der Dialplan neu geladen wird.

  • userscontext=unspecified
    Das ist eine wichtige Einstellung, die einen Default-Kontext für eingehende Anrufe definiert, für die kein anderer Kontext gefunden werden kann. Hier werden solche Anrufe explizit nach "unspecified" umgeleitet und dieser Kontext wird auch als leer respektive als "nicht erlaubt" definiert.

Das wird gleich wie folgt realistischer umgesetzt.

[unspecified]
exten => _X.,1,Answer()
exten => _X.,2,Verbose(D E F A U L T ==> ${CALLERID(num)} at ${STRFTIME(${EPOCH},,%Y%m%d-%H%M%S)} in UNSPECIFIED when was tried to call number ${EXTEN})
exten => _X.,3,Playback(No_permissions)
exten => _X.,4,Hangup()

Hier ist dargestellt, dass wenn eine beliebige Nummer (_X.) heraustelefonieren (extern) will, die uns unbekannt ist und auch nicht zulassen wollen mit einem Log (Verbose) und einer Nachricht (Playback) aus der Datei „No_permissions.wav“ aufgelegt wird (Hangup()).

Mit „extern“ wird im Dialplan also das Heraustelefonieren mit allen definierten Endpoints angeregt.
Eleganter und übersichtlicher lässt sich das auch so formulieren:

[unspecified]
exten => _X.,1,Answer()
same => n,Verbose(D E F A U L T ==> ${CALLERID(num)} kam um ${STRFTIME(${EPOCH},,%Y%m%d-%H%M%S)} in UNSPECIFIED an, als es versuchte die Nummer ${EXTEN} anzurufen.)
  same => n,Playback(No_permissions)
  same => n,Hangup()

[trunk_15201]
; direkt einzelne User anwaehlen
exten => contact_name1,1,Dial(PJSIP/contact_name1)
exten => contact_name2,1,Dial(PJSIP/contact_name2)

;Mailboxabfrage von intern ohne PIN
exten => mailboxname,1,VoiceMailMain(mailboxname@VoiceMailContext,s)
exten => 5201,1,VoiceMailMain(5201@VoiceMail1,s)

Die Namen contact_name1, contact_name2 und mailboxname kann man von SIP-Telefonen direkt anwählen, denn SIP kann auch Namen wählen und nicht nur Nummern. Die Anwahl einzelner User dient der internen Kommunikation von einem Telefon zum Anderen, dabei geht keine Kommunikation nach außen. Das Gleiche gilt für das Abfragen der Voicemailbox.

Nachfolgend wird der allgemeine Weg nach Außen definiert, vorzugsweise der über die Telekom. Bei anderen Providern muss also analog „@tel.t-online.de“ gegen den entsprechenden Wert ausgetauscht werden. Die Dateien im Playback() sind selbst erstellte WAV-Dateien und diese Zeilen sind optional. Wichtig ist die Zeile mit Hangup().

;National, mit +49 gewaehlt
exten => _+49ZXX!.,1,Dial(PJSIP/telekom_15201_out/sip:0${EXTEN:3}@tel.t-online.de,60)
exten => _+49ZXX!.,n,Hangup()

;International
exten => _+X.,1,NoOp(Blocked: ${EXTEN})
  same => n,Playback(sorry-cant-let-you-do-that)
  same => n,Hangup()
exten => _00X.,1,NoOp(Blocked: ${EXTEN})
  same => n,Playback(sorry-cant-let-you-do-that)
  same => n,Hangup()

;National, mit 0 vorneweg
exten => _0Z.,1,Dial(PJSIP/telekom_15201_out/sip:${EXTEN}@tel.t-online.de,60)
exten => _0Z.,n,Hangup()
;Ortsnetz
exten => _Z.,1,Dial(PJSIP/telekom_15201_out/sip:${EXTEN}@tel.t-online.de,60)
exten => _Z.,n,Hangup()

;Notrufe gehen immer
exten => 110,1,Dial(PJSIP/telekom_15201_out/sip:110@tel.t-online.de,60)
exten => 110,n,Hangup()
exten => 112,1,Dial(PJSIP/telekom_15201_out/sip:112@tel.t-online.de,60)
exten => 112,n,Hangup()

Wichtig sind die folgenden Regeln, um kostenpflichtige Sondernummern zu sperren.

Inzwischen bieten die Provider solche Sperrungen auch auf Ihren Benutzerportalen an, besser ist es aber, diese bereits auf der Asterisk-PBX zu sperren. Die Zeile mit Plackback() kann man wieder als optional ansehen. Manchmal es jedoch Sinn, wenn der Telefonierende erfährt warum die Verbindung aufgehängt wird.

; ********* Kostenpflichtige Sondernummern ***********
exten => _0137Z.,1,NoOp(Blocked: ${EXTEN}) ;Servicenummern für TeleVoting
  same => n,Playback(sorry-cant-let-you-do-that3)
  same => n,Hangup()
exten => _0138Z.,1,NoOp(Blocked: ${EXTEN})
  same => n,Playback(sorry-cant-let-you-do-that3)
  same => n,Hangup()
exten => _0180Z.,1,NoOp(Blocked: ${EXTEN}) ;Servicenummern für Service-Dienste
  same => n,Playback(sorry-cant-let-you-do-that3)
  same => n,Hangup()
exten => _0181Z.,1,NoOp(Blocked: ${EXTEN}) ;Zugang zu VPN, Kunden-Hotline
  same => n,Playback(sorry-cant-let-you-do-that3)
  same => n,Hangup()
exten => _0182Z.,1,NoOp(Blocked: ${EXTEN})
  same => n,Playback(sorry-cant-let-you-do-that3)
  same => n,Hangup()
exten => _0183Z.,1,NoOp(Blocked: ${EXTEN})
  same => n,Playback(sorry-cant-let-you-do-that3)
  same => n,Hangup()
exten => _0184Z.,1,NoOp(Blocked: ${EXTEN})
  same => n,Playback(sorry-cant-let-you-do-that3)
  same => n,Hangup()
exten => _0185Z.,1,NoOp(Blocked: ${EXTEN})
  same => n,Playback(sorry-cant-let-you-do-that3)
  same => n,Hangup()
exten => _0186Z.,1,NoOp(Blocked: ${EXTEN})
  same => n,Playback(sorry-cant-let-you-do-that3)
  same => n,Hangup()
exten => _0187Z.,1,NoOp(Blocked: ${EXTEN})
  same => n,Playback(sorry-cant-let-you-do-that3)
  same => n,Hangup()
exten => _0188Z.,1,NoOp(Blocked: ${EXTEN})
  same => n,Playback(sorry-cant-let-you-do-that3)
  same => n,Hangup()
exten => _032Z.,1,NoOp(Blocked: ${EXTEN}) ;Vorwahl für Internettelefonie-Nutzer
  same => n,Playback(sorry-cant-let-you-do-that3)
  same => n,Hangup()
exten => _0700Z.,1,NoOp(Blocked: ${EXTEN}) ;persönliche Rufnummer 0700
  same => n,Playback(sorry-cant-let-you-do-that3)
  same => n,Hangup()
exten => _09001Z.,1,NoOp(Blocked: ${EXTEN}) ;Premiumdienste Information
  same => n,Playback(sorry-cant-let-you-do-that3)
  same => n,Hangup()
exten => _09003Z.,1,NoOp(Blocked: ${EXTEN}) ;Premiumdienste Unterhaltung
  same => n,Playback(sorry-cant-let-you-do-that3)
  same => n,Hangup()
exten => _09005Z.,1,NoOp(Blocked: ${EXTEN}) ;Premiumdienste Sonstiges, Erotik
  same => n,Playback(sorry-cant-let-you-do-that3)
  same => n,Hangup()
exten => _09009Z.,1,NoOp(Blocked: ${EXTEN}) ;Dialer
 same => n,Playback(sorry-cant-let-you-do-that3)
 same => n,Hangup()

Jetzt wird noch der Kontext für eingehende Gespräche von außen benötigt. Das Basis-Schema sieht wie folgt aus.

exten => own-number,1,Dial(PJSIP/own-phone,30)
exten => own-number,n,VoiceMail(mailboxname@mailboxcontext)
exten => own-number,n,Hangup()

Wichtig ist der Abschnitts-Context, das sich auch in der pjsip.conf für ausgehende Telefonate wiederfindet. Die erste Zeile beinhaltet mit own-number die jeweilige Festnetznummer (ohne +49, Vorwahl mit 0) und mit own-phone das in der pjsip.conf definierte Telefon oder den Endpoint. Weiter wird mit der Priorität „1“ die Funktion Dial() für PJSIP/Endpoint aufgerufen und damit klingelt das Telefon 30 Sekunden lang. Die zweite Zeile bezieht sich immer noch auf die gleiche Rufnummer und teilt Asterisk-PBX mit, was nach den 30 Sekunden geschehen soll, sofern nicht der Anruf vorher angenommen wird. In diesem Fall soll nämlich die Funktion VoiceMail() die Mailbox starten und mit der dritten Zeile wird das Gespräch wieder beendet.
Zum Einen wird eine solche Strukturierung recht schnell unübersichtlich und zum Anderen springt hier sofort ohne Ansagetext die VoiceBox an, ohne dass der Anrufende davon etwas mitbekommt.

[telekom_15201_in]
exten => own-number,1,Dial(PJSIP/own-phone,30)
  same => n,Playback(Ansagetext)
  same => n,VoiceMail(
mailboxname@mailboxcontext)
  same => n,Hangup()

Mit dieser Variante ersetzt „same => n,“ den längeren Part „exten => own-number,n,“, das ist weniger fehleranfällig und übersichtlicher. Und die zusätzliche Zeile mit dem Playback() fügt vor der Aufnahme einen Ansagetext aus der Datei Ansagetext.wav ein.
Auf diese Art und Weise lassen sich jetzt für alle Endpoints repektive Telefonnummern die Regeln erstellen. Jeweils unterhalb desselbes Abschnitt-
Context.