| Crates.io | typed-jni |
| lib.rs | typed-jni |
| version | 1.1.4 |
| created_at | 2025-10-20 17:45:25.012546+00 |
| updated_at | 2026-01-13 12:48:44.291928+00 |
| description | Type-Safe JNI access for Rust. |
| homepage | https://github.com/Kr328/typed-jni-rs |
| repository | https://github.com/Kr328/typed-jni-rs |
| max_upload_size | |
| id | 1892398 |
| size | 91,533 |
This crate provides Rust bindings for the Java Native Interface (JNI) with typed references.
Assume you have Java classes org.example.Example1 and org.example.Example2 with following declarations:
package org.example;
public class Example1 {
private final String str;
public Example1(String str) {
this.str = str;
}
public void hello() {
System.out.println(str);
nativeHello(str);
}
private native void nativeHello(String str);
private native String getStr();
}
public class Example2 {
private static final Example1 staticExample1 = new Example1("Hello World!!!");
private final Example1 example1;
public Example2(Example1 example1) {
this.example1 = example1;
}
public static void staticHello(int n) {
for (i = 0; i < n; i++) {
staticExample1.hello();
}
}
public void hello(int n) {
for (i = 0; i < n; i++) {
example1.hello();
}
}
}
Firstly, add necessary classes defines in your Rust code.
use typed_jni::define_java_class;
define_java_class!(JavaExample1, "org.example.Example1"); // `Java` prefix of name is not required
define_java_class!(JavaExample2, "org.example.Example2");
Now you can access Java classes in type-safe way.
use std::string::String;
use typed_jni::{
LocalClass, LocalObject, TypedCallExt, TypedClassExt, TypedFieldAccessExt, TypedStringExt, builtin::JavaString, core::JNIEnv,
define_java_class,
};
define_java_class!(JavaExample1, "org.example.Example1");
define_java_class!(JavaExample2, "org.example.Example2");
fn run_jni<'env>(env: &'env JNIEnv<'static>) {
// create Example object
let example1_cls: LocalClass<JavaExample1> = env.typed_find_class().unwrap();
let example1_obj: LocalObject<JavaExample1> = env
.typed_new_object(&example1_cls, (env.typed_new_string("Hello World!"),))
.unwrap();
// call hello method
env.typed_call_method::<(), _, _>(&example1_obj, "hello", ()).unwrap();
// get str field
let str: LocalObject<JavaString> = env.typed_get_field(&example1_obj, "str").unwrap();
let str: String = env.typed_get_string(&str);
// create Example2 object
let example2_cls: LocalClass<JavaExample2> = env.typed_find_class().unwrap();
let example2_obj: LocalObject<JavaExample2> = env.typed_new_object(&example2_cls, (example1_obj,)).unwrap();
// call staticHello method
env.typed_call_method::<(), _, _>(&example2_cls, "staticHello", (3i32,))
.unwrap();
// call hello method
env.typed_call_method::<(), _, _>(&example2_obj, "hello", (3i32,)).unwrap();
// get staticExample1 field
let static_example1: LocalObject<JavaExample1> = env.typed_get_field(&example2_cls, "staticExample1").unwrap();
// get example1 field
let example1: LocalObject<JavaExample1> = env.typed_get_field(&example2_obj, "example1").unwrap();
}
You should define native methods in Rust code with following signature.
use typed_jni::{define_java_class, TrampolineObject, core::JNIEnv, builtin::JavaString, TypedStringExt};
define_java_class!(JavaExample1, "org.example.Example1");
#[unsafe(no_mangle)]
pub extern "system" fn Java_org_example_Example1_nativeHello<'env>(env: &'env JNIEnv, obj: TrampolineObject<'env, JavaExample1>, str: TrampolineObject<'env, JavaString>) {
let str: String = env.typed_get_string(&str);
println!("{}", str);
}
#[unsafe(no_mangle)]
pub extern "system" fn Java_org_example_Example1_getStr<'env>(env: &'env JNIEnv, obj: TrampolineObject<'env, JavaExample1>) -> TrampolineObject<'env, JavaString> {
env.typed_new_string("native string").into_trampoline()
}
Then load it in Java code.
System.loadLibrary("example1");
NOTE: All object reference in native function parameters and return value should be TrampolineObject or
TrampolineClass, it is ffi safe.
std - Enables the use standard library. (default)cache - Enables the use cache for class and member lookups. (default, requires std)