diff --git a/spring-core/src/main/java/org/springframework/aot/hint/RuntimeHints.java b/spring-core/src/main/java/org/springframework/aot/hint/RuntimeHints.java
index 672af1bd28..a64488ac2a 100644
--- a/spring-core/src/main/java/org/springframework/aot/hint/RuntimeHints.java
+++ b/spring-core/src/main/java/org/springframework/aot/hint/RuntimeHints.java
@@ -28,6 +28,7 @@ package org.springframework.aot.hint;
* recorded as well.
*
* @author Stephane Nicoll
+ * @author Janne Valkealahti
* @since 6.0
*/
public class RuntimeHints {
@@ -40,6 +41,8 @@ public class RuntimeHints {
private final ProxyHints proxies = new ProxyHints();
+ private final ReflectionHints jni = new ReflectionHints();
+
/**
* Provide access to reflection-based hints.
@@ -73,4 +76,12 @@ public class RuntimeHints {
return this.proxies;
}
+ /**
+ * Provide access to jni-based hints.
+ * @return jni hints
+ */
+ public ReflectionHints jni() {
+ return this.jni;
+ }
+
}
diff --git a/spring-core/src/main/java/org/springframework/aot/nativex/NativeConfigurationWriter.java b/spring-core/src/main/java/org/springframework/aot/nativex/NativeConfigurationWriter.java
index 192c7c48d0..674602ae65 100644
--- a/spring-core/src/main/java/org/springframework/aot/nativex/NativeConfigurationWriter.java
+++ b/spring-core/src/main/java/org/springframework/aot/nativex/NativeConfigurationWriter.java
@@ -29,6 +29,7 @@ import org.springframework.aot.hint.SerializationHints;
*
* @author Sebastien Deleuze
* @author Stephane Nicoll
+ * @author Janne Valkealahti
* @since 6.0
* @see Native Image Build Configuration
*/
@@ -52,6 +53,9 @@ public abstract class NativeConfigurationWriter {
hints.resources().resourceBundles().findAny().isPresent()) {
writeResourceHints(hints.resources());
}
+ if (hints.jni().typeHints().findAny().isPresent()) {
+ writeJniHints(hints.jni());
+ }
}
/**
@@ -82,4 +86,9 @@ public abstract class NativeConfigurationWriter {
ResourceHintsWriter.INSTANCE.write(writer, hints));
}
+ private void writeJniHints(ReflectionHints hints) {
+ writeTo("jni-config.json", writer ->
+ ReflectionHintsWriter.INSTANCE.write(writer, hints));
+ }
+
}
diff --git a/spring-core/src/main/java/org/springframework/aot/nativex/ReflectionHintsWriter.java b/spring-core/src/main/java/org/springframework/aot/nativex/ReflectionHintsWriter.java
index 454222b866..3e2f220f0a 100644
--- a/spring-core/src/main/java/org/springframework/aot/nativex/ReflectionHintsWriter.java
+++ b/spring-core/src/main/java/org/springframework/aot/nativex/ReflectionHintsWriter.java
@@ -34,12 +34,15 @@ import org.springframework.lang.Nullable;
/**
* Write {@link ReflectionHints} to the JSON output expected by the GraalVM
- * {@code native-image} compiler, typically named {@code reflect-config.json}.
+ * {@code native-image} compiler, typically named {@code reflect-config.json}
+ * or {@code jni-config.json}.
*
* @author Sebastien Deleuze
* @author Stephane Nicoll
+ * @author Janne Valkealahti
* @since 6.0
* @see Reflection Use in Native Images
+ * @see Java Native Interface (JNI) in Native Image
* @see Native Image Build Configuration
*/
class ReflectionHintsWriter {
diff --git a/spring-core/src/test/java/org/springframework/aot/nativex/FileNativeConfigurationWriterTests.java b/spring-core/src/test/java/org/springframework/aot/nativex/FileNativeConfigurationWriterTests.java
index 79537eb4f7..6f297cb3f8 100644
--- a/spring-core/src/test/java/org/springframework/aot/nativex/FileNativeConfigurationWriterTests.java
+++ b/spring-core/src/test/java/org/springframework/aot/nativex/FileNativeConfigurationWriterTests.java
@@ -49,6 +49,7 @@ import static org.assertj.core.api.Assertions.assertThat;
* Tests for {@link FileNativeConfigurationWriter}.
*
* @author Sebastien Deleuze
+ * @author Janne Valkealahti
*/
public class FileNativeConfigurationWriterTests {
@@ -149,6 +150,23 @@ public class FileNativeConfigurationWriterTests {
]""", "reflect-config.json");
}
+ @Test
+ void jniConfig() throws IOException, JSONException {
+ // same format as reflection so just test basic file generation
+ FileNativeConfigurationWriter generator = new FileNativeConfigurationWriter(tempDir);
+ RuntimeHints hints = new RuntimeHints();
+ ReflectionHints jniHints = hints.jni();
+ jniHints.registerType(StringDecoder.class, builder -> builder.onReachableType(String.class));
+ generator.write(hints);
+ assertEquals("""
+ [
+ {
+ "name": "org.springframework.core.codec.StringDecoder",
+ "condition": { "typeReachable": "java.lang.String" }
+ }
+ ]""", "jni-config.json");
+ }
+
@Test
void resourceConfig() throws IOException, JSONException {
FileNativeConfigurationWriter generator = new FileNativeConfigurationWriter(tempDir);