Expressions

Minimum version required

The features described in this page require EZproxy 5.1a GA or later unless otherwise noted.

Overview

EZproxy 5.1 introduced the ability to perform more complex string and math manipulations to allow more advanced authorization decisions. The following information explains the constant, variables, and functions that are available to create complex expressions.

The EZproxy administration page provides a Test user.txt configuration option, which can be used to experiment with variables and functions.

From the Test user.txt configuration page, you can check the Force Debug option and then enter a test like this:

::Common
If login:user eq "test"; Msg user is test
If login:user =~ "/^(.)(.)(.)(.)$/" {
  Set rev = re:4 . re:3 . re:2 . re:1
  Msg 4-letter username reversed and stored in rev
}
/Common

If you past in this example, try entering the 4-letter usernames test and TEST, noting that only the lower-case test triggers the message "user is test" to appear since eq is case-sensitive.

Conventions

[5.1b]
If a function was introduced after EZproxy 5.1a, the version in which the function was introduced is noted after the function name in square brackets.
aggvar
the base name of a variable that can have one or more value, such as the base name of an array or the name of an auth: variable that returns multiple values; when used with an aggregate test, EZproxy will also include any non-array variable of the specified name in the test (e.g., abc, abc[1], and abc["xyz"] are all considered when performing an aggregate test for the variable abc).
bool, bool1, bool2
For Boolean values, empty strings and 0 are considered to be false, all other values are considered true.
The result of a Boolean operation is 0 if the value is false or 1 if the value is true.
dt
A numeric value representing a date/time as the number of seconds that have elapsed since midnight, January 1, 1970.
int, int1, int2
An integer numeric value (any decimal portion is ignored).
num, num1, num2
A numeric value that can include decimal points.
str, str1, str2
A string value.
re
A string containing a regular expression; the string must starts with a non-alpha, non-digit character, a pattern, the same non-alpha, non-digit character, and may optionally be followed by i for a case-insensitive comparison and/or g to indicate a global replace.
wild
A wildcard comparison string which is compared using a case-insensitive comparison and in which ? matches to any single character and * matches 0 or more characters.

Constants

Numeric constants are formed from digits and an optional decimal point.

String constants must be surrounded by either a single quote (') or a double quote (") characters. The use of a single quote (') or double quote character (") has identical meaning to EZproxy. Within a string, the backslash (\) can be used to escape the string quoting character (e.g. O'Grady can be specified as 'O\'Grady' or "O'Grady"). Since backslash acts as an escape character, \\ must be used within a string to specify a \ character.

Variables

Standard variables are case-sensitive and must start with a letter which can be followed by any combination of letters, digits, underscores (_), and at signs (@). Variables may also be followed by an opening square bracket, an expression that forms an associate index, and a closing square bracket to store values in an associative array.

There are several namespace prefixes that are used to access special variable sets. The standard namespace prefixes are auth:, db:, login:, re:, and session:

The auth: namespace is used to access variables from an authentication source. Examples of support authentication methods include CAS, HIP, III, LDAP, Shibboleth, SIP, and TLC. The auth: variables are only available during the processing of user.txt, so any value that needs to be retained should be stored in a session: variable. See the example below. If an authentication source can return more than one value for the same variable, access the first value by include [0] at the end of the variable names, [1], for the second, etc. When using auth:, the variable names can include any of these additional special characters: ! # $ % & * + - . / ^ | ~

The db: prefix provides access to database definition information within the ^B/^E loop of menu.htm. The variables available include db:title, db:description, and db:url.

The env: prefix was introduced in EZproxy 5.1b and provides access to operating system environment variables.

The login: prefix provides access to key variables that are come from login.htm and loginbu.htm during login, including login:auth, login:pass, login:pin, login:url, and login:user. If a value is assigned to login:loguser during login process, the assigned value is used as the username for the user. Starting in EZproxy 5.1c, a value may be assigned to login:user to override the username that is tested by authentication methods.

The re: namespace provides access to the last values that matches during a regular expression comparison, with re:0 holding the last value matched, and re:1 through re:9 holding any values captured by parentheses.

The session: namespace can be used to store values in variables that survive across the entire user session. These variables can be used in files such as menu.htm using the syntax ^{expression}. The special variable session:admin returns 1 if the logged in user is an administrator, 0 if not. The special variable session:user provides the current username if some function has activated username tracking (e.g., if auditing is enabled).

Expressions

Expressions are formed by mixing constants and variables using any appropriate combination of the following comparisons, operations, and functions.

The most common uses for expressions occur in user.txt with an authentication method block using the If or Set directives. For example:

::SIP
Host sip.yourlib.org
SIP2
IfUnauthenticated; Stop
If auth:BV >= 10 || auth:AT > 5; Deny delinquent.htm
Set session:fullname = auth:AE
/SIP

can be used to deny access if someone's outstanding fines (BV in SIP) are $10 or higher, or if the user has five or more items overdue (AT in SIP), and to store away the person's name (AE in SIP) in a session variable called fullname that can then be referenced in menu.htm with ^{session:fullname}.

Numeric operations

num1 + num2
Add num1 to num2
num1 - num2
Subtract num2 from num1
num1 * num2
Multiply num1 by num2
num1 / num2
Divide num1 by num2
int1 % int2
Integer modulus of int1 and int2 (the integer remainder of the division of int1 and int2)
int1 & int2
Bitwise and of int1 and int2
int1 | int2
Bitwise or of int1 and int2

String operation

str1 . str2
Concatenate str1 and str2 together into a single string

Boolean operations

For Boolean operations, empty strings and 0 are considered to be false, all other values are considered true. The result of a Boolean operation is 1 if the value is true or 0 if the value is false.

! bool
1 if bool is considered false, 0 otherwise (not operator)
bool1 && bool2
1 if bool1 and bool2 are considered true, 0 otherwise (and operation)
bool1 || bool2
1 if bool1 or bool2 are considered true, 0 otherwise (or operation)
bool ? val1 : val2
val1 if bool is considered true, val2 otherwise (ternary operation); prior to 5.1c, the order of operation for var = bool ? val1 : val2 was unintentionally evaluated as equivalent to (var = bool) ? val1 : val2; starting in 5.1c, this expression now evaluates to be equivalent to var = (bool ? val1 : val2)

Miscellaneous operations

var = val
Used to assign a value to variable
expression1, expression2
Multiple expressions be combined with a comma, which is most often used to perform multiple variable assignments in a single expression (e.g., a = 1, b = 2, c = 3).

Numeric comparisons

These comparisons are based on the numeric values of the values being compared (e.g., 2 is less than 10).

num1 < num2
1 if num1 is less than num2, 0 if not
num1 <= num2
1 if num1 is less than or equal to num2, 0 if not
num1 == num2
Note: this symbol is two equal signs and not just a single equal sign

1 if num1 equals num2, 0 if not
num1 != num2
1 if num1 is not equal to num2, 0 if not
num1 >= num2
1 if num1 is greater than or equal to num2, 0 if not
num1 > num2
1 if num1 is greater than num2, 0 if not

String comparisons

Unless otherwise noted, these comparisons are case-sensitive based on the sequences of characters in the string values being compared (e.g., "10" is less than "2" since the character "1" comes before the character "2", and "B" is less than "a" since internally"B" comes before the character "a"). To perform a case-insensitive comparison, use either the Upper or Lower function (e.g., Upper("B") is greater than Upper("a") since "B" is comes after "A", and likewise Lower("B") is greater than Lower("a") since "b" comes after "a").

str1 lt str2
1 if str1 is less than str2, 0 if not
str1 le str2
1 if str1 is less than or equal to str2, 0 if not
str1 eq str2
1 if str1 is equal to str2, 0 if not
str1 ne str2
1 if str1 is not equal to str2, 0 if not
str1 ge str2
1 if str1 is greater than or equal to str2, 0 if not
str1 gt str2
1 if str1 is greater than str2, 0 if not
str =* wild
1 if str is wildcard equal to wild, 0 if not
str =~ re
1 if str matches the regular expression re and set local variable re:0 to the match string and re:1 through re:9 to anything capture by parentheses, 0 if not.
str !~ re
0 if str matches the regular expression, 1 if not and set local variable re:0 to the match string and re:1 through re:9 to anything capture by parentheses

Functions

ActiveGroupMember(str) [5.1b]
This Boolean function returns 1 if the user has an active session and if the user is a member of any of the groups specified by str, or 0 if not.
ActiveSession() [5.1b]
This Boolean function returns 1 if the user has an active session, or 0 if not.
All(aggvar, str)
This Boolean function returns 1 if all of the values of aggvar are case-sensitive equal to str, 0 if not.
AllRE(aggvar, re)
This Boolean function returns 1 if all of the values of aggvar equal the regular expression, 0 if not.
AllWild(aggvar, wild)
This Boolean function returns 1 if all of the values of aggvar are wildcard equal to wild, 0 if not.
Any(aggvar, str)
This Boolean function returns 1 if any of the values of aggvar is case-sensitive equal to str, 0 if not.
AnyRE(aggvar, re)
This Boolean function returns 1 if any of the values of aggvar equal the regular expression, 0 if not.
AnyWild(aggvar, wild)
This Boolean function returns 1 if any of the values of aggvar are wildcard equal to wild, 0 if not.
Authenticated()
This Boolean function returns 1 if the user has successfully authenticated, or 0 if not.
Chr(int)
The string function returns a string based on the character associated with the integer value (e.g., Chr(65) returns "A").
City()
This string function returns the city associated with the user's IP address based on information provided by Location directives in config.txt.
Coalesce(str1 [,str2 , str3, ...]) [5.1c]
This string function returns the first string that exists and is not blank.
Count(aggvar)
This numeric function returns the number of aggvar variables that exist.
Country()
This string function returns the country associated with the user's IP address based on information provided by Location directives in config.txt.
CountryName()
This string function returns the country name associated with the user's IP address based on information provided by Location directives in config.txt.
DateTime(year, month, day, hour, min, sec)
This numeric function returns the number of seconds that have elapsed between midnight, January 1, 1970 and the date/time specified. If all values are omitted by specifying just DateTime(), return the value based on the current date and time. If year is specified, the default values for month and day are 1, and the default values for hour, min, and sec are 0. Hour is specified in military time from 0 to 23. Time is computer based on the local timezone.
Expired()
This Boolean function returns 1 if the EZproxy attempted to authenticate the user and the credentials were accepted but were considered invalid, or 0 if not.
FormatDateTime(str, dt)
Format a date specified as the number of seconds that have elapsed since midnight, January 1, 1970 using the specified string. The string can contain %Y for a 4-digit year, %y for the two-digits of the year, %m for the month, %d for the day, %H for the 24-hour clock hour, %I for the 12-clock hour, %M for the minutes, %S for the seconds, %p for the locale equivalent of a.m. or p.m. For example, FormatDateTime("%Y-%m-%d %H:%M:%S", DateTime()) can be used to obtain the current date and time in YYYY-MM-DD HH:MM:SS format.
GroupMember(str)
This Boolean function returns 1 if the user would be assigned to any of the groups specified by str upon successful authentication, or 0 if not.
Hash(str1, str2 [, bool]) [5.1c]
This string returns a hexadecimal representation of the cryptographic hash of str2 based on the value of str1. The supported values for str1 are "MD5", "SHA1", "SHA256", or "SHA512". The optional bool value indicates if alphabetic character in the hash should use upper-case (value 1) or lower-case (value 0), and defaults to 1.
HTMLEncode(str)
This string function returns a copy of str with HTML special characters (e.g., <, >) encoded for safe display.
Index(str, substr)
This numeric function check to see if substr is contained with str. Returns -1 if substr is not contained within str, or returns the position where substr begins based from 0 (e.g., Index("abc", "d") returns -1, Index("abc", "a") return 0, Index("abc", "c") return 2).
Invalid()
This Boolean function returns 1 if the EZproxy attempted to authenticate the user but the credentials provided were invalid, or 0 if not.
IP()
This string function returns the IP address of the remote user in dotted-quad format (e.g., 132.174.1.2).
Join(delim, str1 [,str2 , str3, ...])
This string function joins together one or more strings, inserting delim between each string (e.g., Join(" ", "sample", "join", "data") returns "sample join data").
Left(str, len)
This function returns the first len characters of str.
Lower(str)
This string function returns a copy of str with all alpha characters converted to lower-case.
LTrim(str)
This string function returns a copy of str with all left-side (leading) whitespace removed.
Mid(str, start [, len])
This string function returns a portion of str beginning at position start (based from 0) through the rest of the string if len is omitted, or for up to len characters.
NoActiveGroups() [5.1b]
This Boolean function returns 1 if the user has an active session but is not currently assigned to any groups, or 0 if the user is not authenticated or if the user is assigned to any groups.
NoGroups()
This Boolean function returns 1 if the user would not be assigned to any groups upon successful authentication, or 0 if there are groups to which the user would be assigned upon successful authentication.
Null(var)
This Boolean function returns 1 if the variable var does not exist or 0 if the variable does exist.
Ord(str)
This numeric function returns the numeric value of the first character of str.
ParseName(namestr, formatstr, namespacestr)

This function parses a name to extract specified components into individual variables. Extracted name components are placed in variables named title, forename, middleName, surname, and nameSuffix. These variable names are case-sensitive. If namespacestr is specified, then the variable names are prefixed with the value of namespacestr and a colon (:).

The formatstr may contain the letters T (title), F (forename), M (middleName), S (surname), X (nameSuffix), K (keep existing variable values), and the comma character (,).

Sample uses include:

# Example 1: name in surname, forename middleName, nameSuffix format
# store results to surname, title, forename, middleName, nameSuffix
Set ParseName(name, "S,TFM,X", "")
# Example 2: name in title forename middleName surname nameSuffix
# store results to session:title, session:forename, session:middleName,
# session:surname, session:nameSuffix,
Set ParseName(name, "TFMSX", "session")

By default, ParseName erases the values of all possible destination variables before it parses the name. To prevent the clearing of existing variables, add K anywhere in formatstr.

QueryStringPass()
This Boolean function returns 1 if a password came into EZproxy through the query string, or 0 if not.
Refused()
This Boolean function returns 1 if a remote authentication server has yet to be accessed or if the server refused a connection request from EZproxy, or 0 if not.
Region()
This string function returns the region associated with the user's IP address based on information provided by Location directives in config.txt. Region codes are based on the two-character ISO 3166-2 subcountry code for the US and Canada or the FIPS 10-4 subcountry code for other regions of the world.
REReplace(re, replace, str)
This string function search str for matches to re and replaces them with replace.
Right(str, len)
This function returns the last len characters of str.
RTrim(str)
This string function returns a copy of str with all right-side (trailing) whitespace removed.
Upper(str)
This string function returns a copy of str with all alpha characters converted to upper-case.
URLEncode(str)
This string function returns a copy of str with URL special characters percent-hex encoded.
UserFile(str)

This Boolean function directs EZproxy to try to open a file of the specified str and evaluate it based on the rules normally applied to user.txt and then returns 1 if the current user credentials are considered valid or 0 if not.

During user authentication, if the Admin directive has been used to declare a user as an administrator and then UserFile is called, the earlier Admin directive will be cancelled out. To avoid this, insure that any use of the Admin directive occurs either within the file invoked by UserFile or appears somewhere in the main file after UserFile is invoked.

The file specified does not need to include authentication directives, and may instead contain a simple ::Common /Common block of commands that manipulate variables. An advanced application of this concept to incorporate a time-of-day based greeting into login.htm might involve adding:

^{UserFile("greeting.txt"), greeting}

to login.htm and creating greeting.txt in the directory where EZproxy is installed with this content:

::Common
Set now = DateTime()
Set hour = FormatDateTime("%H", now)
Set timeOfDay = "afternoon"
If hour < 12; Set timeOfDay = "morning"
If hour >= 18; Set timeOfDay = "evening"
Set greeting = "Good " . timeOfDay
/Common
UserString(str)
This Boolean function operates identical to the UserFile function, with the exception that str is a string variable that should be evaluated as though it was part of user.txt.

GeoLite data

This product includes GeoLite data created by MaxMind, available from www.maxmind.com .