Numeric Expression algorithms mask numeric input by evaluating it within a one-line, mathematical expression written by
the user in the Java programming language. The expression can reference the current unmasked value via an implicit
For example, to mask a numeric column by always multiplying the input by 50%, the following expression could be used:
input * 0.5
In addition to
input, the expression can reference user-defined constant variables whose values are determined at the
beginning of a masking job and remain fixed for the life of the masking job.
See below for examples of expressions and constants.
Creating a Numeric Expression Algorithm via UI¶
- In the upper right-hand corner of the Algorithms tab, click Add Algorithm.
- Select Numeric Expression Framework. The Create Numeric Expression Algorithm pane appears.
Enter an Algorithm Name. (Required)
This MUST be unique on the Masking Engine.
- Enter an optional Description.
Enter an Expression. This must be a one-line, mathematical expression written in the Java programming
language that references
input(the current unmasked value), e.g.
input * 0.5or
input + Math.random(). See below for more examples of expressions.
Choose the Input Type. This is the data type that
inputconforms to within the expression. The default double option causes
inputto be treated as a double-precision floating point variable in expressions such as:
input * 0.5
Input Type can also be set to long, which causes
input + Math.random()
inputto be treated as a long integer variable in expressions such as:
The final Input Type option is BigDecimal, which causes
inputto be treated as a
java.math.BigDecimalvariable in expressions such as:
- Enter an optional Replacement Value for Nonconforming Data if necessary. This is the default masked value to be used if the unmasked input is not a numeric data type and can't automatically be converted to one.
Optional: define any constants used by the expression. Constants are variables that the expression can
reference by name and whose values remain fixed for the life of a masking job. For example, to mask every
column value in a masking job by multiplying them all by the same random number, you could use an expression
but theSameRandomNumber would need to be defined as a constant whose Name is
input * theSameRandomNumber
theSameRandomNumberand whose Value is something like
new java.util.Random().nextDouble(). See below for more examples of constants.
- When you are finished, click Save.
For information on creating Numeric Expression algorithms through the API, see API Calls for Creating Algorithms - Numeric Expression.
Writing Good Expressions & Constants¶
Expressions and the Java programming language are powerful. Care must be taken to avoid writing bad expressions, which will manifest in the form of failed masking jobs. It is highly recommended to stage complex expressions with a Java IDE such as Eclipse or IntelliJ IDEA before using them in a masking job.
The requirement that expressions must be written in Java might be intimidating to non-programmers, but simple
mathematical equations in Java look similar to simple mathematical equations in general. The four most common operators
are supported: addition (
+), subtraction (
-), multiplication (
*), and division (
/). For operators not supported
by Java, use methods from the java.lang.Math library.
For example, one might expect
input ^ 5 to mean "take input to the fifth power," but
^ is not a power operator in
Java. Instead, use
To isolate parts of the expression for clarity or to enforce order of operations, use open and closed parentheses
only. Do not use square braces
 or curly braces
Expression Do's and Don'ts¶
Do use an Input Type (explained above) that corresponds to the data type of the column being masked. For columns whose values are floating-point numbers (i.e. numbers that have digits to the right of the decimal point) set Input Type to double (the default) or BigDecimal if the expression needs to treat the input as a java.math.BigDecimal object in order to perform more complex math. For columns whose values are integers (whole numbers), set Input Type to long.
Don't write expressions that do mathematically impossible things (e.g. divide by zero) or will result in numeric overflow or values that are too large or too small to fit in the database column being masked.
Don't use line breaks or other whitespace to force an expression to be longer than one line.
Don't attempt to assign an expression to a variable. For example, this won't work:
output = input * 0.5
but this will:
input * 0.5
The result of the expression will be automatically assigned as the masked value. It's not necessary or allowed to assign it to anything else.
Don't use the
return keyword or end the expression with a semicolon.
Don't write expressions that return a non-numeric value, e.g.
The above expression would return a
List object, which can't be converted into a numeric value. Expressions must
return a value whose type is numeric: an
double Java primitive type (or their
object wrappers) as well as
(character array) values is also acceptable as long as they can be converted into a numeric value.
Do fully-qualify any Java class the expression references that isn't in the
java.lang package, e.g.
input * new java.util.Random().nextDouble()
This won't work:
input * new Random().nextDouble()
Random class is in the
java.util package rather than
Don't use the
import keyword in an attempt to import non-
java.lang classes that are referenced frequently by
the expression and/or constants. Fully-qualify such Java classes every time they're referenced.
Constants are variables that the expression can reference by name and whose values remain fixed for the life of a masking job. Constant names must be valid Java variable names. No two constants can have the same name, nor can "input" or "seed" be used as a constant name.
Constant values are very much like the expression: one-line Java expressions that must return a value. However, unlike the algorithm's main expression, constant values aren't required to be numeric.
Constants can reference by name other constants defined before them.
There is a built-in constant named
seed. Its value is a long integer that's based on the algorithm key, so the value
seed is guaranteed to remain the same across multiple masking jobs as long as the algorithm key remains the same.
A common use case for
seed is to seed a random number generator to produce the same (i.e. predictable) "random"
number(s) among different masking jobs.
Numeric Expression Examples¶
A numeric column must be masked by multiplying all of its values by the same random percentage. The random percentage must remain the same across every masking job.
A single constant is required for the random percentage:
Note that the built-in
seed constant is being used to seed the random number generator, an instance of
java.util.Random, which is used to produce a single random number.
The expression can then reference
randomPercentage like this:
input * randomPercentage
A numeric column must be masked by taking the square root of each value, then rounding it to a certain number of decimal places. Initially, it will be rounded to two decimal places, but the number of decimal places will be changed frequently, so it should be easily adjustable by the user.
We'll define two constants this time:
then use this expression:
Math.floor(Math.sqrt(input) * multiplier + 0.5) / multiplier
The heavy lifting is being done by the main expression, which uses the
multiplier constant. Note that
decimalPlaces, whose value could be easily changed by someone who is not inclined mathematically and
doesn't understand how the expression is rounding numbers.
We must mask a numeric column that represents the day of the current month, e.g. 1-31 (or 1-28, 1-29, 1-30). This column will be masked by adding to it a random number of days, which can be between 1 and the highest day in the current month, inclusive. If the masked value exceeds the highest day in the current month, it will simply be set to the highest day in the current month.
First, since the day of the current month is an integer (whole number), set the algorithm's Input Type to long (integer) instead of the default double (floating point).
Then define three constants:
calendar is a new instance of
java.util.Calendar set to the current date and time.
calendar to determine the last day of the current month.
lastDayOfMonth to generate a random number between 1 and
The expression will then look like this:
(input + randomDays > lastDayOfMonth) ? lastDayOfMonth.longValue() : input + randomDays
This expression leverages Java's ternary operator to mask conditionally. If the unmasked input plus
lastDayOfMonth, then the masked value will simply be
lastDayOfMonth. Otherwise, the masked value will be
the unmasked input plus