Nashorn compatibility with Java 1.8 to 15? - javascript

I need my software which uses the Nashorn JavaScript engine to be compatible with Java 1.8 upwards.
If I use the one bundled with the JDK it will not work on Java >= 15. If I use the standalone Nashorn it will not be compatible with Java < 15.
Is there a way to keep compatibility? I have already thought about reflection but there might be more efficient ways.

Nashorn maintainer here. It should be possible to compile standalone Nashorn from sources for Java 11. I'm pretty sure we can't go below that, unfortunately. Are you using its API directly? In that case you unfortunately have a mismatch between built-in Nashorn's package names and the standalone version. If you can only rely on javax.script.* API then it should be possible to use both.
I want to understand your use case a bit better and help you arrive at a solution.

As you have noticed, Nashorn was deprecated in JEP 335 (JDK Enhancement Proposal) in Java 11 and it has subsequently been removed in JEP 372 that was delivered as part of Java 15. The motivation for the removal is
With the rapid pace at which ECMAScript language constructs, along with APIs, are adapted and modified, we have found Nashorn challenging to maintain.
Consequently, it will not be an option in the future. Instead I suggest that you take a look at options like GraalVM if you are looking for alternatives. As stated in the introduction:
It is designed for applications written in Java, JavaScript, LLVM-based languages such as C and C++, and other dynamic languages. It removes the isolation between programming languages and enables interoperability in a shared runtime.

If you cannot simply not distribute a standalone Nashorn JAR for JDKs <15, you should be able to build a multi-release version of it instead.
The root level should provide nothing, and then have all the actual classes in META-INF/versions/15/
Documentation: JAR Specification: Multi-release JAR files

Related

The benefits of React-Native JavaScriptCore

Definitely, all of us know about powerful JavaScript engine, So why in React Native is used a different engine that name is JavaScriptCore.
The JavaScriptCore does not support some ES6 features like below function:
Array.prototype.flatten
What is benefits of JavaScriptCore to V8? Why the Facebook developers didn't use V8?
V8 does not run on iOS, because Apple does not allow third-party apps to generate code at runtime (a.k.a. "JIT-compiling"), which V8 heavily relies on for performance (*). JavaScriptCore, being made by Apple, is allowed to run (and JIT-compile code) on iOS. Since React Native's purpose is cross-platform development, this is a strong argument.
That said, Array.prototype.flatten is not an ES6 feature. It is currently a "stage 3 proposal", meaning it will probably soon become an official part of JavaScript -- maybe ES2019 ("ES10" in the old naming scheme) or so. Also, it has been renamed to Array.prototype.flat due to web compatibility issues with the name .flatten. JavaScript engines have started to implement it; according to MDN the latest version of Safari/JavaScriptCore already support it, so it's probably only a matter of time until support arrives in React Native too.
(*) There is an ongoing effort to build a version of V8 that avoids all runtime code generation, trading a lot of performance for the ability to run anywhere, but it's not available yet.

Array.filter function in serverside Javascript

I would like to filter an array in my XPage with serverside Javascript. Unfortunately I get the following error:
Error calling method 'filter(Function)' on an object of type 'Array [JavaScript Object]'
I have an Array of Strings like ["elem1","elem2","elem3"]
I call the function like this:
list.filter(function(){
});
Is there any reason why this error happens? Does this function even exist in ssjs?
This question is not duplicate since it is not clear that Xpages/Lotus Notes runs Rhino in background.
It sounds like whatever server-side JavaScript environment you're using doesn't support ES5 features (that's features from the 5th edition specification from December 2009).
You can use a polyfill for that and other things that were added to Array, see MDN, but beware: If ES5 features aren't supported, it's impossible to add things to Array.prototype without making them enumerable, meaning any code (mis)using for-in to loop through arrays will be affected.
There is Rhino behind XPages. And this SO topic
No Array.filter() in Rhino? says, it is out of date.
Edit:
No, it is not. Years ago I read somewhere about it. Now it seems it was not true. According to comment by Dan Sickles (quoting Philippe Riand?) here:
It runs on the server jvm and uses javascript as the application
language. For licensing reasons, IBM wrote their own jvm javascript
engine instead of using Rhino. With Rhino shipping in java 6, they
should be able to ship it in Designer 8.5 (or later). The licensing
problems may have been around the extensions like #Formulas and type
declarations. Classes, modules/namespaces and type declarations are
coming in javascript 2 and even google is helping to get that
implemented in Rhino. I'd hate to see a non-standard, javascript
engine underlying the coolest web development technology in Domino.
Speaking of Rhino, the "most important new feature that is not as
certain to be in 8.5 as XPages" uses Rhino and other jvm scripting
languages on the client. If this makes it into the product, two years
from now most new Notes applications will be written in neither
Lotusscript nor Java. I'll leave it at that.
In fact, there are few topics how to use Rhino in XPages, so with newest Rhino version your code would work. Anyway, my advice is to use Java calls.

Do compilers for javascript differ from web browser to web browser

So I am asking does each web browser have there own compiler example IE compiles Javascript from a website and generates sequence A of byte code .
On the other hand, google chrome compiles the same Javascript from the same website and generates sequence B .
I am wondering this because if that is the case would it be beneficial to run the compiler on the Javascript and upload the generated byte code to the website rather than the Javascript itself. And send different byte code based on each browser.
Or are there some other limitations.
As others have pointed out, there are different ECMAScript engines and some of them use a JIT (Just-In-Time) compiler while some others use runtime interpreters, being the former the preferred option for most browsers nowadays as it gives some performance benefits over the latter option.
You can see another question about this on: https://softwareengineering.stackexchange.com/questions/138521/is-javascript-interpreted-by-design
For example, V8 is the JavaScript engine used in Google Chrome, node.js and can also be embedded into C++ applications.
About your idea of sending compiled or precompiled code to the client instead of the raw JS, there are some projects working on something similar:
Asm.js consists of a strict subset of JavaScript, into which code written in statically-typed languages with manual memory management (such as C) is translated by a source-to-source compiler such as Emscripten (based on LLVM). Performance is improved by limiting language features to those amenable to ahead-of-time optimization and other performance improvements.
The important fact about Asm.js is that existing JavaScript engines do work quite well with its style of code, so you can start using it right now! But the code it produces is still (a subset of) the JS we know but written in some way that helps JS engines to run it faster:
Of course, there are also a lot of restrictions about what you can do with it, as it is mainly oriented to work with just numbers. See http://ejohn.org/blog/asmjs-javascript-compile-target/
Real support for Asm.js is still a limitation, so you can't use things like "use asm" and although you can run Asm.js code on today browsers and get some performance improvements, it won't be as good as it could be in browsers that could optimize Asm.js code. However, we may start having that and some other improvements in the (hope that near) future. See https://blog.mozilla.org/research/2015/02/23/the-emterpreter-run-code-before-it-can-be-parsed/
Meanwhile, and for a more general purpose JS that needs to work with more than just numbers, you can use Google Closure Compiler. I would recommend that you take a look at the FAQ first, and then you could start playing with it in the online tool.
There are several JavaScript (or rather ECMAScript) implementations in wide use, and while in theory there are standards, most widely used one being ES5 (ECMAScript 5) - yes, not everything in all browsers is properly, consistently implemented (I'm looking at you, old IE).
Here's nice compatibility table for ES5 (the one you're writing in today): http://kangax.github.io/compat-table/es5/
And here's same thing for shiny-new ES6: http://kangax.github.io/compat-table/es6/
Note the disclaimer at the top of these tables:
Please note that some of these tests represent existence, not functionality or full conformance.
Also, on the issue of whether JavaScript is compiled or interpreted language: it is definitely interpreted language - at least originally. But most common JavaScript engines in use today implement JIT (Just-In-Time compiler), translating much of JavaScript to byte or machine code before executing it (ergo - compiling).
Most widely used (and most performant as well) of these engines is V8, used by WebKit (and therefore present in Chrome, Safari, Opera, ... - Node.JS is using it as well). Read more about V8 and its JIT implementation: How the V8 engine works?
Yes, each browser has its own implementation of an ECMAScript engine, most commonly implementing/supporting ECMA-262, commonly known as JavaScript. While there are several large related families of browser engines such as Webkit, each engine further can have its own JavaScript engine. For example, as many have pointed out, Google use the V8 engine. Because these engines each do things a little differently, there is no one set of code that is promised to be deterministic across them, the way say Java code will run the same on any machine that supports the JVM.
Inherently, JavaScript is not compiled like a traditional language such a Java or C/C++. This is why, without the help of a 3rd party program, you cannot find non-syntax errors in your JavaScript code until that code runs. ECMAScript is an interpreted language.
Now, this is the tricky part. Most modern JavaScript engines do in fact compile JavaScript, often to another language (also known as Source-to-Source compiling or transpiling) such as C, to perform performance optimizations on it. Of course, at some point, all code gets compiled into byte code.
Your best bet for writing JavaScript that will work on all major browsers is to use core/standard features. For example, this means passing timestamp string in the form of "yyyy/mm/dd" instead of "yyy-mm-dd" when using new Date() since Firefox does not support the latter format - the Chrome developers simply added it to be nice to you. IE is notorious for handling certain non-standard features differently. I'm a big fan of http://caniuse.com/ to help with this.
Nowadays most javascript engines are JIT compilers. More here: What does a just-in-time (JIT) compiler do?
So yes, javascript is compiled (not interpreted), and most major browsers do it differently.

SpiderMonkey vs JavaScriptCore vs?

I have a C++ desktop application (written in wxWidgets) and I want to add support for some scripting language.
Scripting would mostly be used for run-time conversions of strings, numbers and dates by user supplied JavaScript code.
I'd like to use JavaScript because it is widely used and everyone is familiar with the syntax.
Googling around, it seems I have two options:
SpiderMonkey from Mozilla
JavaScriptCore from WebKit
Has anyone tried those? Which one would be easier to set up?
Do you know of some other implementation that is better for my needs?
BTW, I target Windows and Linux platforms.
There is also Google's V8 JavaScript engine, builds nicely on Linux, embedding API seems quite straightforward too: (Compared to SpiderMonkey's, never looked at the JavaScriptCore API)
http://code.google.com/apis/v8/get_started.html
Of course, you could also use Lua, which not only is designed specifically for this, it's vastly faster than any JS.
Also, it's has well-designed semantics, a very minimal core, simple C API, great portability, a very mature JIT, the most helpful online community I've seen, etc...
JavaScriptCore has a stable C API (and ABI), and has been available (and used as) a standard system framework on macos.
[edit: oh, and it works on linux and windows as a standalone library, although i believe only debian distributes it as such]

Javascript interpreter to replace Python

In terms of quick dynamically typed languages, I'm really starting to like Javascript, as I use it a lot for web projects, especially because it uses the same syntax as Actionscript (flash).
It would be an ideal language for shell scripting, making it easier to move code from the front and back end of a site, and less of the strange syntax of python.
Is there a good, javascript interpreter that is easy to install (I know there's one based on java, but that would mean installing all the java stuff to use),
I personally use SpiderMonkey, but here's an extensive list of ECMAScript shells
Example spidermonkey install and use on Ubuntu:
$ sudo apt-get install spidermonkey
$ js myfile.js
output
$ js
js> var f = function(){};
js> f();
Of course, in Windows, the JavaScript interpreter is shipped with the OS.
Just run cscript or wscript against any .js file.
There are four big javascript interpreters currently. V8, Squirrelfish, Spidermonkey and Rhino. I think more important than performance is how well it integrates into existing infrastructure, and I guess Rhino with its bridge to Java wins here.
Try jslibs, a scripting-focused standalone JS runtime and set of libraries that uses SpiderMonkey (the Gecko JS engine).
On the 'easy to translate' theme, there's also Lua.
It's somewhat similar to Javascript, but more 'orthogonal' (closer to functional roots).
The heavy orientation to 'pure' programming theory has made it really small and fast. It's the fastest scripting language around, and the JIT runs circles around the new JavaScript JITs that are starting to appear.
Also, since it was originally thought as an extension language, it has a very nice and clean interface to C, making it very easy to create bindings to any C library you might want to access.
Google's V8 can be used as a standalone interpreter. Configuring with scons sample=shell will build an executable named shell, that can be called like so: ./shell file.js.
You'll need some server-side JavaScript interpreter. Check out the following blog post. Something such as Rhino might be useful for you.
You might try toying around with SquirrelFish or v8, both should be runnable on the command line.
FYI, there is a built-in one already on modern windows platforms. You need to use JScript, but it's close enough. Same environment also allows for VBScript. To run a program you can execute something like:
cscript foo.js
The windows system API is a bit weird and frustrating if you expect the same flexibility as with basic JS objects, but they do have thorough documentation if you can handle digging through the MSDN pages and seeing all the examples in VBScript.
Not sure what's available for Linux/Mac in terms of js shell.
Well, for safety reasons, javascript had not been provided with file access right by design. So as a scripting language, it's a bit limited.
But still, if you really want to, spider monkey is your best option. Here is a tuto :
http://developer.mozilla.org/en/Introduction_to_the_JavaScript_shell
Node.JS. It's great. Has many modules. you can do all your file scripting with Node.
In my years I've found most Javascript developers find it quite easy to transfer over to PHP and vice versa - it isn't a direct answer to your question, although if you're working in ActionScript and JavaScript then you're best to stick with something like PHP (if you're not willing to move to Java, and stick with the ECMA base)

Categories