NexJ Logo

NexJ JavaScript differences

JavaScript scripting is implemented to support NexJ's business modeling use cases. The entirety of the JavaScript specification is not implemented for this purpose; for example, templates are not supported. Note the following when adding JavaScript code to classes and unit tests, creating JavaScript libraries, or using JavaScript in the console.

ECMA Standard 5th edition is supported. Any code using subsequent changes or additions to the standard are ignored. 

Variables

All variables must be defined with a var statement. The var statements must be declared at the beginning of your code. Hoisting or lifting variables is not supported.

The JavaScript var statement converts directly to a Scheme define statement. Variables cannot be dynamically defined without a var statement.

Arrays

Sparse arrays are not supported.

If an element is set using an index which is beyond the size of the array, you will get an out-of-bounds exception.

If an element is accessed using an index which is less than 0, you will get an out-of-bounds exception.

You cannot add an element to an array with an index which is greater than the size of the array.

Classes

You cannot define objects in your script. Objects must be defined in the model as classes and their manipulations must be defined in the model as class events.

You also cannot instantiate objects. However, you can instantiate model classes, using the `new` command.

Remember to commit or rollback any new instances that you wish to add to the database. Use the commit() or rollback() command.

You can only access class attributes and class events using the dot notation, for example objectName.propertyName.

You can import Java classes using the importJava("className") function, where className is the fully qualified name of the Java class you want to import.

Identifiers

You can access identifiers that already exist in the model and were written in Scheme. For non-standard identifiers, specify with a special sequence:

#"sample Scheme identifier"

This code is included as Scheme code. It does not get translated and its value is not modified. This sequence is helpful to use for function calls using the dot notation but which do not include the grave accent or backtick (`). 

To pass any Scheme code, use the predefined function scm(). For example, scm("sample Scheme code"). This function can also be used for identifiers. This text is added as  Scheme script and is not translated.

Only the double quotation mark (") can be used as a literal text delimiter.

Statements

The return statement is only supported within a function. In a complete script, you must define a "result" variable at the beginning or the script, and then use this variable as the script output.

The following statements are not supported:

  • import statement
  • for ... in statement
  • for ... var... in statement
  • with statement
  • debugger statement
  • property getter function
  • property setter function

In addition, statements using any future reserved words are not supported.

Functions 

All Scheme functions can be called using JavaScript. Use the following format: functionName(parameter1, parameter2, ...)

If the Scheme function name contains illegal characters, use the following format instead: #"functionName(parameter1, parameter2, ...)"

JavaScript Math object functions are not supported. You can use the equivalent Scheme functions. For example, the abs(x) function in Scheme is equivalent to the Math.abs() function in JavaScript and returns the absolute value of a number.  

JavaScript Date object functions are not supported. You can use the new Date() function that has been created.

Date function

The new Date function supports date and time requirements.

To get a date as a timestamp, use new Date(parm1, parm2 ... parm7) statement, where the arguments are the following in sequence: year, month, day, hour, minute, second, millisecond. You can specify fewer than seven arguments, as long as the argument preceding the missing argument in the sequence has been specified.

For example, new Date(1951 9 2 10) returns #m1951-09-02T10:00:00.000000000

If no arguments are passed to the new Date() statement, then the current date and time is returned as a timestamp. To get the current date as a string, use Date() instead.

The date is in UTC (Coordinated Universal Time).

Operators

The following operators are not supported:

  • postfix decrement operator (--)
  • postfix increment operator (++)
  • typeof operator
  • delete operator
  • zero fill right shift operator (>>>) 
  • zero fill right shift assignment operator (>>>=)
  • void operator

All infix operators must be separated from operands by a space.

Comparison operators

The equals comparison has to be interpreted in a way that is compatible with the existing underlying system.  As a result, the following behavior is to be expected:

Implementation of obj1  === obj2 (Equals Strict Comparison) 

ExpressionResult
  • Both obj1 and obj2 are null.
true
  • Only one of obj1 or obj2 is null.
false
  • Both obj1 and obj2 are the same Boolean value.
true
  • Both obj1 and obj2 are Boolean values.
  • Objects obj1 and obj2 are different Boolean values.
false
  • Both obj1 and obj2 are numbers.
  • At lease one of obj1 or obj2 equals NaN.
false
  • Both obj1 and obj2 are numbers.
  • Object obj1 equals -0.0 or +0.0
  • Object obj2 equals -0.0 or +0.0
true
  • Both obj1 and obj2 are numbers.
  • Object obj1 and obj2 have the same value.
  • Object obj1 and obj2 are either the same type or different types.
true
  • Both obj1 and obj2 are symbols.
  • Both obj1 and obj2 have the same name.
true
  • Both obj1 and obj2 are strings with the same value.
true
  • obj1 equals(obj2)
true (if obj1 and obj2 refer to the same instance of an object)

Implementation of obj1 == obj2 (Equals Abstract)

ExpressionResult or evaluation
The result of strict comparison of obj1 === obj2 is true.

true

If the result is false, the following logic is processed in order.

Both obj1 and obj2 are null.true
Only one of obj1 or obj2 is null.false
One of obj1 or obj2 is a number and the other is a string.
  1. The string is converted to a number. If it cannot be converted to a number, it is set to #f.  
  2. The resulting obj1 and obj2 are compared as numbers. If obj1 === obj2, then the result is true.
One of obj1 or obj2 is a string or a number and the other is a Boolean value.
  1. The Boolean value is set to a number: 0 if true, 1 if false.
  2. The resulting obj1 and obj2 are compared as numbers. If obj1 == obj2, then the result is true.
One of obj1 or obj2 is a number and the other is a timestamp.
  1. The timestamp is converted to a long.
  2. The resulting obj1 and obj 2 are compared as numbers. If obj1 === obj2, then the result is true.
Both obj1 and obj2 are timestamps.
  1. Both objects are cast to long.
  2. The resulting numbers are compared. If obj1 == obj2, then the result is true.
One of obj1 or obj2 is a string and the other is a timestamp.
  1. The timestamp is converted to a string
  2. The resulting strings are compared. If obj1 == obj2, then the result is true.
One of obj1 or obj2 is a string and the other is an array (collection).
  1. The array is converted to a string.
  2. The array is converted to an object as follows:
    1. Initialize the converted object to null.
    2. If the array is empty, set the object to 0 (zero).
    3. If the array has a single value, set the object to that value.
  3. The string is compared to the resulting object. If obj1 == obj2, then the result is true.
One of obj1 or obj2 is an ArrayList and the other is a Boolean value or a number.
  1. The array is converted to an object as follows:
    1. Initialize the converted object to null.
    2. If the ArrayList is empty, set the object to 0 (zero).
    3. If the ArrayList has a single value, set the object to that value.
  2. The original Boolean value or number is compared to the result of converted array object. If obj1 == obj2, then the result is true.

One of obj1 or obj2 is a string.

  1. The other object is converted to a string.
  2. The strings are compared. If obj1 == obj2, then the result is true.
None of the above conditions is evaluated to true.false