CommuniGate Pro
Version 5.2
Applications
 
 
CG/PL

CommuniGate Programming Language (CG/PL)

The CommuniGate Programming Language (CG/PL) is a powerful, yet simple procedural language. It can be used with various components of the CommuniGate Pro Server software, including:

The language structure and the language features are the same for all applications, but different applications use different sets of built-in functions and procedures.

The following is a simple CG/PL program (using the "basic" and "alternative" syntax):
//	
// A simple CG/PL application
//
entry Main is
  myName = "Jim" + " " + "Smith";
  if length(myName) > 10 then
    myName = Substring(myName,0,8) + "..";
  end if;
end;
 
/*
 * A simple CG/PL application
 */
entry Main {
  myName = "Jim" + " " + "Smith";
  if(myName.length() > 10) {
    myName = myName.substring(0,8) + "..";
  }
}


Data Model

Information is presented as objects. An object can be a string, a number, a datablock, a timestamp, an ip-address, an array, a dictionary, or an XML object. See the Data section for more details.

An object can also be a Mailbox handle, a Task handle, or any other special object defined within a particular environment.

A special type of object is a null-value (null value or "no object" value).

When processing logical (boolean) values, a null-value is used as a false-value, and a string "YES" is used as a true-value.


Lexemes

The program source code is a plain text encoded using the UTF-8 character set.

The language lexemes are:

A comment is a double-slash (//) symbol and all following symbols up to and including the next EOL (end-of-line) symbol.

white-space is a sequence of 1 or more space symbols, tabulation symbols, EOL symbols, and/or comments. At least one white space is required between a name and a keyword, other lexemes can be separated with zero or more white spaces.


Variables

Any name not declared as a procedure or function name, and not matching a built-in procedure or function name is a name of a variable.

Each variable has a value assigned to it. Initially, this value is a null-value. Any object can be assigned to any variable to become that variable value.

myCount = 3;           // the myCount variable is created and
                       // a numeric value 3 is assigned to it
myCount = myCount + 2; // myCount variable value changed to 5
myCount = "Service";   // myCount variable value changed to a string

Variables are local to the function/procedure instance (invocation) where they were created. All their values are destroyed when the function/procedure exits (returns).


Expressions

The keywords null and false can be used in expressions to specify a null-value, while the keyword true can be used to specify a true-value.

The language implements unary operations. Unary operations are specified as

operation operand

The following unary operations are supported:

-
unary minus. If the operand value is a number, operation value is the number with the opposite sign, otherwise the operation value is the number 0.
The following expressions have the value of -5:
-5
-(3+2)
+
unary plus. If the operand value is a number, operation value is that number, otherwise the operation value is the number 0.
The following expressions have the value of 5:
+5
+(10/2)
not
Negation. If the operand value is a null-value, the operation value is a true-value, otherwise the operation value is a null-value.
The ! symbol can be used instead of the not keyword.
The following expressions have the value of "YES":
not null
!(2 == 3)

The unary operations have a higher priority than binary and ternary operations.

The following expression has the value of -1, not -3:
-2 + 1

The language implements binary operations. Binary operations are specified as

left-operand operation right-operand
Unless explicitly specified otherwise, both operands are computed first (in a non-specified order), and the operation is applied to the operand values.

The following binary operations are supported, listed in the descending priority order:

*, /, %
These arithmetic operations can be applied to numeric operand values only.
If one of the operands is not a Number, or if the right operand of the / or % operations is number 0, the operation value is a null-value.
The following expressions have the value of 10:
5 * 2
-20 / -2
30 % 20
+, -
These arithmetic operations can be applied to numeric operand values.
The + operation can be applied to a pair of string operand values, producing a string value with their catenation.
The + operation can be applied to a pair of datablock operand values, producing a datablock value with their catenation.
The + operation can be applied to a datablock and a string value operands, producing a datablock copy with the string bytes added to the datablock end.
The + operation can be applied to a datablock and a numeric value operands, where the numeric value should be in the 0..255 range, producing a datablock copy with an additional byte (containing the numeric operand value) added to the datablock end.
The + operation can be applied to a timestamp and a numeric value operands, producing a timestamp value that is the numeric value seconds later than the timestamp operand value.
The - operation can be applied to a left operand with a timestamp value and a right operand with a numeric value, producing a timestamp value that is the numeric value seconds earlier than the timestamp operand value.
The - operation can be applied to a pair or operands with timestamp values, producing a numeric value - the number of seconds between the left and the right operand values.
In other cases the operation value is a null-value.
The following expressions have the value of 5:
3 + 2
-2 - -7
The following expression has the value of "John Doe":
"Joh" + "n Doe"
<, <=, ==, !=, >=, >
These comparison operations can be applied to a pair of numeric operands, to produce a true-value when the arithmetic comparison condition is met.
These comparison operations can be applied to a pair of timestamp operands, to produce a true-value when the arithmetic comparison condition is met.
The ==, != comparison operations can also be applied to any pair of objects, checking if they are "equal":
  • A null-value is equal to and only to a null-value.
  • Numbers are equal if their numeric values are equal.
  • Strings are equal if they have the same length and have the same symbol in each string position.
  • Datablocks are equal if they have the same length and have the same data byte in each block position.
  • Arrays are equal if they have the same number of elements and elements in each position are equal.
  • Dictionaries are equal if they have the same number of key-value pairs, the key strings are equal, and the values for each key are equal in both dictionaries.
  • For all other object types any object is equal to itself only (no two different objects are considered equal).

In other cases the comparison operation value is a null-value.
The following expressions have the value of "YES":
1+2 == 3
2+2 != 3
2+2 >= 3
"Joe" == "Joe"
null == (2 == 3)
and, or, xor, and then, or else
these logical operations compare their operands with null-values.
The and operation value is a true-value if both operand values are not null-values, and a null-value otherwise.
The & symbol can be used instead of the and keyword.
The or operation value is a true-value if at least of the operand values is not a null-value, and a null-value otherwise.
The | symbol can be used instead of the or keyword.
The xor operation value is a null-value if none or both operand values are null-values. Otherwise, the operation value is the operand value that is not a null-value.
The ^ symbol can be used instead of the xor keyword.
The and then operation computes the left operand value first. If that value is a null-value, the right operand is not computed, and the operation value is a null-value. Otherwise the right operand is computed and its value becomes the operation value.
The && symbols can be used instead of the and then keywords.
The or else operation computes the left operand value first. If that value is not a null-value, the right operand is not computed, and the left operand value becomes the operation value. Otherwise the right operand is computed and its value becomes the operation value.
The || symbols can be used instead of the or else keywords.
The following expressions have the value of "YES":
1+2 == 3 & 2+2 == 4
2+2 == 3 or else 7-5 == 2
false ^ true

The binary operations of the same priority group left-to-right: X op Y op Z is the same as ( X op Y ) op Z

The binary operations have a higher priority than the ternary operations.

The language implements one ternary operation:
cond ? expr1 : expr2
  • the cond operand is computed.
  • If the computed value is not a null-value, the expr1 operand is computed and its value becomes the operation value.
  • Otherwise the expr2 operand is computed and its value becomes the operation value.
The following expressions have the value of "Good":
3 == 3 ? "Good" : "Bad"
null ? 77777 : "Good"

The ternary operation groups right-to-left: A ? B : C ? D : E is the same as A ? B : (C ? D : E)

The language implements the indexing operation:

object[index]
where
the object expression should have an array, a dictionary value, a string value, or a datablock (otherwise the operation results in a program exception), and
the index expression should have a numeric value smaller than the number of object elements, or the length of the object string or datablock.

If the object expression value is an array, the operation references the array element number index (the first element has the number 0).
Retrieving an element that does not exist results in a null-value.
Assigning a new value to the first array element that does not exist adds the value to the array as a new element.
An attempt to assign a new value to any other non-existing array element results in a program exception.
If SquareArray value is (1,4,9,16,25), the following expression has the value of 9:
SquareArray[2]
while the following operator:
SquareArray[5] = "Blue";
changes the SquareArray value to (1,4,9,16,25,"Blue"),

If the object expression value is a dictionary, the operation references the dictionary key number index (the first key has the number 0).
Retrieving a key that does not exist results in a null-value.
An attempt to assign a new value to a referenced key results in a program exception.

If SquareDictionary value is {"one" = 1; "two" = "four"; "three"=9;}, the following expression has the value of "three":
SquareDictionary[2]

If the object expression value is a string, the operation returns a 1-byte string containing the string symbol number index (the first string symbol has the number 0).
Retrieving a symbol that does not exist results in a null-value.
An attempt to assign a new value to any string symbol results in a program exception.
If SquareString value is "grass", the following expression has the value of "r":
SquareString[1]

If the object expression value is a datablock, the operation returns a number representing the datablock byte number index (the first datablock byte has the number 0).
Datablock bytes have unsigned numeric values in the 0..255 range.
Retrieving a byte that does not exist results in a null-value.
An attempt to assign a new value to any datablock byte results in a program exception.

The language implements the key, or dictionary-element operation:

dictionary.keyName
where
the dictionary expression should have a dictionary value (otherwise the operation results in a program exception), and
the keyName is a name.

The operation references the dictionary element with the key keyName.
Retrieving an element for a key that does not exist results in a null-value.
Assigning a null-value to a key results in the key-value pair being removed from the dictionary.
Assigning a non-null-value to a key that does not exist results in a new key-value pair being added to the dictionary.
If SquareDictionary value is {"one" = 1; "two" = "four"; "three"=9;},
the following expression has the value of 9:
SquareDictionary.three

and the following expression has the value of null:
SquareDictionary.four
The language implements the computed key, or dictionary-element operation:
dictionary.(keyExpr)
where
the dictionary expression should have a dictionary value, and
the keyExpr expression should have a string value (otherwise the operation results in a program exception).

The operation references the dictionary element for the keyExpr key.
If SquareDictionary value is {"one" = 1; "two" = "four"; "three"=9;}, the following expression has the value of 9:
SquareDictionary.("th" + "ree")

The language implements function calls. A function call is specified as a name followed by parentheses optionally containing a list of expressions (parameter-expressions):

functionName()
functionName(arg1)
functionName(arg1,arg2,...)

The functionName should be a name of a built-in function or an already defined function.
Parameter expressions (if any) are computed, and the function code is executed using the parameter expression values.
A function result is an object, and the indexing and dictionary-element operations can be applied to a function result.

If MyFunction function has 2 parameters and its returned value is an array (1,"four",9), the following expression has the value of "four":

MyFunction(myData,"zzz")[1]

A function with one or more parameters can be called as a method:

arg1.functionName()
arg1.functionName(arg2)
arg1.functionName(arg2,arg3,...)

The MyFunction function call (see above) can be expressed as a method:

myData.MyFunction("zzz")[1]

Operators

An operator sequence contains zero or more operators, followed by the semicolon (';') symbol.

An empty operator performs no action:

;

A null operator consists of the keyword null. It performs no action:

null;

An assignment operator consists of a data container reference (a variable, an array element, or a dictionary element), the assignment operation, and an expression. The expression and the data container reference are computed (in an unspecified order), and the expression value is used to modify the data container.
The = operaton assignes the expression value to the data container.

myVar = 123 + 111;
myVar = "string";
Other assignment operations consist of a binary operation symbol and the = symbol. They apply the corresponing binary operation to the current data container value and the expression value, and store the result in the data container.
myVar[123] += 123; myVar.message += ", program stopped";

If a data container reference is an array element, that element must exist or it must be the first non-existent array element, i.e. if an array has 3 elements, you can assign values to elements number 0,1,2, and 3. In the last case, a new element is added to the array.

If a data container reference is a dictionary element, assigning a null-value effectively removes the element from the dictionary.

A procedure call operator is specified in the same way as a function call expression. The name used should be a name of a built-in procedure or an already defined procedure.

If MyProc procedure has 2 parameters, the following operator is a correct procedure call:
MyProc(myData,"zzz");

For procedure with one or more parameters, a call operator can be specified as a method:

arg1.procedureName()
arg1.procedureName(arg2)
arg1.procedureName(arg2,arg3,...)
The MyProc call (see above) can be specified as a method:
myData.MyProc("zzz");

A stop operator terminates the Task execution. It consists of the stop keyword:

stop;

A return operator finishes function or procedure execution.
A return operator within a function consists of the return keyword and an expression. This expression is computed and its value becomes the value of the function call.

return 12*year+month;

A return operator within a procedure consists of the return keyword.
return;

A conditional operator consists of the if keyword followed by an expression (if-expression), the end keyword, an operator sequence (if-sequence), and the end keyword optionally followed by the if keyword.
The if-expression is computed, and if its value is not a null-value, the if-sequence is executed, and the conditional operation execution ends.

The following example increases the myCount variable value by 2 if its value is less than 10:
if myCount < 10 then
  myCount = myCount + 2;
end if;

A conditional operator can optionally contain one or more elif-portions after the if-sequence. Each elif-portion consists of the elif keyword, an expression (elif-expression), the then keyword, and an operator sequence (elif-sequence).
If the if-expression value is a null-value, the first elif-expression is computed, and if its value is not a null-value, its elif-sequence is executed and the conditional operation execution ends. If the elif-expression value is a null-value, the next elif-portion is processed.
In the following example the myCount variable value is checked. If the value is less than 10, the variable value is increased by 2. Otherwise (i.e. if the variable value is not less than 10), if the value is less than 20, it is decreased by 3:
if myCount < 10 then
  myCount = myCount + 2;
elif myCount < 20 then
  myCount = myCount - 3;
end if;

A conditional operator can optionally contain an else-portion. It is specified after the if-sequence and after all optional elif-portions. The else-portion consists of the else keyword and an operator sequence (else-sequence).
If the if-expression value is a null-value, and all optional elif-expression values are null-values, the else-sequence is executed and the conditional operator execution ends.
The following example increases the myCount variable value by 2 if the value is less than 10, it decreases the variable value by 3 if the value is not less than 10, but it is less than 20, and the variable value is multiplied by 4 in all other cases:
if myCount < 10 then
  myCount = myCount + 2;
elif myCount < 20 then
  myCount = myCount - 3;
else
  myCount = myCount * 4;
end if;

The loop operator consists of the loop keyword, optionally prefixed with the while keyword and an expression (while-expression), an operator sequence (initial sequence), and the end keyword optionally followed by the loop keyword.
If a while-expression is specified, it is computed, and if its value is null the loop operator execution ends. Otherwise the operator sequence is executed, and the loop operator execution repeats.

The following example checks the myCount variable value and keeps increasing it by 2 while that value is less than 10:
while myCount < 10 loop
  myCount = myCount + 2;
end loop;

The following example calls the myProc procedure in an unconditional loop:

loop
  myProc(2,"test.wav");
end loop;

The loop operator can optionally contain one or more exitif-portions between the initial sequence and the end keyword. Each exitif-portion consists of the exitif keyword, followed by an expression (exitif-expression), the semicolon (';') symbol, and an operator sequence. After the initial sequence is executed, the first exitif-expression is computed. If its value is not null, the loop operator execution ends. Otherwise the exitif operator sequence is executed, and the next exitif expression is computed. After the last exitif operator sequence is executed, the loop operator execution repeats.

The following example appends the "aaa" string to the myWord variable, checks the variable lengths, and if the length is less than 20, appends the "bbb" string to the myWord variable, and repeats the process:
loop
  myWord = myWord + "aaa";
exitif length(myWord) >= 20;
  myWord = myWord + "bbb";
end loop;

Alternative Forms

Some operators in a sequence may be presented in an alternative form. Operators in an alternative form are not followed by the semicolon symbol.

The alternative form of a conditional operator consists of the if keyword followed by an expression (if-expression), and an operator sequence (if-sequence) enclosed in left ({) and right (}) brace symbols.
The alternative form of a conditional operator can optionally contain one or more elif-portions after the enclosed if-sequence. Each elif-portion consists of the elif keyword, an expression (elif-expression), and an operator sequence (elif-sequence), enclosed into braces.
The alternative form of a conditional operator can optionally contain an else-portion. It is specified after the enclosed if-sequence and after all optional elif-portions. The else-portion consists of the else keyword and an operator sequence (else-sequence) enclosed in braces.

The following example increases the myCount variable value by 2 if the value is less than 10, it decreases the variable value by 3 if the value is not less than 10, but it is less than 20, and the variable value is multiplied by 4 in all other cases:
if (myCount < 10) {
  myCount = myCount + 2;
} elif (myCount < 20) {
  myCount = myCount - 3;
} else {
  myCount = myCount * 4;
}
Note: it is not required to use parentheses to enclose if-expressions or elif-expressions.

The alternative form of a loop operator consists of the while keyword, an expression (while-expression), a left brace ('{') symbol, an operator sequence (initial sequence), zero or more exitif-portions and a right brace ('}') symbol.
Each optional exitif-portion consists of the exitif keyword, followed by an expression (exitif-expression), the semicolon (';') symbol, and an operator sequence.

The following example appends the "aaa" string to the myWord variable, checks the variable lengths, and if the length is less than 20, appends the "bbb" string to the myWord variable, and repeats the process:
while ( true ) {
  myWord = myWord + "aaa";
exitif (length(myWord) >= 20);
  myWord = myWord + "bbb";
}
Note: it is not required to use parentheses to enclose while-expressions or exitif-expressions.


Code Sections

A program code is a set of code sections:

The procedures and functions can be called recursively: a procedure or a function can call itself - directly or via calling some other procedures or functions.

All code sections are reenterable: the same code section can be used by several program activations or Tasks at the same time.

Code sections must be declared before they can be used. Declarations include forward-declarations, external-declarations, and definitions.

A program code should contain exactly one external-declaration or exactly one definition (but not both) of each code section used.
A program code may contain not more than one forward-declaration of a code section, specified before its definition.
Forward-definitions are used in programs containing two or more code sections calling each other, so it is not possible to define each section before it is used in the other code section.

External-declarations allow code sections to call code sections defined in separate program code modules.
External-declarations are allowed only in the environments that support them, such as the
Real-Time Application environments. See the environment description for more details.
The code section name and its parameter names specified in an external-declaration must match the code section name and its parameter names specified in the code section definition given in an external program code module.
The code section definition can specify more parameters than an external-declaration. The missing parameters are assigned null-values when such an external-declaration is used.

Entries

An entry declaration consists of the entry keyword, the entry name, followed by one of the following:
for a forward-declaration:
the forward keyword followed by the semicolon (;) symbol
for an entry definition:
the is keyword followed by an operator sequence, followed by the end keyword (optionally followed by the entry keyword), and followed by the semicolon (;) symbol
for an alternative entry definition:
the left brace ({) symbol followed by an operator sequence, followed by the right brace (}) symbol

If a running program reaches the end of an entry section operator sequence, an implicit stop operator is executed.

The following example shows an entry for a
Real-Time Application. It tries to accept an incoming call, and if succeeds, it plays a sound. The entry code ends, quitting the program and thus finishing the call:
entry main is
  if acceptCall() == null then
    playFile("greeting.wav");
  end if;
end entry;

Or, in the alternative form, and using the alternative form of the conditional operator:

entry main {
  if (acceptCall() == null) {
    playFile("greeting.wav");
  }
}

Procedures

A procedure declaration consists of the procedure keyword, the procedure name, the left parenthesis, an optional list of parameter names, the right parenthesis, followed by one of the following:
for a forward-declaration:
the forward keyword followed by the semicolon (;) symbol
for a procedure definition:
the is keyword followed by an operator sequence, followed by the end keyword (optionally followed by the procedure keyword), and followed by the semicolon (;) symbol
for an alternative entry definition:
the left brace ({) symbol followed by an operator sequence, followed by the right brace (}) symbol
for an external-declaration:
the external keyword followed by the semicolon (;) symbol

If a running program reaches the end of a procedure operator sequence, an implicit return operator is executed.

The following example shows a
Real-Time Application procedure that speaks the specified number:
procedure sayNumber(x) is
  x = x % 100;
  if x >= 10 then
    PlayFile(String(x/10*10)+".wav");
  end if;
  if x != 0 then
    PlayFile(String(x%10)+".wav");
  end if;
end procedure;

If a forward-declaration is used, the procedure definition must have exactly the same parameters as its forward-declaration.

Example:
procedure sayMoney(x,units) forward;
procedure sayNumber(x) forward;
procedure sayMoney(x,units) is
  sayNumber(x);
  PlayFile(units+".wav");
end procedure;

Functions

A function declaration is the same as a procedure declaration, but the function keyword is used instead of the procedure keyword.

All program control paths in a function code section must end with a return or a stop operator.

The following example defines a function calculating the factorial of its argument:
function Factorial(x) is
  if x <= 1 then return 1; end if;
  return Factorial(x-1)*x;
end function;

Below is the same function definition in the alternative form, using the ternary operator:

function Factorial(x) {
  return x <= 1 ? 1 : Factorial(x-1)*x;
}

All code section (entry, procedure, and function) names used within the same program code must be unique.


Built-in Procedures and Functions

The following procedures and functions are built into the language, and they are available to all applications. You should not use their names for user-defined procedures or functions.

Same(arg1,arg2)
This function returns a true-value if the values of arg1 and arg2 are the same object or if both values are null-values or both values are true-values. In other cases the function returns a null-value.
The value of Same("J" + "ack","Jack") is a null-value.
In the following example:
x = "my string";
y = "my string";
z = x;
test1 = Same(x,y);
test2 = Same(x,x);
test3 = Same(x,z);
the resulting value of test1 is a null-value, while the values of test2 and test3 are true-values.
Copy(arg)
If the arg value is a null-value, this function returns a null-value.
Otherwise, the function returns the copy of the arg value.
For complex objects (such as arrays, dictionaries, XML objects), this function copies all complex object elements, too.
Length(arg)
If arg is a string, this function returns the string size (in bytes);
If arg is a datablock, this function returns the datablock size (in bytes);
If arg is an array, this function returns the number of array elements;
If arg is a dictionary, this function returns the number of dictionary keys;
If arg is a mailbox handle, this function returns the number of messages in the mailbox;
In all other cases, this function returns the number 0.
Min(arg1,arg2)
If the arg1 value < the arg2 value, then the function returns the arg1 value, otherwise it returns the arg2 value.
See above for the < operation definition.
Max(arg1,arg2)
If the arg1 value > the arg2 value, then the function returns the arg1 value, otherwise it returns the arg2 value.
See above for the > operation definition.
Void(arg1)
This procedure does nothing, it just discards the arg1 value. Use this procedure when you need to call a function, but you do not want to use the function result.

Strings

IsString(arg)
This function returns a true-value if the arg value is a string, otherwise the function returns a null-value.
String(arg)
If the arg value is a string, this function returns this string.
If the arg value is a number, this function returns a string with the decimal representation of that number.
If the arg value is a datablock, this function returns a string with the datablock content (interpreted as textual data).
If the arg value is a timestamp, this function returns a string with the system-standard timestamp text representatoin.
If the arg value is an ip-address, this function returns a string with the canonical representation of that network address.
If the arg value is an XML Object, this function returns the XML object text body ("text node").
If the arg value is a null-value, this function returns a null-value.
In all other cases, this function returns a string with a textual representation of the arg value.
FindSubstring(str,substr)
If the str value is a string, and the substr value is a string, and the latter is a substring of the str value, this function returns the position of the substring substr in the str string (positions start with 0).
For example, the value of FindSubstring("forest","for") is 0.
In all other cases this function returns the number -1.
Substring(str,from,len)
If the str value is a string, and the from value is a number, and the len value is a non-negative number, this function returns a string that is a substring of the str value, with the len length.
If from has a non-negative value, the substring starts at the from position (the first symbol of the string has the position 0).
If from is a negative value, then the substring ends at the -1-from position from the string end (to include the last str symbol(s), from should be -1).
If the from value (or -1-from value) is equal to or greater than the str value length, the result is an empty string.
If the from + len (or -1-from + len) value is greater than the str value length, the resulting string is shorter than len.
In all other cases this function returns a null-value.
Note: this function interprets a string as a sequence of bytes, and thus it can break non-ASCII symbols which are stored as a multi-byte sequence.
Range(str,from,len)
This function works in the same way as the Substring function, but if the str value is a string, it is interpreted as a sequence of "glyphs" - single and multi-byte sequences representing ASCII and non-ASCII symbols. The from and len values specify the substring position and length in terms of symbols, rather than bytes.
If the str value is a datablock, the function returns a datablock containing a portion of the str value, cut using the same rules, while The from and len values specify the position position and length in bytes.
EOL()
This function returns a string containing the EOL (end-of-line) symbol(s) used on the Server OS platform.
CRLF()
This function returns a string with the Internet EOL (<carriage-return><line-feed>) symbols.
ToUpperCase(str)
If the str value is a string, the function result is this string with all its letters converted to the upper case.
ToLowerCase(str)
If the str value is a string, the function result is this string with all its letters converted to the lower case.
IsDigit(str)
This function returns a true-value if the str value is a 1-symbol string and that symbol is a decimal digit (0..9), otherwise the function returns a null-value.
FindRegEx(str,picture)
The function compares the str string with the picture string containing a regular expression.
If str is not a string, or picture is not a string, or the picture string cannot be interpreted as a regular expression, or the str string does not match the regular expression, the function returns a null-value.
Otherwise, the function returns an array of strings. Its zero element contains a copy of the str string, while additional elements (if any) contain the str substrings matching the regular expression groups.
The picture string should specify a regular expression using the extended POSIX syntax.
EmailDomainPart(address)
If the address value is a string, and the string contains the @ symbol, this function returns a string containing the address string part after its first the @ symbol.
Otherwise, the function returns a null-value.
EmailUserPart(address)
If the address value is not string, this function returns a null-value.
If the address value is a string not containing the @ symbol, this function returns the same string.
Otherwise (the address value is a string containing the @ symbol), this function returns the address string part before the first @ symbol.

Numbers

IsNumber(arg)
This function returns a true-value if the arg value is a number, otherwise the function returns a null-value.
Number(arg)
If the arg value is a number, this function returns this number.
If the arg value is a string, this function returns the numeric value of that string, till the first non-numeric symbol.
For example, the value of Number("123#") is 123.
In all other cases, this function returns the number 0.
RandomNumber()
This function returns a random integer number in the [0..9223372036854775807] ([0..2*63-1]) range.

TimeStamps

IsDate(arg)
This function returns a true-value if the arg value is a timestamp, otherwise the function returns a null-value.
Date(arg)
If the arg value is a timestamp, this function returns this timestamp.
If the arg value is the number 0, this function returns the "remote past" timestamp.
If the arg value is a negative number, this function returns the "remote future" timestamp.
If the arg value is a positive number N, this function returns the timestamp corresponding to the start of the Nth day, where the 1st day is 2nd of January, 1970.
If the arg value is a string, if should be a textual representation of some timestamp, and this function returns that timestamp.
In all other cases, this function returns a null-value.
GMTTime()
This function returns a timestamp object with the current GMT time.
LocalTime()
This function returns a timestamp object with the current local time.
GMTToLocal(arg)
If the arg value is a timestamp object, this function returns a timestamp object containing the arg value converted from the GMT to the local time.
In all other cases, this function returns a null-value.
LocalToGMT(arg)
If the arg value is a timestamp object, this function returns a timestamp object containing the arg value converted from the local time to the GMT.
In all other cases, this function returns a null-value.
Year(arg)
If the arg value is a timestamp object, this function returns a number containing the arg value year.
If the the timestamp value is the "remote past" timestamp, the function returns the number 0.
If the the timestamp value is the "remote future" timestamp, the function returns the number 9999.
In all other cases, this function returns a null-value.
Month(arg)
If the arg value is a timestamp object, this function returns a string containing the arg value month name (Jan, Feb, Mar, Apr, May, Jun, Jul, Aug, Sep, Oct, Nov, Dec).
If the arg value is a number in the 1..12 range, this function returns a string containing the name of month number arg (Month(1) returns Jan).
In all other cases, this function returns a null-value.
MonthNum(arg)
If the arg value is a timestamp object, this function returns the arg value month number (1 for January).
In all other cases, this function returns a null-value.
MonthDay(arg)
If the arg value is a timestamp object, this function returns a number containing the day of month for the arg value date (1 is returned for the first day of month).
In all other cases, this function returns a null-value.
WeekDay(arg)
If the arg value is a timestamp object, this function returns a string containing the name of week day of the arg value date (Mon, Tue, Wed, Thu, Fri, Sat, Sun).
In all other cases, this function returns a null-value.
YearDay(arg)
If the arg value is a timestamp object, this function returns a number containing the day of year for the arg value date (the number 1 is returned for the 1st of January).
In all other cases, this function returns a null-value.
TimeOfDay(arg)
If the arg value is a timestamp object, this function returns the number of seconds between the date arg value and the start of its day.
In all other cases, this function returns a null-value.
DateNumber(arg)
If the arg value is a timestamp object, this function returns the number of full days between the arg value date and 01-Jan-1970.
In all other cases, this function returns a null-value.
DateByMonthDay(year,monthNum,monthDay)
The year, monthNum, monthDay values should be positive numbers. If any of these values is incorrect, this function returns a null-value. Otherwise, the function returns a timestamp object presenting midnight of the specified date.
The following expression timestamp value is midnight, 05-Nov-2008:
DateByMonthDay(2008,11,5)
DateByYearDay(year,yearDay)
The year, yearDay values should be positive numbers. If any of these values is incorrect, this function returns a null-value. Otherwise, the function returns a timestamp object presenting midnight of the specified date.
The following expression timestamp value is midnight, 01-Feb-2006:
DateByYearDay(2006,32)

IP Addresses

IsIPAddress(arg)
This function returns a true-value if the arg value is an ip-address, otherwise the function returns a null-value.
IPAddress(arg)
If the arg value is an ip-address, this function returns this ip-address.
If the arg value is a string with a correct presentation of an IP address (with an optional port number), the function returns that ip-address.
In all other cases, this function returns a null-value.

Datablocks

IsData(arg)
This function returns a true-value if the arg value is a datablock, otherwise the function returns a null-value.
RandomData(length)
The length value should be a positive numbers not larger than 4096.
This function returns a datablock of the specified length, filled with random data.

Arrays

IsArray(arg)
This function returns a true-value if the arg value is an array, otherwise the function returns a null-value.
NewArray()
This function returns a newly created empty array.
Invert(arg)
The arg value should be an array, otherwise this function call results in a program exception.
This function returns an array containing the same elements as the arg value, but in the reversed order.
Find(source,object)
If the source value is an array, this function returns a number - the index in the array for the first element equal to the object value. If the source array does not contain such an object, a negative numeric value is returned.
If the source value is not an array, a negative numeric value is returned.
AddElement(target,element)
If the target value is an array, this procedure adds element value as the new last element of that array.
If the target value is an XML Object, this procedure adds element value as its new sub-element (the element value should be a string or an XML Object).
In all other cases this procedure call results in a program exception.
If the myArray value is (1,4,9,16,25), the AddElement(myArray,"test") call changes the myArray value to (1,4,9,16,25,"test").
RemoveElement(target,index)
This procedure removes an element from an array.
The target value should be an array, otherwise this procedure call results in a program exception.
The index value should be a number or a string containing a decimal number, specifying the array element to remove. In other cases the first (the zero index) element is removed.
If the myArray value is (1,4,9,16,25), the RemoveElement(myArray,2) call changes the myArray value to (1,4,16,25).
InsertElement(target,index,element)
This procedure inserts an element into an array.
The target value should be an array, otherwise this procedure call results in a program exception.
The index value should be a number or a string containing a decimal number, specifying where to insert the element value. All existing array elements with index number of index and bigger increase their index number by one.
If the myArray value is (1,4,9,16,25), the InsertElement(myArray,2,"Jack") call changes the myArray value to (1,4,"Jack",9,16,25).
SortStrings(arg)
This procedure sorts array elements.
The arg value should be an array, and all array elements must be strings, otherwise this procedure call results in a program exception.
The array elements are compared as case-insensitive UTF-8 strings.

Dictionaries

IsDictionary(arg)
This function returns a true-value if the arg value is a dictionary, otherwise the function returns a null-value.
NewDictionary()
This function returns a newly created empty dictionary.
SetCaseSensitive(target,flag)
This procedure specifies if dictionary keys should be processes as case-sensitive.
The target value should be a dictionary, otherwise this procedure call results in a program exception.
If flag value is a null-value, the target dictionary becomes case-insensitive, otherwise it becomes case-sensitive.
New dictionaries are created as case-sensitive.

XML Objects

IsXML(arg)
This function returns a true-value if the arg value is an XML object, otherwise the function returns a null-value.
NewXML(type,prefix)
This function returns a newly created XML Object of type type. The type value should be a string containing a valid XML tag.
The prefix value can be a null-value or a string containing a valid XML prefix. This prefix is used to qualify the XML object name.
SetNamespace(data,namespace,prefix)
This procedure associates an XML prefix with some namespace.
The data value should be an XML Object, otherwise this procedure call results in a program exception.
The prefix value should be a string containing a valid XML prefix.
If the namespace value is a null-value, the namespaces associated with the prefix value is removed. Otherwise the namespace value should be a string, containing the namespace to be associated with the prefix value.
GetNamespace(data,prefix)
This function returns a string with the namespace associated with the specified XML prefix, or a null-value if there is no associated namespace.
The data value should be an XML Object, otherwise this function call results in a program exception.
The prefix value should be a string containing a valid XML prefix.
SetAttribute(data,attribute,name,prefix)
This procedure sets an XML Object attribute for the specified name and prefix.
The data value should be an XML Object, otherwise this procedure call results in a program exception.
The name value should be a string containing a valid XML attribute name.
The prefix value should be a null-value or a string containing a valid XML prefix.
If the attribute value is a null-value, the attribute with the specified name and prefix is removed. Otherwise the attribute value should be a string containing the new attribute value.
GetAttribute(data,name,prefix)
This function returns a string value of the attribute with the specified name and prefix, or a null-value if there is no such attribute.
The data value should be an XML Object, otherwise this function call results in a program exception.
The name value should be a string containing a valid XML attribute name.
The prefix value should be a null-value or a string containing a valid XML prefix.
XMLBody(data,type,namespace,index)
This function returns an XML sub-element with the specified type, namespace, and position, or a null-value if there is no such sub-element.
The data value should be an XML Object, otherwise this function call results in a program exception.
The type value should be a null-value or a string containing a valid XML attribute name. If the type value is a null-value, the function retrieves sub-elements of any type.
The namespace value should be a null-value or a string containing a namespace. If the namespace value is a null-value, the function looks for sub-elements ignoring their namespaces.
The index value should be a non-negative number. To retrieve the first sub-element with the specified type and namespace, the index value should be 0.
XMLType(data)
This function returns a string with the XML Object type.
The data value should be an XML Object, otherwise this function call results in a program exception.
XMLPrefix(data)
This function returns a string with the XML Object type prefix.
The data value should be an XML Object, otherwise this function call results in a program exception.

Data Conversion

ObjectToString(arg)
This function returns a string with a textual representation of the arg value.
If the arg value is a null-value, the function returns the #null# string.
ObjectToXML(arg)
This function returns an XML representation of the arg value, as specified in XML Objects section.
ToObject(arg)
If the arg value is a string or a datablock, this function returns an object textually represented with the arg value.
If the arg value is an XML object, this function returns an object this XML represents (as specified in XML Objects section).
Otherwise this function call results in a program exception.
If conversion fails or if the arg value is the #null# string, the function returns a null-value.
Base64Encode(arg)
The arg value should be a string or a datablock, otherwise this function call results in a program exception.
This function returns a string containing the base64-encoded arg data.
Base64Decode(arg)
The arg value should be a string, otherwise this function call results in a program exception.
This function returns a datablock containing the base64-decoded arg data.
AppToXML(data,format)
This function converts application data into its XML representation.
The data value should be a string or a datablock containing the application data text.
The format value should be a string specifying the application data format. The following formats are supported:
  • vCard - vCard format, the function returns either a vCard XML object, or an array of vCard XML objects.
  • vCardGroup - vCardGroup format, the function returns a vCardGroup XML object.
  • iCalendar - iCalendar format, the function returns an iCalendar XML object.
  • sdp - SDP format, the function returns an SDP XML object.

If the function fails to parse the application data, or the specified format is not supported, the function returns an error code string.
XMLToApp(data)
This function converts an XML representation into application data (see above).
The data value should be an XML object.
The function returns the application data string.
If the XML object is not a representation of some supported application data format, the resulting string is a generic textual representation of the data value XML object.
If the function fails to convert the XML representation into application data, the resulting string contains the error code.
ObjectToJSON(arg)
This function returns a string with a JSON (JavaScript Object Notation) representation of the arg value.
If the arg value is a null-value, the function returns the null string.
JSONToObject(arg)
If the arg value is a string or a datablock, this function returns an object textually represented with the arg value, using the JSON format.
Otherwise this function call results in a program exception.
If conversion fails or if the arg value is the null string, the function returns a null-value.

Environment

Vars()
This function returns a dictionary unique for this Task (a program invocation). This dictionary can be used to store variables visible in all procedures and functions executed in this Task.
When a Task is started with parameters (for example, when a
Real-Time Application is started to process a Signal directed with the Router), the parameter array is placed into the startParameter element of the Vars() dictionary.
The following example retrieves the first two Task parameters:
  firstParam  = Vars().startParameter[0];
  secondParam = Vars().startParameter[1];

Addresses and URIs

SIPURIToEmail(uri)
This function converts the uri value from a SIP URI into an E-mail string.
If the uri value is not a string, or if it cannot be parsed as a SIP URI, the function returns a null-value.
EmailToSIPURI(email)
This function converts the email value from an E-mail address into a SIP URI string.
If the email value is not a string, or if it cannot be parsed as an E-mail, the function returns a null-value.
PhoneNumberToSIPURI(phoneNumber)
This function converts the phoneNumber value into a SIP URI string.
If the email value is not a string, or if it cannot be parsed as a telephone number, the function returns a null-value.
The function removes all formatting symbols from the phoneNumber value, leaving only the digits and the leading plus (+) symbol (if it exists).
The function adds the current Domain name to the converted number.
RouteAddress(email,type)
This function uses the Router to process the email address.
The type value specifies the address type: it should be the mail, signal, or access string.
If address routing fails, the function returns an error code string. Otherwise, the function result is a dictionary with the following elements:
module
the name of the CommuniGate Pro module that will process this address.
host
a string with the name of the host (a local Account, a remote domain, etc.) the address is routed to.
object
a string with the name of the host object the address is routed to.
canRelay
this optional element exists and contains a true-value if information can be relayed to this address.
RouteENUM(service,phoneNumber,domain)
This function uses the Domain Name Resolver to convert the phoneNumber telephone number (any sequence of digits with an optional leading + symbol) into a URL.
The service value should be a string. It specifies the ENUM "service" (such as E2U+SIP or E2U+MAIL).
The domain value should be a string. It specifies the ENUM domain name (such as e164.arpa).
If the telephone number has been converted successfully, this function returns an array. Its first element contains a string - the resulting URL.
Otherwise, this function returns an error code string.

Account Data

The following functions and procedures are available when the program (a Task) has a "current Account" set.
MyDomain()
This function returns a string with the current Domain name, if there is one. If there is no Account or Domain associated with the current Task, this function returns a null-value.
MyEmail()
This function returns a string with the current Account E-mail, if there is one. If there is no Account associated with the current Task, this function returns a null-value.
GetAccountPreferences(keyName)
This function returns Preference data for the current Account.
If the keyName is a non-empty string, the Account Preference object for that key is returned. Otherwise a dictionary with all effective Account Preferences is returned.
If the keyName string starts with a ~username/ prefix, the prefix is removed. The username string specifies the name of the Account to use. If this Account is not the same as the current Account, the operation succeeds only if the current Account has a Domain Administrator right for the specified Account Domain.
SetAccountPreferences(keyValue,keyName)
This function updates Preference data for the current Account.
If the keyName is a non-empty string, the keyValue value specifies the new object for that key. If the keyValue is a null-value, the object is removed from the Account Preference data, enabling the default value for the specified key.
If the keyName string starts with a ~username/ prefix, the prefix is removed. The username string specifies the name of the Account to update. If this Account is not the same as the current Account, the operation succeeds only if the current Account has a Domain Administrator right for the specified Account Domain.
If the keyName is a ~username/ string, or an empty string, or if it is not a string, the keyValue value must be a dictionary. It is used to update the Account Preference Data.
This function returns a null-value if Preference data is successfully updated, otherwise it returns a string with an error code.
Impersonate(email)
This function Routes the email address and sets the result as the current Account.
If the routed address is not local, the current Account is cleared.
If the routed address is local and it is not the same as the current Account, the current Account must have the
CanImpersonate access right for the routed address Domain.
When the current Account is changed, the preferences, the selected language, and the selected time zone are changed, too.
This function returns a null-value if the operation has succeeded, otherwise it returns a string with an error code.
ReadGroupMembers(groupName)
This function reads a Group.
The groupName value should be a string. It specifies the name of the Group to read. If this name does not contain a Domain name, the current Domain is used.
This function returns an array of strings containing Group member E-mail addresses. This function returns a null-value if there is no Group with the specified name.
The current Account should have the Domain Administrator right for the Group Domain.
ReadTelnums(accountName)
This function reads Phone Numbers assigned to the accountName Account or to the current Account, if the accountName value is a null-value.
This function returns an array of strings. This function returns a null-value if there is no Account with the specified name.
To retrieve the Phone Numbers assigned to a different Account, the current Account should have the Domain Administrator right for the accountName Account Domain.
UpdateAccountMailRule(ruleData,accountName)
UpdateAccountSignalRule(ruleData,accountName)
These functions modify Account Queue or Signal Rules.
The ruleData parameter is a string or an array. It has the same meaning as the newRule parameter of the UpdateAccountMailRule and UpdateAccountSignalRule CLI commands.
These functions update the Rules of the the accountName Account, or the current Account if the accountName value is a null-value.
To update Queue Rules of a different Account, the current Account should have the RulesAllowed Domain Administrator right for the accountName Account Domain.
To update Signal Rules of a different Account, the current Account should have the SignalRulesAllowed Domain Administrator right for the accountName Account Domain.
This function returns a null-value if the operation has succeeded, otherwise it returns a string with an error code.

Mailboxes

ListMailboxes(filter)
This function lists all Mailboxes in the current Account.
The filter value should be a string - it specifies the search pattern. If the value is a null-value, the search pattern * (all Account Mailboxes) is used.
To search Mailboxes in a different Account, the search pattern should be specified as ~accountName/pattern
If the operation is successful, this function returns a dictionary. Each dictionary key is a string with the found Mailbox name.
The dictionary element value is:
  • a dictionary with the Mailbox attributes - if the found Mailbox is an "item container" only.
  • an empty array - if the found Mailbox is a "mailbox folder" only.
  • an array with one dictionary element- if the found Mailbox is both a "mailbox folder" and an "item container".

If the Mailbox Access rights allow the current Account to see that Mailbox, but do not allow the current Account to open it, the Mailbox Attribute dictionary is replaced with a string containing the Mailbox Access Rights for the current Account.
If this function fails, it returns a string with an error code.
CreateMailbox(mailboxName,class)
This function creates the mailboxName Mailbox in the current Account.
If the class is not a null-value, it specified the Mailbox Class for the newly created Mailbox.
This function returns a null-value if the Mailbox is successfully created, otherwise it returns a string with an error code.
RenameMailbox(oldMailboxName,newMailboxName,renameSub)
This function renames the oldMailboxName Mailbox in the current Account into newMailboxName. Both parameters must have string values.
If the renameSub value is not a null-value, all oldMailboxName sub-Mailboxes are renamed, too.
This function returns a null-value if the Mailbox is successfully renamed, otherwise it returns a string with an error code.
DeleteMailbox(mailboxName,deleteSub)
This function deletes the mailboxName Mailbox from the current Account.
If the deleteSub value is not a null-value, all mailboxName sub-Mailboxes are deleted, too.
This function returns a null-value if the Mailbox is successfully deleted, otherwise it returns a string with an error code.
GetMailboxACLs(mailboxName)
This function reads the Access Control List for the mailboxName Mailbox.
If the function successfully retrieves the ACL data, it returns a dictionary containing ACL identifiers as keys, and access rights as value strings.
Otherwise the function returns a string with an error code.
SetMailboxACLs(mailboxName,newACLs)
This function updates the Access Control List for the mailboxName Mailbox.
The newACL value should be a dictionary, containing ACL identifiers as keys, and access rights as value strings.
To remove an identifier from the ACL, specify an empty array as its value.
This function returns a null-value if the Mailbox ACL is successfully modified, otherwise it returns a string with an error code.
Note: To access Mailboxes in other Accounts, specify a Mailbox name as
~account[@domainName]/mailboxName
GetMailboxAliases(accountName)
This function reads Mailbox Aliases created in the accountName Account or to the current Account, if the accountName value is a null-value.
If the function successfully retrieves the Mailbox Aliases data, it returns a dictionary. Each dictionary key is the Mailbox Alias name, and its value is a string with the Mailbox name this Mailbox Alias points to.
Otherwise the function returns a string with an error code.
SetMailboxAliases(newAliases,accountName)
This function sets the Mailbox Aliases for the accountName Account or for the current Account, if the accountName value is a null-value. The old Mailbox Aliases are removed.
The newAliases value should be a dictionary. Each dictionary key is the Mailbox Alias name, and its value is a string with the Mailbox name this Mailbox Alias points to.
This function returns a null-value if the Mailbox Aliases are successfully modified, otherwise it returns a string with an error code.
GetMailboxSubscription(accountName)
This function reads Mailbox Subscription created in the accountName Account or to the current Account, if the accountName value is a null-value.
If the function successfully retrieves the Mailbox Subscription data, it returns an array. Each array element is a string containing a Mailbox name.
Otherwise the function returns a string with an error code.
SetMailboxSubscription(newSubscription,accountName)
This function sets the Mailbox Subscription for the accountName Account or to the current Account, if the accountName value is a null-value. The old Mailbox Subscription elements are removed.
The newSubscription value should be an array. Each array element is a string containing a Mailbox name.
This function returns a null-value if the Mailbox Subscription is successfully modified, otherwise it returns a string with an error code.

Mailbox Handles

Mailbox handles are internal objects representing a Mailbox.

OpenMailbox(mailboxName)
This function opens a Mailbox. The mailboxName value should be a string. It specifies the Mailbox name.
If the name does not start with the ~ symbol, the mailbox is opened in the current Account, if any.
The current Account (if any) must have the Read/Select access right for the specified mailbox.
The function returns a Mailbox handle if the Mailbox has been opened successfully, otherwise it returns a null-value.
OpenMailboxView(params)
This function opens a Mailbox and creates a Mailbox handle.
The params value should be a dictionary containing a mailbox and sortField string elements, and optional mailboxClass, sortOrder, filter, filterField string elements, and UIDValidity, UIDMin numeric elements.
See the XIMSS section for more details on these parameter values.
The function returns a Mailbox handle if the Mailbox has been opened successfully, otherwise it returns an error code string.
MailboxUIDs(boxRef,flags)
This function returns an array of numbers - mailbox message UIDs.
The boxRef value should be a Mailbox handle.
If the flags value is a string, it should contain a comma-separated list of message flag Names and/or Negative Names. Only UIDs of messages that have flags specified with the flag Names and do not have flags specified with the Negative Names are included into the resulting array.
The following example retrieves UIDs of all messages that have the Seen flag and do not have the Deleted flag:
myMailbox = OpenMailbox("INBOX");
seen = MailboxUIDs(myMailbox,"Seen,Undeleted");
SubscribeEvents(object,refData)
This function enables or disables object object event generation.
If the refData value is a null-value, the object stops to generate events.
Otherwise, the refData value should be a "basic" object. When the object generates events and send them to this Task, the event parameter element contains the refData value.
If the object value is a Mailbox handle, it should be created with the OpenMailboxView function. A Mailbox notification Event is sent to this Task when the Mailbox messages are removed, added, or modified. The "mailbox view" is not actually modified (i.e. the MailboxUIDs function returns the same set of message UIDs) until the Sync operation is applied to that Mailbox handle.
IsMailboxNotifyEvent(data)
This function returns a true-value if the data value is a Mailbox notification Event, otherwise it returns a null-value.
Sync(boxRef)
This function checks for Mailbox modifications.
The boxRef value should be a Mailbox Handle.
This function takes the first pending Mailbox modification and "commits" it by modifying the message UIDs (adding added messages, removing removed messages). It returns a dictionary with the following elements:
mode
a removed, added, or updated string specifying this Mailbox modification type.
UID
a number - the UID of the removed, added, or modified message
index
for an updated message - its position in the message UIDs array.
for a removed message - its position in the message UIDs array before it was removed from that array.
for an added message - its position in the message UIDs array after it was added to that array.

If there is no pending modification in the Mailbox, this function returns a null-value.
MailboxInternalTimeByUID(boxRef,uid)
This function returns a timestamp object containing the message Internal Date.
The boxRef value should be a Mailbox handle, the uid value should be a number - the message UID.
If a message with the specified UID does not exist in the mailbox, the function returns a null-value.
MailboxFlagsByUID(boxRef,uid)
This function returns a string containing a comma-separated list of mailbox message flags Names.
The boxRef value should be a Mailbox handle, the uid value should be a number - the message UID.
If a message with the specified UID does not exist in the mailbox, the function returns a null-value.
MailboxSetFlagsByUID(boxRef,uid,flags)
This function modifies mailbox message flags.
The boxRef value should be a Mailbox handle, the uid value should be a number - the message UID, the flags value should be a comma-separated list of message flag Names and/or Negative Names.
The function sets the flags specified by their Names and resets the flags specified with their Negative Names.
The function returns a null-value if the current Account (if any) has sufficient Mailbox Access Rights to modify the flags, and flags have been successfully modified, otherwise the function returns an error code string.
MailboxExpunge(boxRef)
This function removes all mailbox messages marked as "purgable" or "deleted".
The boxRef value should be a Mailbox handle.
This function returns a null-value if the operation has succeeded, otherwise it returns a string with an error code.
MailboxAudioByUID(boxRef,uid)
This function returns a datablock containing an audio section of the message.
The boxRef value should be a Mailbox handle, the uid value should be a number - the message UID.
If a message with the specified UID does not exist in the mailbox, or the message does not contain an audio part, the function returns a null-value.
MailboxRedirectByUID(boxRef,uid,addresses)
MailboxForwardByUID(boxRef,uid,addresses)
These function redirect or forward the specified message to the specified E-mail addresses.
The boxRef value should be a Mailbox handle, the uid value should be a number - the message UID, the addresses should be a string containing one E-mail address or several E-mail addresses separated with the comma (,) symbols.
These functions return a null-value if the operation has succeeded, otherwise they return a string with an error code.
MailboxAppend(boxRef,headers,content)
These function composes an E-mail message and appends it to the mailbox.
The boxRef value should be a Mailbox handle.
The headers and content values are processed in the same way they are processed with the SubmitEMail function.
The headers dictionary may contain the following additional elements:
flags
a string that specifies the message flags the newly created message will have in the Mailbox. Several flags can be specified, separated with the comma symbol. See the Mailbox section for more details.
internalDate
a timestamp value with the "internal timestamp" for the newly created message. If absent, the current time is used.
replacesUID
an UID value for the previous version of this message. If the new message has been successfully composed and appended to the Mailbox, the message with the replacesUID UID is removed from the Mailbox.
checkOld
if this element and the replacesUID element are specified, the operation fails if the Mailbox does not contain a message with replacesUID UID. This check and the append/delete operations are executed atomically.
report
if this element is specified, it should have the uid value.

If the content value is a vCard or vCardGroup XML object, a Contacts item is composed (regular headers elements are ignored), and this item is added to the Mailbox.
If the operation has failed, this function returns a string with an error code.
If the operation has succeeded, this function returns a null-value, or, if the report element was specified in the headers dictionary, the function returns a number - the UID value for the newly created Mailbox message.
MailboxCopyByUID(boxRef,uid,parameters)
These function copies or moves an E-mail message from one Mailbox to some other Mailbox.
The boxRef value should be a Mailbox handle, the uid value should be a number - the UID of the Mailbox message to be copied.
If the parameters value is a string, it specifies the target Mailbox name.
Otherwise, the parameters value should be a dictionary with the following elements:
targetMailbox
the target Mailbox name string.
doMove
if this element is present, the original message is removed after it has been successfully copied.
mailboxClass
if this element value is a string, and the targetMailbox Mailbox does not exist, that Mailbox is created.
If the element value is a non-empty string, that value is assigned as the Mailbox Class to the newly created Mailbox.

This function returns a null-value if the operation has succeeded, otherwise it returns a string with an error code.

Message Handles

Message Handles are internal objects representing individual messages stored in Mailboxes.

OpenMessage(boxRef,uid)
This function opens a Message Handle.
The boxRef value should be a Mailbox handle, the uid value should be a number - the message UID.
The function returns a Message Handle if the message has been opened successfully, otherwise it returns a null-value.
MessagePart(msgRef,type)
The msgRef value should be a Message Handle.
If the type value is a null-value, this function returns a dictionary containing the message MIME structure.
Otherwise, the type value should be a string. It specifies the message subpart to search for:
audio
a subpart with audio/* Content-Type.
plain
a subpart with text/plain Content-Type.
text
a subpart with text/* Content-Type. If several alternative subtypes are available, the text/plain part has the lowest priority, followed by text/html part.
If a subpart is found, this function returns a dictionary with this subpart MIME structure.
If no subpart is not found, the function returns a null-value.
If the message cannot be read or parsed, the function returns an error code string.
The dictionary elements are:
estimatedSize
estimated size of the message (or message part) decoded body.
filename
optional - the decoded message part file name.
Content-Type
the message (or message part) content type (such as text, image, etc.)
Content-Subtype
the message (or message part) content subtype (such as plain, jpeg, etc.)
DispositionParams
a dictionary with Content-Disposition field parameters
ContentTypeParams
a dictionary with Content-Type field parameters
MIMEPartID
This element is an empty string for the message itself. For message subparts, this element is a string with the message part ID.
MIMEParts
an array of MIME subparts. Each array element is a dictionary with subpart MIME structure.
contentFieldName
a string with Content-contentFieldName field value
MessageHeader(msgRef,partID,fieldName)
This function returns an array of the specified message header fields, or a dictionary with all message header fields. If the message cannot be read or parsed, the function returns an error code string.
The msgRef value should be a Message Handle.
If the partID is a null-value, then the message headers are returned.
If the partID is a string, it should be a message part ID, and that message part should be of the text/rfc822headers type or it should be the subpart of the message/rfc822 part. The message part headers are returned.
The fieldName value is a string, it specifies the message header field name, and the function value is an array of the specified field values.
Otherwise, the msgRef value should be a null-value. In this case the function value is an dictionary: the dictionary keys are the names of all message header fields, and their values are arrays with the corresponding field values.
If the field name specifies an Email-type field (From, To, Sender, etc.) then the field value is a dictionary. The dictionary element with an empty ("") key is the parsed E-mail address. An optional realName element contains the address "comment" string.
If the field name is E-emailField where emailField is an Email-type field name, then the field value is a string with the parsed E-mail address.
If the field name is a date-type field (Date,Resent-Date), then the field value is a timestamp.
In all other cases, the field value is a string containing the field data, MIME-decoded and converted into the UTF-8 character set.

Example: the msgRef Message Handle references a message with the following header:

From: "Sender Name" <fromName@domain>
Subject: I'll be there!
To: "Recipient Name" <toName@domain>, <toName1@domain1>,
To: <toName2@domain2>
Cc: "Cc Name" <toName3@domain3>
MIME-Version: 1.0
X-Mailer: SuperClient v7.77
Date: Fri, 24 Oct 2008 02:51:24 -0800
Message-ID: <ximss-38150012@this.server.dom>
Content-Type: text/plain; charset="utf-8"
Then the MessageFields(msgRef,"To") returns
({""="toName@domain",realName="Sender Name"},{""="toName1@domain1"},{""="toName2@domain2"})
the MessageFields(msgRef,"E-Cc") returns
("toName3@domain3")
and the MessageFields(msgRef,null) returns
{
 Cc = ({""="toName3@domain3",realName="Cc Name"});
 Date = (#T24-10-2008_10:51:24);
 From = ({""="fromName@domain",realName="Sender Name"});
 Message-ID = ("<ximss-38150012@this.server.dom>");
 Subject = ("I'll be there!");
 To=({""="toName@domain",realName="Recipient Name"},{""="toName1@domain1"},{""="toName2@domain2"});
 X-Mailer = ("SuperClient v7.77");
}
MessageBody(msgRef,partID)
This function returns the message or message part body.
The msgRef value should be a Message Handle.
If the partID is a null-value, then the entire message body is returned.
If the partID is a string, it should be a message part ID. The message part body is returned.
If the message cannot be read, or if the specified message part is not found, this function returns an error code string.
If the message or message part Content-Type is text/*, the function reencodes the result using the UTF-8 character set.
If the message or message part Content-Type is text/xml, the function retruns a parsed XML object.
For all other Content-Types, the function returns a datablock with the message body data.

File Storage

The following functions manage files and file directories in the current Account File Storage.
To access other Accounts File Storage, specify a file or folder name as

~account[@domainName]/fileName
ReadSiteFile(fileDescr)
This function reads a File Storage file.
If the fileDescr value is a string, it specifies the name of the File Storage file to read. The entire file is read - and only files not larger than 1MB in size can be read this way.
If the fileName value is a dictionary, the following dictionary elements are used:
fileName
a string - the name of the file to read
position
an optional element. Its value should be a non-negative number, it specifies the file position (in bytes) from which reading should start.
limit
an optional element. Its value should be a non-negative number, it specifies the maximum data length to read (in bytes). If the file is shorter than starting position plus the read limit, a shorter data block is read. This value should not exceed 1MB.

This function returns a datablock value with the file content, or a null-value if the specified file could not be read.
WriteSiteFile(fileDescr,data)
This function stores the data value (which should be either a datablock or a string) into the specified File Storage file.
If the fileDescr value is a string, it specifies the name of the file to write to. The entire file is rewritten.
If the fileName value is a dictionary, the following dictionary elements are used:
fileName
a string - the name of the file to write
position
an optional element. If present, the file is not completely rewritten.
If this element value is a non-negative number, it specifies the file position (in bytes) from which writing should start.
If this element value is the end or append string, the writing operation starts from the current file end.
If this element value is the new string, the writing operation checks that the file does not already exist.

This function returns a null-value if the file is successfully written, otherwise it returns a string with an error code.
AppendSiteFile(fileName,data)
This function appends the data datablock or string to the end of the fileName File Storage file.
If fileName is not a string or data is not a datablock nor it is a string, this function call results in a program exception.
This function returns a null-value if the file is successfully written, otherwise it returns a string with an error code.
DeleteSiteFile(fileName)
This function deletes the fileName File Storage file.
This function returns a null-value if the file is successfully deleted, otherwise it returns a string with an error code.
RenameSiteFile(oldFileName,newFileName)
This function renames the oldFileName File Storage file into newFileName. Both parameters must have string values.
This function returns a null-value if the file is successfully renamed, otherwise it returns a string with an error code.
CreateSiteDirectory(directoryName)
This function creates the directoryName File Storage directory.
This function returns a null-value if the directory is successfully created, otherwise it returns a string with an error code.
RenameSiteDirectory(oldDirectoryName,newDirectoryName)
This function renames the oldDirectoryName File Storage directory into newDirectoryName. Both parameters must have string values.
This function returns a null-value if the directory is successfully renamed, otherwise it returns a string with an error code.
DeleteSiteDirectory(directoryName)
This function deletes the directoryName File Storage directory. The directory should be empty.
This function returns a null-value if the directory is successfully deleted, otherwise it returns a string with an error code.
ListSiteFiles(folderName)
This function returns information about all files in the specified File Storage subdirectory.
If folderName is not a string, information about the top-level directory in the current Account File Storage is returned.
This function returns a null-value if an error occurred. Otherwise, the function returns a dictionary. Each dictionary key is a file or a subfolder name. For folders, the dictionary value is an empty array. For files, the dictionary value is a dictionary with the following elements:
STCreated
a timestamp value with the file creation date.
STModified
a timestamp value with the file modification date.
STFileSize
a numeric value with the file size in bytes.

Roster

The following built-in functions implement an interface to the Account Roster.

ReadRoster(accountName)
This function retrieves Roster items.
If the the accountName value is a null-value, the current Account Roster is read, otherwise the accountName value should be a string specifying the name of the Account to read Roster items from.
This function returns a dictionary with Roster items, where dictionary keys are contact E-mail addresses, and dictionar values are dictionaries with the following elements:
Inp
the "incoming" subscription mode: it controls if the contact can watch the user presence. Possible values: null-value, true-value, Pending, Blocked.
Out
the "outgoing" subscription mode: it controls if the user can watch the contact presence. Possible values: null-value, true-value, Pending.
RealName
the contact real name string (optional).
If the function fails to retrieve Roster items, it returns an error code string.
SetRoster(params,accountName)
This function updates a Roster item.
If the the accountName value is a null-value, the current Account Roster is updated, otherwise the accountName value should be a string specifying the name of the Account to update.
The params should be a dictionary with the following elements:
peer
The contact E-mail address string (accountName@domainName.
what
The operation type string:
  • update: update the contact information.
  • remove: remove the contact from the Roster.
  • subscribed: confirm the contact request to monitor the user's presence information.
  • unsubscribed: reject the contact request to monitor the user's presence information, or revoke the already granted right to monitor.
  • subscribe: send a request to monitor the contact's presence information.
  • subBoth: confirm the contact request to monitor the user's presence information, and send a request to monitor the contact's presence information.
  • unsubscribe: stop monitoring the contact's presence information.
data
optional - a dictionary containing new contact info.

Datasets

The following built-in functions implement an interface to the Account Datasets. To access Datasets in other Accounts, the dataset name should be specified as ~accountName/datasetName or ~accountName@domainName/datasetName

DatasetList(datasetName,filterField,filterValue)
This function retrieves data entries from an Account dataset.
The datasetName value should be a string with the dataset name.
The filterField, filterValue values should be null-values or strings. If the values are strings, they specify an entry attribute name and value. Only the entries that have the specified attribute with the specified value are included into the resulting value.
This function returns a dictionary with dataset entries. The dictionary keys are entry names, the dictionary elements are data entries. Each data entry is a dictionary containing the data entry attributes.
If the dataset entries could not be retrieved, the function returns an error code string.
DatasetRemove(datasetName,ifExists)
This function removes an Account dataset.
The datasetName value should be a string; it specifies the dataset name.
If the ifExists value is not a null-value, and the dataset to be removed already does not exist, the function does not return an error code.
If the dataset is removed successfully, the function returns a null-value. Otherwise the function returns an error code string.
DatasetSet(datasetName,entryName,entryData,ifExists)
This function modifies data entries in an Account dataset.
The datasetName value should be a string; it specifies the dataset name.
The entryName value should be a string; it specifies the entry name.
The entryData value should be a dictionary; it specifies the entry data (attributes).
If the ifExists value is a null-value, then the dataset is created if it does not exist, and the entry with the specified name is created if it does not exist.
If the dataset is updated successfully, the function returns a null-value. Otherwise the function returns an error code string.
DatasetDelete(datasetName,entryName,ifExists)
This function deletes a data entry from an Account dataset.
The datasetName value should be a string; it specifies the dataset name.
The entryName value should be a string; it specifies the entry name.
If the ifExists value is not a null-value, and the entry to be deleted already does not exist, the function does not return an error code.
If the dataset is removed successfully, the function returns a null-value. Otherwise the function returns an error code string.

Directory

The following built-in functions implement an interface to the Directory Manager.

DirectorySearch(baseDN,filter,parameters)
This function performs a directory search, returning a dictionary with found records.
The baseDN value should be a string with the search base DN. If this value is "$", the Directory Integration settings are used to compose the base DN for the current Domain.
The filter value should be a null-value, or a string with a search filter, in the RFC2254 format.
The parameters value should be a null-value or a dictionary containing search options:
limit
If this option value is a positive number, it specifies the maximum number of records to return. Otherwise, the record limit is set to 100.
keys
If this option value is DN, the resulting dictionary keys are full record DNs. Otherwise, the record RDNs are used as resulting dictionary keys.
scope
If this option value is sub, a subtree search is performed. Otherwise, only the direct children of the base DN record are searched.
attributes
If this option value is an array of strings, only the attributes listed in the array are included into resulting records.
Otherwise, all record attributes are included into resulting records.

If the directory search operation fails (no base DN record, insufficient access rights, etc.), this function returns an error code string.

Services

GetLanguage()
This function value is a string with the currently "selected language".
SetLanguage(lang)
This procedure sets the "selected language". The lang value should be a string with the language name, or a null-value to select the default language.
GetTimeZoneName()
This function value is a string with the currently selected time zone name. If no time zone is selected (the Server time offset is used), the function returns a null-value.
SetTimeZone(zoneName)
This procedure sets the current time zone. The zoneName value should be a string with a known time zone name. If an unknown zone name is specified, or if the zoneName value is not a string, the no zone fictitious value is set, and the Server current time offset is used.
SysLog(arg)
This procedure places the textual representation of the arg value into the Server Log.
SysProfile(arg)
If the arg value is a null-value, the procedure decreases an internal integer profile level counter by 1, otherwise it increases it by 1.
The profile level counter is set to zero when the program starts.
When the profile level counter is positive, profiling records are placed into the Server Log when every user-defined and some built-in functions and procedures are entered and exited.
ExecuteCLI(arg)
This function executes the Command Line Interface (CLI) command.
The arg value should be a string containing one CLI command.
If the CLI command has been executed successfully, this function returns a null-value. Otherwise this function returns an error code string.
If the CLI command has produced an output, it is placed into the Task variable executeCLIResult (it can be accessed as Vars().executeCLIResult. If the CLI command has failed, or it has not produced any output, this Task variable is assigned a null-value.
SetApplicationStatus(arg)
This procedure copies its argument and stores is in the current Task descriptor.
External modules and entities can retrieve this information from the Task descriptor.
StoreCDR(arg)
This procedure sends the arg value (which should be a string) to the External CDR Processor program.
The APP prefix is added to the arg value, and the application is supposed to provide its name and the version number as the first part of the arg value to allow the External CDR Processor program to differentiate records generated with different applications:
APP arg
DoBalance(parameters,accountName)
This function performs a Billing operation.
If the accountName is null, the operation is applied to the current Account. Otherwise, the accountName value must be a string specifying the target Account name. In any case, the operation is subject to the Access Rights restrictions.
The parameters value must be a dictionary. It specifies the operation parameters, see the Billing section for the details.
The function returns an error code string if the operation has failed.
Otherwise the function returns a dictionary with the operation results (as specified in the Billing section).
BannerRead(type,parameters)
This function sends a request to the External Banner System.
The type value should be a string specifying the banner type (application-specific, such as prontoEmailTop, myClientLeftBanner).
The parameters value is passed to the External Banner System.
The function returns the banner data object from the External Banner System response (it may return a null-value).

Communications

HTTPCall(URL,parameters)
This function performs an HTTP transaction.
The current Account must have the HTTP
Service enabled.
The URL value should be a string. It specifies the request URL. The URL schema should be http or https.
The parameters value should be a dictionary. It specifies the request parameters and, optionally, the request body. The following dictionary elements are processed (all of them are optional):
body
a datablock, string, or an XML Object with the request body, or a dictionary.
If a dictionary is specified, the request body is composed in the multipart/form-data format.
Each dictionary element key is used as the form field name, and the element value is used to compose the form field value.
Content-Type
a string with the request body content type.
Content-Subtype
a string with the request body content subtype.
method
a string with the request method. If this element is absent, the GET method is used if no body is specified, otherwise the POST method is used.
Cookie
a string with the Cookie field data.
authName, authPassword
when present, these strings are used to authenticate the request.
timeout
a number in the 0..30 range, used as the transaction timeout value (in seconds). If not specified, a 30 sec timeout is used.
The function returns an error code string if the HTTP transaction failed.
Otherwise the function returns a dictionary with the following elements:
responseCode
a number with the HTTP response code.
responseText
a string with the HTTP response text.
body
a datablock with the response body (may be absent).
Content-Type
a string with the response body content type.
Content-Subtype
a string with the response body content subtype.
charset
a string with the response body charset.
Date, Last-Modified, Expires
timestamp elements with the response header field values.
Server, Location, Set-Cookie
string elements with the response header field values.
SubmitEMail(headers,content)
This function composes and sends an E-mail message.
The headers value should be a null-value or a dictionary. This dictionary specifies the header field values for the composed E-mail message. The following elements are processed (all of them are optional):
From
the element value should be an E-mail address string. It specifies the message From: address
To
the element value should be an E-mail address string or an array of E-mail address strings. It specifies the message To: address(es)
Cc
the element value should be an E-mail address string or an array of E-mail address strings. It specifies the message Cc: address(es)
Bcc
the element value should be an E-mail address string or an array of E-mail address strings. It specifies the message Bcc: address(es)
Subject
the element value should be a string. It specifies the message Subject: field.
Date
the element value should be a timestamp. It specifies the message Date: field. If this element is absent, the current time is used.
sourceType
the element value should be a string. It specifies the message source. If this element is absent, the "CGPL" string value is used
sourceAddress
the element value should be a string. It specifies the address of the message source (network address, remote system name, etc.)
Message-ID
the element value should be a string. It specifies the message Message-ID: field. If this element is absent, an automatically generated string is used.
protocol
the element value should be a string. It specifies the name of the protocol used to submit this message
Content-Class
the element value should be a string. It specifies the E-mail header Content-Class: field value
X-Priority
the element value should be a string. It specifies the E-mail header X-Priority: field value
X-Mailer
the element value should be a string. It specifies the message X-Mailer: field. If this element is absent, an automatically generated string is used.
The content value specifies the E-mail message body. If the value is a dictionary, then the dictionary body element is the actual content, and other dictionary elements specify various body parameters (content header fields). Otherwise the content itself is the actual content and the content body parameters set is an empty one.
The following content body parameters (dictionary elements) are processed (all of them are optional):
Content-Type
the element value should be a string. It specifies the content body Content-Type. If this element is not specified, the Content-Type is set to "text" if the actual content is a string, otherwise it the Content-Type is set to "application"
Content-Subtype
the element value should be a string. It specifies the content body Content-Type subtype. If this element is absent, and the Content-Type is set to "text", the Content-Subtype is set to "plain"
filename
the element value should be a string. It specifies the content body file name
Content-Disposition
the element value should be a string. It specifies the content body Content-Disposition. If this element is absent, and the fileName element is present, the Content-Disposition value is set to "attachment"

If the actual content is a string, it is stored "as is", using the 8bit Content-Transfer-Encoding.
If the actual content is a datablock, it is stored using the base64 Content-Transfer-Encoding.
If the actual content is an array, the content is a multi-part one. Only the Content-Subtype parameter element is used, if it is absent, the "mixed" value is used.
Each array element is stored in the same way as the content value itself.
If the actual content is not an array, a string, or a datablock, an empty content body is stored.
This function returns a null-value if an E-mail message has been composed and sent (submitted to the Queue). Otherwise, this function returns an error code string.

In the following example, a simple text message is sent.

  headers = NewDictionary();
  headers.From    = "from@sender.dom";
  headers.Subject = "Test Message";
  headers.To      = "To@recipient.dom";
  result  = SubmitEmail(headers,"Test Message Body\eEnd Of Message\e");

In the following example, a multipart/mixed message is sent. It contains an HTML text and a binary attachment.

  content = NewArray();

  textPart = NewDictionary();
  textPart.("Content-Type") = "text";
  textPart.("Content-Subtype") = "html";
  textPart.body = "<HTML><BODY>This is an <B>HTML</B> text</BODY></HTML>";
  content[0] = textPart;

  dataPart = NewDictionary();
  dataPart.("Content-Type")    = "image";
  dataPart.("Content-Subtype") = "gif";
  dataPart.fileName = "file.gif";
  dataPart.body     = ReadSiteFile(dataPart.fileName);
  content[1] = dataPart;

  headers = NewDictionary();
  headers.From    = "from@sender.dom";
  headers.Subject = "Test Attachment";
  headers.To      = "To@recipient.dom";
  headers.("Content-Class") = "message";

  result = SubmitEMail(headers,content);

It is possible to include parts of other E-mail messages into a newly composed one. If there is a content body parameter MIMEPartID with a string value, then there must be a content body parameter source with a Message Handle value.
The MIMEPartID parameter value specifies the MIME part of the source Message to be copied into the new message.
If the MIMEPartID parameter value is message, the entire source Message is copied (as a message/rfc822 MIME part body).

  content = NewArray();

  textPart = NewDictionary();
  textPart.("Content-Type")    = "text";
  textPart.("Content-Subtype") = "plain";
  textPart.body = "Please see the attached letter.\e";
  content[0] = textPart;

  attachPart = NewDictionary();
  attachPart.("source")    = MyOldMessage;
  attachPart.("MIMEPartID") = "message";
  content[1] = dataPart;

  headers = NewDictionary();
  headers.From    = "from@sender.dom";
  headers.Subject = "Test Forwarded message";
  headers.To      = "To@recipient.dom";
  headers.("Content-Class") = "message";

  result = SubmitEMail(headers,content);
SendEMail(fromAddress,subject,to,headers,content)
This function composes and sends an E-mail message. A call to this function does the same as the SubmitEMail(headers,content) function call, where the fromAddress, subject, and to value (if they are not null-values) are used instead of the headers dictionary From,Subject, and To elements.

In the following example, a simple text message is sent.

  result = SendEmail("from@sender.dom","Test Message","To@recipient.dom",
                      null,"Test Message\eEnd Of Message\e");
SendInstantMessage(fromAddress,toAddress,content)
This function composes and sends an Instant Message.
The fromAddress value should be a string. It specifies the message From: address.
The toAddress value should be a string. It specifies the message To: (recipient) address.
The content value should be a string. It specifies the message content.
The function only initiates an Instant Message signaling operation, it does not wait for this operation to complete.
This function returns a null-value if an Instant Message has been composed and sent (submitted to the Signal component). Otherwise, this function returns an error code string.
RADIUSCall(address,parameters)
This function composes and sends a RADIUS request.
The address value should be an ip-address. It specifies the address and the port of the RADIUS server to send the request to.
The parameters value should be a dictionary with the following elements:
Type
this element should be a string. It specifies the type of RADIUS request to send:
authenticate, accountingStart, accountingUpdate, accountingStop.
Secret
this element should be a string. It specifies the "shared secret" of the RADIUS server.
Username
this element should be a string. It is used to compose the userName (1) request attribute.
Password
this element should exist in the authenticate requests, and it should be a string. It contains the clear text password to use in the authentication operation.
nn (where nn is a decimal number)
these elements specify additional request attributes (by their attribute numbers).
These element values should be strings, or (for the integer-type parameters) - numbers, or (for Internet-type parameters) ip-addresses.
If an element value is a datablock, then the content of the datablock is sent without any encoding.
If an element value is an array, then the request attribute is added to the request zero or more times, once for each array value.
-nnnnn (where nnnnn is a decimal number)
these elements specify additional vendor-specific attributes (where nnnnn is the VendorID). See the RADIUS section to see more on the vendor-specific attribute presentation.

If the RADIUS operation succeeds, this function returns a dictionary. This dictionary contains attributes the RADIUS server sent in its response. If the RADIUS fails, this function returns a string with an error code.
Note: requests are sent using the UDP socket of the RADIUS module, so this module should be enabled (it should be configured to use some non-zero port number).

In the following example, a RADIUS authentication request is sent. The request contains the nasIdentifier (32) text attribute.

callParam = newDictionary();
callParam.Type     = "authenticate";
callParam.Secret   = "sys2";
callParam.Username = "user4567";
callParam.Password = "drum$1245";
callParam.("32")   = "my NAS";
result = RADIUSCall(IPAddress("[10.0.1.77]:1812"),callParam);

In the following example, a RADIUS accounting request is sent. The request contains the nasIdentifier (32) text attribute and the acctSessionTime (46) numeric attribute.

callParam = newDictionary();
callParam.Type     = "accountingStart";
callParam.Secret   = "sys2";
callParam.Username = "user4567";
callParam.("32")   = "my NAS";
callParam.("46")   = SessionTimeInMinites*60;
result = RADIUSCall(IPAddress("[10.0.1.77]:1812"),callParam);

Multitasking

Certain environments (such as Real-Time Application environments) provide multitasking functionality. In these environments, program invocations (Tasks) can locate each other and exchange data. This section defines the additional language features available in these multitasking environments.

Task handles are internal objects representing a Task. In a Cluster environment, a Task handler includes a reference to the cluster member running the Task.

Spawning

A program (a running Task) can create a new Task by using the spawning expression. It is specified using the spawn keyword followed by a name of an entry code section. A new Task is created and it starts to run concurrently with the Task that used the spawning expression, executing the specified entry code section.
The entry code section name can be followed with an expression enclosed in parentheses. If specified, the copy of the expression value is assigned to the startParameter element of the
Vars() dictionary in the new Task.
The current Task handle is assigned to the parent element of the Vars() dictionary in the new Task.
The spawning expression value is a Task handle for the newly created Task, or null if the system failed to create a new Task.

In the following example, a program executing the Main entry code section creates a new task that starts to execute the DoBackup entry code section, which copies files "file1","file2",...."file100" into "backup1","backup2",..., files.

entry DoBackup is
  nameIndex = 1;
  while nameIndex <= 100 loop
    fileData = ReadSiteFile("file" + String(nameIndex));
    if fileData != null then
      resultCode = WriteSiteFile("backup" + String(nameIndex),fileData);
      if resultCode != null then
        Log("failed to backup file" + String(nameIndex) +
            ". Error Code=" + resultCode);
      end if;
    end if;
  end loop;
end entry;
 
entry Main is
  backuper = spawn DoBackup;
  if backuper == null then
    Log("Failed to start a Backup Task");
  end if;
end entry;

Tasks do not share any variables, even when a Task directly creates a new Task using the spawning expression.

ThisTask()
This function returns the Task handle of the current Task.
This function returns a null value if the current environment is not a Task.
IsTask(arg)
This function returns a true-value if the arg value is a Task Handle, otherwise the function returns a null-value.

Events

The Actor Model is used: Tasks exchange data by sending each other Events.

SendEvent(taskRef,eventName,eventParam)
This function sends an Event to a Task. It returns a null value if an Event was sent successfully, or a string with an error code otherwise (for example, when the specified Task does not exist).
The taskRef value should be a Task handle.
The eventName value should be a string starting with a Latin letter.
The eventParam value should be a null-value, or a Task handle, or a
"basic" object.
This function only sends an Event to the specified (target) Task. It does not wait till that Task receives an event, nor does it wait for any response from the target Task.
ReadInput(secsToWait)
Events sent to a task are enqueued, and the task can read the first Event in queue using this function. The function value is a dictionary containing the event data.
The secsToWait value should be a non-negative number.
If the Task Event queue is empty and the Task does not receive a new Event within the specified number of seconds, the function returns a null-value.
If this function returns a dictionary value, the dictionary contains the following elements:
what
the Event name string. If the Event was sent using the SendEvent operation, this string is the eventName parameter value used in the SendEvent call in the sender Task.
sender
the Task handle of the sender Task (the Task that has sent this event). In a Cluster environment, this Task and the current Task may be running on different Cluster member computers.
If the Event is sent by the platform itself, or if the sender was not a Task, the sender element does not exist.
parameter
the event parameter. If the event was sent using the SendEvent operation in the sender Task, this element contains the eventParam parameter value of the SendEvent call.
Note: depending on the environment, the ReadInput function can return various other objects. For example, if the function is used in a Real-Time Application environment, it can return a string containing the first enqueued DTMF symbol.
Note: the ReadInput function may have "false wakeups", i.e. it can return a null-object even before the specified time period has elapsed.

Meetings

The Meeting mechanism allows a Task to make itself known to other Tasks associated with the same Account.

Each Account can have several named Meeting Sets and an unnamed Default Meeting Set. Several named Meetings can be created in any Meeting Set. Each Meeting is a dictionary object that can contain zero or one Task handle.

The set name can be specified as ~accountName/setName or ~accountName@domainName/setName to access Meetings Sets in other Accounts.
To access Meeting Sets in other Accounts, the current Account should have the canImpersonate Domain Access Right for the target Account Domain.

CreateMeeting(setName,key,param)
This function creates a Meeting object in some Meeting Set within the current Account.
The setName parameter specifies the Meeting set name. If the parameter value is a null-value or an empty string, the Default Meeting Set is used.
The key parameter must be a string. It specifies a unique ID or name for the new Meeting. For example, an application implementing real-time conferencing can generate a random numeric string to be used as the conference password, and it can create a Meeting using that string. Other Tasks associated with the same Account can find that Meeting (and a Task handle for the Task associated with it) if they know the key and the setName parameter values used with the CreateMeeting operation.
The parameter parameter value is stored with the Meeting. Note that the value is stored using its textual representation, so only the standard objects can be used as the parameter values or the parameter value sub-elements. For example, you cannot store Mailbox or Task handles.
This function returns a null-value if a Meeting has been created. Otherwise, this function returns an error code string.
ActivateMeeting(setName,key)
This function adds the Task handle for the current Task to a Meeting in the current Account.
The setName and key parameter values specify an already created Meeting.
There should be no other Task handle stored in this Meeting.
The current Task becomes the Meeting Active Task.
This function returns a null-value if the Task handle has been successfully added. Otherwise, this function returns an error code string.
DeactivateMeeting(setName,key)
This function removes Task handle for the current Task from a Meeting in the current Account.
The setName and key parameter values specify an already created Meeting, and that Meeting should contain a Task handle for the current Task.
When this operation completes successfully, the Meeting has no Active Task.
This function returns a null-value if the Task handle has been successfully removed. Otherwise, this function returns an error code string.
RemoveMeeting(setName,key)
This function removes a Meeting from a current Account Meeting Set.
The setName and key parameter values specify the Meeting to remove.
This function returns a null-value if the Meeting has been successfully removed or if the specified Meeting has not been found. Otherwise, this function returns an error code string.
FindMeeting(setName,key)
This function retrieves Meeting information from a current Account Meeting Set.
The setName and key parameter values specify the Meeting to look for.
If the Account does not have the specified Meeting, the function returns null.
Otherwise, the function returns the Meeting information dictionary containing the following elements:
parameter
the value of the parameter parameter used with the CreateMeeting operation.
id
a Task handle for the Active Task, if any.
In a
Cluster environment, the Active Task and the current Task may be running on different Cluster member computers.
ClearMeeting(setName,key)
This function removes a Task handle from a Meeting (if any).
The setName and key parameter values specify the Meeting to clear.
This function can be used to clear a reference set by a Task that has died.
This function returns a null-value if the Meeting has been successfully cleared. Otherwise, this function returns an error code string.

Queues

The Queue mechanism allows a Task to make itself known to other Tasks associated with the same Account. When a Task registered in a Queue is found by some other Task, the found Task is removed from the Queue.

The queue name can be specified as ~accountName/queueName or ~accountName@domainName/queueName to access Queues in other Accounts.
To access Queues in other Accounts, the current Account should have the canImpersonate Domain Access Right for the target Account Domain.

Enqueue(queueName,parameter,pty)
This function registers the current Task with the Account associated with it.
An Account may have several Queues with Task registrations. The queueName parameter specifies the Queue name. If this parameter value is a null-value or an empty string, the default Queue of the associated Account is used.
The parameter parameter value is stored with the Task registration. Note that the value is stored using its textual representation, so only the standard objects can be used as the parameter values or the parameter value sub-elements. For example, you cannot store Mailbox or Task handles.
The pty parameter value should be a string containing a decimal number with one digit, the dot (.) symbol and any number of digits. The Task is placed in the Queue before all other Tasks with a smaller pty parameter value, but after all tasks with the same or larger pty parameter value. If the pty parameter value is a null-string, the default "1.0" value is assumed.
A Task may register itself several times in different Queues, but it can be registered only once with any given Queue. If the Enqueue function is used by a Task that has been already enqueued into the same Queue, the function does not create a second registration. Instead, the function updates the parameter value enqueued with the Task and may change the Task position in the Queue according to the new pty parameter value.
The function returns a null-value if registration has failed. If registration was successful, the function returns a dictionary containing the following elements:
length
a number - the total number of Tasks in the Queue
position
a number - the current position of the current Tasks in the Queue.
The position of the first Task in the Queue is 0
CheckQueue(queueName)
This function checks the current Task position in an Account Queue.
The queueName parameter specifies the Queue name.
The function returns a null-value if it has failed to access the specified Queue. Otherwise, it returns the same dictionary as the Enqueue function.
Note: the position element exists in the returned dictionary only if the current Task is currently enqueued into the specified Queue. If current Task was not enqueued, or if it has been already removed from the Queue by some other task, this elements will be absent.
Dequeue(queueName)
This procedure removes the current Task from the Account Queue.
The queueName parameter specifies the Queue name.
ReadQueue(queueName)
This function retrieves the first Task from the Account Queue.
The queueName parameter specifies the Queue name.
The function returns a null-value if there is no Tasks in the specified Queue.
Otherwise, the function returns a dictionary containing the following elements:
id
the Task handle for the retrieved Task. In a Cluster environment, this Task and the current Task may be running on different Cluster member computers
parameter
the value of the parameter parameter used when the Task was enqueued
Note: this function removes the first Task from the Queue. Unless the retrieved Task re-enqueues itself into the same Queue, no other Task will find it in that Queue.

Formal Syntax

string::="string-data"
number::=digits
name ::=alpha-numeric-and-underscore-starting-with-alpha
variable::=name
dataRef::=variable | expr [ expr ] | expr . name | expr . ( expr )
spawnExpr::=spawn name [ ( expr ) ]
basicExpr::=string | number | null | false | true | dataRef | expr . name ( [argList] ) | spawnExpr
unaryOp::=! | not | - | +
unary::=basicExpr | unaryOp unary | ( expr )
multOp::=* | / | %
multBinary::=unary | multBinary multOp unary
addOp::=+ | -
addBinary::=multBinary | addBinary addOp multBinary
cmpOp::=< | <= | == | != | >= | >
cmpBinary::=addBinary | cmpBinary cmpOp addBinary
logicOp::=& | and | | | or | && | and then | || | or else
logicBinary::=cmpBinary | logicBinary logOp cmpBinary
ternary::=logicBinary | logicBinary ? logicBinary : ternary
expr::=ternary
argList::=expr 0*(, expr)
funcCall::=name ( [argList] )
procCall::=name ( [argList] ) | expr . name ( [argList] )
letOp::== | += | -= | *= | /= | %= | |= | &=
letOper::=dataRef letOp expr
nullOper::=| null
stopOper::=stop
returnOper::=return [ expr ]
ifOper::=if expr then opSequence 0*( elif expr then opSequence ) [ else opSequence ] end [ if ]
altIfOper::=if expr { opSequence } 0*( elif expr { opSequence } ) [ else { opSequence } ]
loopOper::=[while expr ] loop opSequence 0*( exitif expr ; opSequence) end [ loop ]
altLoopOper::=while expr { opSequence 0*( exitif expr ; opSequence) }
oper::=nullOper | procCall | letOper | returnOper | stopOper | ifOper | loopOper
altOper::=altIfOper | altLoopOper
seqOper::=oper ; | altOper
opSequence::=0*( seqOper )
entryBody::=forward ; | is opSequence end [ entry ] ; | { opSequence }
procBody::=forward ; | external ; | is opSequence end [ procedure ] ; | { opSequence }
funcBody::=forward ; | external ; | is opSequence end [ function ] ; | { opSequence }
parmList::=name 0*(, name)
entry::=entry name entryBody
procedure::=procedure name ( [ paramlist] ) procBody
function::=function name ( [ paramlist] ) funcBody
program::=1*(entry | procedure | function)

CommuniGate® Pro Guide. Copyright © 1998-2009, Stalker Software, Inc.