Getting Started with Oracle GraalVM Enterprise 19

Here you will find information about downloading and installing GraalVM Enterprise, running basic applications with it, and adding support for its accompanying features. Further, you will learn about the polyglot capabilities of GraalVM Enterprise and see how to build platform-specific native executables of JVM-based applications.

If you are new to GraalVM Enterprise or have little experience using it, we recommend starting with the GraalVM Enterprise Overview page. There you will find information about GraalVM Enterprise’s architecture, the distributions available, supported platforms, licensing and support, core and additional features, and much more.

If you have GraalVM Enterprise already installed and have experience using it, you can skip this getting started guide and proceed to the in-depth Reference Manuals.

Download GraalVM Enterprise

You can get Oracle GraalVM Enterprise Edition by:

Install

Getting GraalVM Enterprise installed and ready-to-go should take a few minutes. Choose your operating system and proceed to the installation steps for your specific platform:

Start Running Applications

For demonstration purposes here, we will use GraalVM Enterprise based on Java 8.

The core distribution of GraalVM Enterprise includes the JVM, the GraalVM compiler, the LLVM runtime, and Node.js JavaScript runtime. Having downloaded and installed GraalVM Enterprise, you can already run Java, Node.js, JavaScript, and LLVM-based applications.

GraalVM Enterprise’s /bin directory is similar to that of a standard JDK, but includes a set of additional launchers:

Check the versions of the runtimes provided by default:

java -version
java -version
java version "1.8.0_271"
Java(TM) SE Runtime Environment (build 1.8.0_271-b09)
Java HotSpot(TM) 64-Bit GraalVM EE 19.3.4 (build 25.271-b09-jvmci-19.3-b18, mixed mode)

node -v
v12.14.0

lli --version
LLVM 10.0.0 (GraalVM EE Native 19.3.4)

The executables of all language runtimes in GraalVM Enterprise emulate the behavior of the languages’ default runtimes. Further below you will find information on how to run other optionally available languges (Ruby, R, Python, and WebAssembly) with GraalVM Enterprise.

Runtime for Different Languages

Java

The java launcher runs the JVM with the GraalVM Enterprise default compiler - the GraalVM compiler. Take a look at this typical HelloWorld class:

public class HelloWorld {
  public static void main(String[] args) {
    System.out.println("Hello, World!");
  }
}

Run the following commands to compile this class to bytecode and then execute it:

javac HelloWorld.java
java HelloWorld
Hello World!

For more information on the GraalVM compiler, go to Compiler. For more extensive documentation on running Java, proceed to JVM Languages.

JavaScript and Node.js

GraalVM Enterprise can execute plain JavaScript code, both in REPL mode and by executing script files directly:

js
> 1 + 2
3

GraalVM Enterprise also supports running Node.js applications. More than 100,000 npm packages are regularly tested and are compatible with GraalVM Enterprise, including modules like express, react, async, request, browserify, grunt, mocha, and underscore. To install a Node.js module, use the npm executable from the /bin folder, provided by default. The npm command is equivalent to the default Node.js command and supports all Node.js APIs.

Install the colors and ansispan modules using npm install. After the modules are installed, you can use them from your application.

npm install colors ansispan

Use the following code snippet and save it as the app.js file in the same directory where you installed the Node.js modules:

const http = require("http");
const span = require("ansispan");
require("colors");

http.createServer(function (request, response) {
    response.writeHead(200, {"Content-Type": "text/html"});
    response.end(span("Hello Graal.js!".green));
}).listen(8000, function() { console.log("Graal.js server running at http://127.0.0.1:8000/".red); });

setTimeout(function() { console.log("DONE!"); process.exit(); }, 2000);

Run app.js on GraalVM Enterprise using the node command:

node app.js

For more detailed documentation and information on compatibility with Node.js, proceed to JavaScript and Node.js.

LLVM Languages

The GraalVM Enterprise LLVM runtime can execute C/C++, Rust, and other programming language that can be compiled to LLVM bitcode. A native program has to be compiled to LLVM bitcode using an LLVM frontend such as clang. The C/C++ code can be compiled to LLVM bitcode using clang shipped with GraalVM Enterprise via a prebuilt LLVM toolchain.

To set up the LLVM toolchain support:

  1. Install the plugin:
    gu install llvm-toolchain
    
  2. Export the LLVM_TOOLCHAIN variable to the toolchain location for convenience:
    export LLVM_TOOLCHAIN=$(lli --print-toolchain-path)
    

As an example, put this C code into a file named hello.c:

#include <stdio.h>

int main() {
    printf("Hello from GraalVM!\n");
    return 0;
}

Then compile hello.c to an executable hello with embedded LLVM bitcode, and run it as follows:

$LLVM_TOOLCHAIN/clang hello.c -o hello
lli hello

For in-depth documentation and more examples of running LLVM bitcode on GraalVM Enterprise, go to LLVM Languages.

Python

With GraalVM Enterprise you can run Python applications in the Python 3 runtime environment. The support is not available by default, but you can quickly add it to GraalVM using the GraalVM Updater tool:

gu install python

Once it is installed, you can run Python programs:

graalpython
...
>>> 1 + 2
3
>>> exit()

More examples and additional information on Python support in GraalVM can be found in the Python reference manual.

Ruby

GraalVM Enterprise provides a high-performance Ruby runtime environment including the gem command that allows you to interact with RubyGems, Ruby Bundler, and much more. The Ruby runtime is not available by default in GraalVM, but can be easily added using the GraalVM Updater tool:

gu install ruby

Once it is installed, Ruby launchers like ruby, gem, irb, rake, rdoc, and ri become available to run Ruby programs:

ruby [options] program.rb

GraalVM Ruby runtime environment uses the same options as the standard implementation of Ruby, with some additions. For example:

gem install chunky_png
ruby -r chunky_png -e "puts ChunkyPNG::Color.to_hex(ChunkyPNG::Color('mintcream @ 0.5'))"
#f5fffa80

More examples and in-depth documentation can be found in the Ruby reference manual.

R

GraalVM Enterprise provides a GNU-compatible environment to run R programs directly or in the REPL mode. Although the R language support is not available by default, you can add it to GraalVM Enterprise using the GraalVM Updater tool:

gu install R

Once it is installed, you can execute R scripts and use the R REPL:

R
R version 3.6.1 (FastR)
...

> 1 + 1
[1] 2

More examples and in-depth documentation can be found in the R reference manual.

Native Images

With GraalVM Enterprise you can compile Java bytecode into a platform-specific, self-contained, native executable - a native image - to achieve faster startup and a smaller footprint for your application. The Native Image functionality is not available by default, but can be easily installed with the GraalVM Updater tool:

gu install native-image

The HelloWorld example from above is used here to demonstrate how to generate a native image:

public class HelloWorld {
  public static void main(String[] args) {
    System.out.println("Hello, World!");
  }
}

Compile HelloWorld.java to bytecode and then build a native image:

javac HelloWorld.java
native-image HelloWorld

The last command generates an executable file named helloworld in the current working directory. Invoking it executes the natively compiled code of the HelloWorld class as follows:

./helloworld
Hello, World!

More detailed documentation on this innovative technology is available in the Native Image reference manual.

Polyglot Capabilities of Native Images

GraalVM Enterprise makes it possible to use polyglot capabilities when building native images. Take this example of a JSON pretty-printer Java program that embeds some JavaScript code:

import java.io.*;
import java.util.stream.*;
import org.graalvm.polyglot.*;

public class PrettyPrintJSON {
  public static void main(String[] args) throws java.io.IOException {
    BufferedReader reader = new BufferedReader(new InputStreamReader(System.in));
    String input = reader.lines()
    .collect(Collectors.joining(System.lineSeparator()));
    try (Context context = Context.create("js")) {
      Value parse = context.eval("js", "JSON.parse");
      Value stringify = context.eval("js", "JSON.stringify");
      Value result = stringify.execute(parse.execute(input), null, 2);
      System.out.println(result.asString());
    }
  }
}

Compile it and build a native image for it. The --language:js argument ensures that JavaScript is available in the generated image:

javac PrettyPrintJSON.java
native-image --language:js --initialize-at-build-time PrettyPrintJSON

The native image generatation will take several minutes as it does not just build the PrettyPrintJSON class, but also builds JavaScript. Additionally, the image building requires large amounts of physical memory, especially if you build an image with the Truffle language implementation framework included, which is the case here.

The resulting executable can now perform JSON pretty-printing:

./prettyprintjson <<EOF
{"GraalVM":{"description":"Language Abstraction Platform","supports":["combining languages","embedding languages","creating native images"],"languages": ["Java","JavaScript","Node.js", "Python", "Ruby","R","LLVM"]}}
EOF

Here is the JSON output from the native executable:

{
  "GraalVM": {
    "description": "Language Abstraction Platform",
    "supports": [
      "combining languages",
      "embedding languages",
      "creating native images"
    ],
    "languages": [
      "Java",
      "JavaScript",
      "Node.js",
      "Python",
      "Ruby",
      "R",
      "LLVM"
    ]
  }
}

The native image runs much faster than running the same code on the JVM directly:

time bin/java PrettyPrintJSON < test.json > /dev/null
real	0m1.101s
user	0m2.471s
sys	0m0.237s

time ./prettyprintjson < test.json > /dev/null
real	0m0.037s
user	0m0.015s
sys	0m0.016s

Combine Languages

GraalVM Enterprise allows you to call one programming language into another and exchange data between them. To enable interoperability, GraalVM Enterprise provides the --polyglot flag.

For example, running js --jvm --polyglot example.js executes example.js in a polyglot context. If the program calls any code in other supported languages, GraalVM Enterprise executes that code in the same runtime as the example.js application. For more information on running polyglot applications, see Polyglot Programming.