123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298 |
- EXTENSION LOGIC :
- There are two levels of parameter evaluation done in asterisk in
- extensions.conf.
- The first, and most frequently used, is the substitution of variable
- references with their values.
- Then there are the evaluations done in $[ .. ]. This will be
- discussed below.
- ___________________________
- PARAMETER QUOTING:
- ---------------------------
- exten => s,5,BackGround,blabla
- The parameter (blabla) can be quoted ("blabla"). In this case, a
- comma does not terminate the field. However, the double quotes
- will be passed down to the Background command, in this example.
- Also, characters special to variable substitution, expression evaluation, etc
- (see below), can be quoted. For example, to literally use a $ on the
- string "$1231", quote it with a preceding \. Special characters that must
- be quoted to be used, are [ ] $ " \. (to write \ itself, use \\).
- These Double quotes and escapes are evaluated at the level of the
- asterisk config file parser.
- Double quotes can also be used inside expressions, as discussed below.
- ___________________________
- VARIABLES:
- ---------------------------
- Parameter strings can include variables. Variable names are arbitrary strings.
- They are stored in the respective channel structure.
- To set a variable to a particular value, do :
- ;exten => 1,2,SetVar,varname=value
- You can substitute the value of a variable everywhere using ${variablename}.
- For example, to stringwise append $lala to $blabla and store result in $koko,
- do:
- ;exten => 1,2,SetVar,koko=${blabla}${lala}
- There are also the following special variables:
- ${ACCOUNTCODE} Account code (if specified)
- ${CALLERID} Caller ID
- ${CALLERIDNAME} Caller ID Name only
- ${CALLERIDNUM} Caller ID Number only
- ${CALLINGPRES} PRI Caller ID presentation for incoming calls
- ${CHANNEL} Current channel name
- ${CONTEXT} Current context
- ${DATETIME} Current date time in the format: DDMMYYYY-HH:MM:SS
- ${DNID} Dialed Number Identifier
- ${ENUM} Result of application EnumLookup
- ${EPOCH} Current unix style epoch
- ${EXTEN} Current extension
- ${ENV(VAR)} Environmental variable VAR
- ${HANGUPCAUSE} Asterisk hangup cause
- ${INVALID_EXTEN}The invalid called extension (used in the "i" extension)
- ${LANGUAGE} Current language
- ${LEN(VAR)} String length of VAR (integer)
- ${MEETMESECS} Number of seconds a user participated in a MeetMe conference
- ${PRIORITY} Current priority
- ${RDNIS} Redirected Dial Number ID Service
- ${SIPCALLID} SIP Call-ID: header verbatim (for logging or CDR matching)
- ${SIPDOMAIN} SIP destination domain of an inbound call (if appropriate)
- ${SIPUSERAGENT} SIP user agent
- ${TIMESTAMP} Current date time in the format: YYYYMMDD-HHMMSS
- ${TXTCIDNAME} Result of application TXTCIDName
- ${UNIQUEID} Current call unique identifier
- NOTE: Attempting to set any of these "special" variables will not change
- their value, but will not display any warning either.
- The dial() application sets the following variables:
- ${DIALEDPEERNAME} Dialed peer name
- ${DIALEDPEERNUMBER} Dialed peer number
- ${DIALEDTIME} Total time for the call in seconds (Network time).
- ${ANSWEREDTIME} Time from answer to end of call in seconds (Billable time).
- ${DIALSTATUS} Status of the call, one of:
- CHANUNAVAIL | CONGESTION | BUSY | NOANSWER | ANSWER | CANCEL
- There are two reference modes - reference by value and reference by name.
- To refer to a variable with its name (as an argument to a function that
- requires a variable), just write the name. To refer to the variable's value,
- enclose it inside ${}. For example, SetVar takes as the first argument
- (before the =) a variable name, so:
- ;exten => 1,2,SetVar,koko=lala
- ;exten => 1,3,SetVar,${koko}=blabla
- stores to the variable "koko" the value "lala" and to variable "lala" the
- value "blabla".
- In fact, everything contained ${here} is just replaced with the value of
- the variable "here".
- ___________________________
- EXPRESSIONS:
- ---------------------------
- Everything contained inside a bracket pair prefixed by a $ (like $[this]) is
- considered as an expression and it is evaluated. Evaluation works similar to
- (but is done on a later stage than) variable substitution: the expression
- (including the square brackets) is replaced by the result of the expression
- evaluation. The arguments and operands of the expression MUST BE separated
- by at least one space.
- For example, after the sequence:
- exten => 1,1,SetVar,"lala=$[1 + 2]";
- exten => 1,2,SetVar,"koko=$[2 * ${lala}]";
- the value of variable koko is "6".
- And, further:
- exten => 1,1,SetVar,"lala=$[1+2]";
- will not work as you might have expected. Since all the chars in the single
- token "1+2" are not numbers, it will be evaluated as the string "1+2". Again,
- please do not forget, that this is a very simple parsing engine, and it
- uses a space (at least one), to separate "tokens".
- and, further:
- exten => 1,1,SetVar,"lala=$[ 1 + 2 ]";
- will parse as intended. Extra spaces are ignored.
- ___________________________
- SPACES INSIDE VARIABLE
- ---------------------------
- If the variable being evaluated contains spaces, there can be problems.
- For these cases, double quotes around text that may contain spaces
- will force the surrounded text to be evaluated as a single token.
- The double quotes will be counted as part of that lexical token.
- As an example:
- exten => s,6,GotoIf($[ "${CALLERIDNAME}" : "Privacy Manager" ]?callerid-liar|s|1:s|7)
- The variable CALLERIDNAME could evaluate to "DELOREAN MOTORS" (with a space)
- but the above will evaluate to:
- "DELOREAN MOTORS" : "Privacy Manager"
- and will evaluate to 0.
- The above without double quotes would have evaluated to:
- DELOREAN MOTORS : Privacy Manager
- and will result in syntax errors, because token DELOREAN is immediately
- followed by token MOTORS and the expression parser will not know how to
- evaluate this expression.
- _____________________
- OPERATORS
- ---------------------
- Operators are listed below in order of increasing precedence. Operators
- with equal precedence are grouped within { } symbols.
- expr1 | expr2
- Return the evaluation of expr1 if it is neither an empty string
- nor zero; otherwise, returns the evaluation of expr2.
- expr1 & expr2
- Return the evaluation of expr1 if neither expression evaluates to
- an empty string or zero; otherwise, returns zero.
- expr1 {=, >, >=, <, <=, !=} expr2
- Return the results of integer comparison if both arguments are
- integers; otherwise, returns the results of string comparison
- using the locale-specific collation sequence. The result of each
- comparison is 1 if the specified relation is true, or 0 if the
- relation is false.
- expr1 {+, -} expr2
- Return the results of addition or subtraction of integer-valued
- arguments.
- expr1 {*, /, %} expr2
- Return the results of multiplication, integer division, or
- remainder of integer-valued arguments.
- expr1 : expr2
- The `:' operator matches expr1 against expr2, which must be a
- regular expression. The regular expression is anchored to the
- beginning of the string with an implicit `^'.
- If the match succeeds and the pattern contains at least one regu-
- lar expression subexpression `\(...\)', the string correspond-
- ing to `\1' is returned; otherwise the matching operator
- returns the number of characters matched. If the match fails and
- the pattern contains a regular expression subexpression the null
- string is returned; otherwise 0.
- Parentheses are used for grouping in the usual manner.
- The parser must be parsed with bison (bison is REQUIRED - yacc cannot
- produce pure parsers, which are reentrant)
- ___________________________
- CONDITIONALS
- ---------------------------
- There is one conditional operator - the conditional goto :
- ;exten => 1,2,gotoif,condition?label1:label2
- If condition is true go to label1, else go to label2. Labels are interpreted
- exactly as in the normal goto command.
- "condition" is just a string. If the string is empty or "0", the condition
- is considered to be false, if it's anything else, the condition is true.
- This is designed to be used together with the expression syntax described
- above, eg :
- exten => 1,2,gotoif,$[${CALLERID} = 123456]?2|1:3|1
- Example of use :
- exten => s,2,SetVar,"vara=1"
- exten => s,3,SetVar,"varb=$[${vara} + 2]"
- exten => s,4,SetVar,"varc=$[${varb} * 2]"
- exten => s,5,GotoIf,"$[${varc} = 6]?99|1:s|6";
- ___________________________
- PARSE ERRORS
- ---------------------------
- Syntax errors are now output with 3 lines.
- If the extensions.conf file contains a line like:
- exten => s,6,GotoIf($[ "${CALLERIDNUM}" = "3071234567" & "${CALLERIDNAME}" : "Privacy Manager" ]?callerid-liar|s|1:s|7)
- You may see an error in /var/log/asterisk/messages like this:
- May 3 15:58:53 WARNING[1234455344]: ast_yyerror(): syntax error: parse error; Input:
- "3072312154" : "3071234567" & & "Steves Extension" : "Privacy Manager"
- ^^^^^^^^^^^^^^^^^^^^^^^^^^^
- ^
- The first line shows the string passed to the expression parser. This
- string is the result of the variable replacements, etc. This way, you
- can see the actual string that went into the parser.
- The second line usually shows a string of '^' chars, that show what's
- been legally parsed so far.
- And the third line shows where the parser was (lookahead token lexing,
- etc), when the parse hit the rocks. A single '^' here. The error is
- going to be somewhere between the last '^' on the second line, and the
- '^' on the third line. That's right, in the example above, there are two
- '&' chars, separated by a space, and this is a definite no-no!
- ___________________________
- NULL STRINGS
- ---------------------------
- Testing to see if a string is null can be done in one of two different ways:
- exten => _XX.,1,GotoIf($["${calledid}" != ""]?3)
- exten => _XX.,1,GotoIf($[foo${calledid} != foo]?3)
- The second example above is the way suggested by the WIKI. It will
- work as long as there are no spaces in the evaluated value.
- The first way should work in all cases, and indeed, might now
- be the safest way to handle this situation.
- ___________________________
- WARNING
- ---------------------------
- If you need to do complicated things with strings, asterisk expressions
- is most likely NOT the best way to go about it. AGI scripts are an
- excellent option to this need, and make available the full power of
- whatever language you desire, be it Perl, C, C++, Cobol, RPG, Java,
- Snobol, PL/I, Scheme, Common Lisp, Shell scripts, Tcl, Forth, Modula,
- Pascal, APL, assembler, etc.
|