java_interop library
Call Java from pure Dart over JNI, using only dart:ffi.
Boots a JVM in-process (or attaches to the one this process already has), loads jars from a class path, and calls constructors, methods, fields and arrays with full primitive coverage. Java throwables surface as Dart JavaExceptions.
final jvm = Jvm.startOrAttach(classPath: ['path/to/your.jar']);
final greeter = JavaClass.forName(jvm, 'com.nfeflash.example.Greeter');
final instance = greeter.newInstance('(Ljava/lang/String;)V', ['Dart']);
print(instance.call('greet', '()Ljava/lang/String;')); // Hello, Dart!
print(greeter.callStatic('add', '(II)I', [2, 40])); // 42
instance.release();
greeter.release();
There are two layers. JavaClass / JavaObject / JavaArray read the
signature string and dispatch, convert Dart arguments — a String to a
jstring, a List to a Java array, a number to its wrapper — and release
the temporaries that makes; they also cache the member ids they resolve.
Use these.
Underneath, extensions on Jvm (JvmClasses, JvmCalls, JvmFields,
JvmArrays, JvmStrings) mirror the JNI C API one-to-one for the cases the
high-level layer does not cover, and Jvm.fnSlot is the escape hatch for
JNI functions this binding does not wrap at all.
One JVM per process.
JNI_CreateJavaVMmay be called once, and HotSpot cannot start another after Jvm.destroy. Jvm.startOrAttach therefore reuses an existing VM when it finds one — which is what makes this work underdart test, where every suite is a separate isolate in a shared process.
Classes
- JavaArray
- A Java array of elementDescriptor elements.
- JavaClass
- A resolved Java class.
- JavaField
-
A parsed Java field declaration:
int count,static String NAME. - JavaMethod
- A parsed Java method declaration: the name, when one was given, and the signature.
- JavaObject
- An instance of a Java class.
- JavaRef
- A handle to a Java object.
- JavaWrapper
-
One of the eight
java.langprimitive wrapper classes. - JniFn
-
Slots in
struct JNINativeInterface_, reached throughJNIEnv*. - JniResult
-
Return codes from
JNI_CreateJavaVM,GetEnvand friends. - JniSignature
- A parsed JNI method signature.
- JniType
-
The eight JNI primitive descriptors, plus
void. - JniVersion
-
JNI_VERSION_1_6from jni.h — the lowest version that supports everything bound here, so JniVersion.v1_6 is what JniVmFn.getEnv asks for. - JniVmFn
-
Slots in
struct JNIInvokeInterface_, reached throughJavaVM*. - JSig
- A Java method signature, built from JTypes.
- JType
- A Java type, as the JNI descriptor that denotes it.
- JValue
-
A single JNI argument, staged as the raw 64 bits of its
jvalueslot. - Jvm
- An embedded JVM.
- LibjvmSearch
- Where defaultLibjvmPath looked, in order, and what it found.
Enums
- JavaRefKind
- Whether a reference is local (thread- and frame-scoped) or global (valid until explicitly deleted, on any thread).
Extensions
- JvmArrays on Jvm
- Array creation and access.
- JvmBoxing on Jvm
- Boxing and unboxing primitives.
- JvmCalls on Jvm
- Invoking constructors and methods.
- JvmClasses on Jvm
- Looking up classes and their members.
- JvmFields on Jvm
- Field access.
- JvmLocalFrames on Jvm
- Scoped local-reference management.
- JvmStrings on Jvm
- String conversion.
Properties
- classPathSeparator → String
-
The class-path list separator:
;on Windows,:elsewhere.no setter
Functions
-
defaultLibjvmPath(
{Map< String, String> ? environment}) → String -
The path to
libjvmfor the current platform. -
doubleFromBits(
int bits) → double -
Reinterprets
bitsas ajdouble. -
floatFromBits(
int bits) → double -
Reinterprets the low 32 bits of
bitsas ajfloat. -
jsig(
String declaration) → String - The JNI descriptor for a Java method declaration.
-
jtype(
String typeName) → String - The JNI descriptor for a Java type, as written in source.
-
libjvmUnder(
String javaHome) → String -
The platform-specific location of
libjvmunder a JDK home. -
searchLibjvm(
{Map< String, String> ? environment}) → LibjvmSearch -
Searches for
libjvmwithout throwing, reporting every candidate tried.
Exceptions / Errors
- JavaException
- A Java throwable that crossed into Dart.
- JniError
- Thrown when the JNI layer itself cannot proceed.
- JniLookupError
- Thrown when a class, method or field cannot be resolved.