0.0.4 • Published 12 months ago

monflabs-jsplayground-pre v0.0.4

Weekly downloads
-
License
ISC
Repository
-
Last release
12 months ago

JsonScript

JsonScript is a language designed to run scripts and manipulate JSON data. It is heavily inspired by JavaScript but it is not not JavaScript. It is designed to integrate well with the underlying platform, which is here Java and the JVM.

Goals and non Goals

  • Create a script language that is tighly integrated with the underlying platform. Make this language easy to use for both Java and JavaScript developers.
  • Create a language designed to run large, long running programs.
    Rather, it is a scripting language used to automate tasks in the underlying platform. For that reason, it doesn't feature modules or classes.
  • Create a 100% compatible JavaScript interpreter. There are several available like Nashorn, Rhino, GraalVM or ES6Draft, just to name the major ones.

Differences With JavaScript

Types

Primitives vs Objects

JsonScript does not make a difference between primitive types and Objects, like in JavaScript. Therefore, everything is an object but certain objects, namely String, Number or Boolean also behave like primitives. This introduces some minor changes compared to JavaScript:

  • "a string" and new String("a string") are identical.
    Actually, new String(s) returns s.

Global Java identifiers

The java library makes the following globals, representing java classes or primitive types:

  char
  byte
  short
  int
  long
  float
  double
  boolean
  String
  BigInteger
  BigDecimal
  List
  Map
  Object
  Array
  Java

undefined and null, and NULL

undefined does not exist in JsonScript, mainly because it does not exist in Java. It only handles the null value.
Now, to efficiently deal with JSON access, we introduce a new null value called NULL. Semantically, it works like null but it propagates when accessing members, instead of raising a NullPointerException.

const n1 = null;
n1.a; // -> throws exception

const n2 = NULL;
n2.a; // -> resolves to NULL (propagated)

Currently, the NULL value is only returned by Array and Object when a member does not exist.

const o = {}
o.a; // -> NULL
o.a.b; // ->NULL

Type coercion

JsonScript enforces that the right types are used and doesn't do coercion, like automatically transforming values to String or Number. It throws errors when the right type is not used. For example, mysstring.charAt("2") fails as the string "2" is not automatically converted to the number 2, and thus generates an error.
It also validates the arguments with the method signature so mysstring.charAt() and mysstring.charAt(1,2) will both fail because the signature of the method is charAt(pos: int).

Use of prototypes

Prototypes methods are meant to be used for the types they are designed for, and they do not try to convert the argument to that type.
String.prototype.charAt.call( 123456, 1 ) will fail instead of returning 2.

Numbers

Numbers are real java numbers, inheriting from Number. Internally, the script engine uses Integer, Long, Double and even BigInteger or BigDecimal. This can affect the result of computations.

new

The new operator works a bit differently from JavaScript to better target Java classes. The syntaxe is:
new <expr>(<args>)
or for arrays:
new <expr>[][<size>]

<expr> is a a simple expr of the form name[.member ...]. A typical use is the following:

const MyClass = Java.type("my.package.MyClass")
var o = new MyClass()

Note that new a.b() doesn't reference the java class a.b, but the member b of the identifier a.

String handling

Supports a subset of ES6 template strings: ${expressions} within a back-ticked string. It does not support tagged strings.

Ex: `My name is ${NAME}`

Dealing with JSON containers (Array and Object)

JsonScript maps the class Object to Java JsonObject and Array Java JsonArray. They are not meant to be generic maps of lists, but to deal with JSON data. To use more generic container, with a regular behavior, use Map (maps to Java LinkedHashMap) or List (maps Java ArrayList).

JsonScript also introduces the notion of a sequence. A sequence is used when querying an Array or an Object returns multiple values.

<<< TODO explain here >>>

Here is how operators work with Array:

  • . or [] When accessing a member of an Array, the runtime browses the array content and accesses the member of each these entry in a sequence.
    When an object or an array is accessed using [] or ., it always returns the value in the maps(s) and never the corresponding function. With one exception: when using the operator . and when the member is immediately followed by a call ():
    • myobject.toString or myobject['toString'] return the toString value, or null
    • myobject.toString() calls the actual toString() method of the container
  • .* or [*] Return all the values of the left part flattenized.
  • .. Search for member through all the tree and return a sequence.
  • Sequence handling.
    When a sequence is deferenced, when used in a expression, it is first dereferenced using the following pattern:
    • An empty sequence generates the null value.
    • A sequence containing one value generates this value
    • A sequence containing multiple values generated an Array with all these values
const a0 = []
const r0 = a0['a'] // Returns null

const a1 = [{ a: '1' }]
const r1 = a1['a'] // Returns '1'

const a2 = [{ a: '1' },	{ a: '2' }]
const r2 = a2['a'] // Returns ['1','2']

Now, there is an ambiguity between the array content and the functions when accessed by name. For both JsonArray & JsonObject, the language distinguishes the functions from the object members when they are called right away:

container.memb    // accesses the member 'memb'of the container
container.func()  // accesses the function 'func' and calls it.  

Exceptions are Java exceptions

JsonScript deals with native exceptions

with() statement

JsonScript supports the with() statement, but its runtime behavior is different: the accessed members must be preceeded by a leading ".", like this:

const anObject = new MyObject()
with(anObject) {
	console.log(.m()); // .m() is eqv to o anObject.m
}  

with() actually sets a context that is similar to the JsonArray

Standard Library

The standard library more or less mimics the standard JavaScript one for the JSON values (JsonObject, JsonArray, Number, Boolean, String, null). It is not a full emulation, but it keeps what makes sense in a non JavaScript environment, while some uncommon functions are not implemented.

console

log & error are implemented. When the first parameter is a message, then it is a Java String format, which is more complete than the JavaScript one.

JSON

parse(obj,reviver)
The reviver function must be null, else it generates an exception

JSON.stringify(obj,replacer,space)
The replacer function must be null, else it generates an exception

Toolbox For Salesforce Developers

Install: https://www.jdeploy.com/~monflabs-jsplayground

Publish:

1- Maven build.

2- Build and deploy package.

npx jdeploy package
npm publish
0.0.4

12 months ago

0.0.3

12 months ago

0.0.2

12 months ago

0.0.1

12 months ago