When trying to use Quarkus Qute Typesafe Templates with Kotlin (converting the static class into an object as per the code below), I run into an UnsatisfiedLinkError at runtime.
The code at issue:
@Path("/subscriber")
@Produces(MediaType.TEXT_HTML)
@Consumes(MediaType.TEXT_HTML)
class SubscriberResource {
@CheckedTemplate
object Templates {
external fun new(): TemplateInstance
}
@GET
fun get(): TemplateInstance {
return Templates.new()
}
}
with the template being available in resources/templates/SubscriberResource/new.html
.
The project builds fine, but when I attempt to open the view, I get the exception given below.
I've also tried making the object a companion
object, but it didn't help.
Any idea what's missing?
java.lang.UnsatisfiedLinkError: 'io.quarkus.qute.TemplateInstance com.app.subscriber.SubscriberResource$Templates.new()' at com.app.subscriber.SubscriberResource$Templates.new(Native Method) at com.app.subscriber.SubscriberResource.get(SubscriberResource.kt:23) at com.app.subscriber.SubscriberResource_Subclass.get$$superaccessor1(SubscriberResource_Subclass.zig:189) at com.app.subscriber.SubscriberResource_Subclass$$function$$6.apply(SubscriberResource_Subclass$$function$$6.zig:29) at io.quarkus.arc.impl.AroundInvokeInvocationContext.proceed(AroundInvokeInvocationContext.java:54) at io.quarkus.arc.runtime.devconsole.InvocationInterceptor.proceed(InvocationInterceptor.java:63) at io.quarkus.arc.runtime.devconsole.InvocationInterceptor.monitor(InvocationInterceptor.java:49) at io.quarkus.arc.runtime.devconsole.InvocationInterceptor_Bean.intercept(InvocationInterceptor_Bean.zig:521) at io.quarkus.arc.impl.InterceptorInvocation.invoke(InterceptorInvocation.java:41) at io.quarkus.arc.impl.AroundInvokeInvocationContext.perform(AroundInvokeInvocationContext.java:41) at io.quarkus.arc.impl.InvocationContexts.performAroundInvoke(InvocationContexts.java:32) at com.app.subscriber.SubscriberResource_Subclass.get(SubscriberResource_Subclass.zig:147) at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method) at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62) at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) at java.base/java.lang.reflect.Method.invoke(Method.java:566) at org.jboss.resteasy.core.MethodInjectorImpl.invoke(MethodInjectorImpl.java:170) at org.jboss.resteasy.core.MethodInjectorImpl.invoke(MethodInjectorImpl.java:130) at org.jboss.resteasy.core.ResourceMethodInvoker.internalInvokeOnTarget(ResourceMethodInvoker.java:643) at org.jboss.resteasy.core.ResourceMethodInvoker.invokeOnTargetAfterFilter(ResourceMethodInvoker.java:507) at org.jboss.resteasy.core.ResourceMethodInvoker.lambda$invokeOnTarget$2(ResourceMethodInvoker.java:457) at org.jboss.resteasy.core.interception.jaxrs.PreMatchContainerRequestContext.filter(PreMatchContainerRequestContext.java:364) at org.jboss.resteasy.core.ResourceMethodInvoker.invokeOnTarget(ResourceMethodInvoker.java:459) at org.jboss.resteasy.core.ResourceMethodInvoker.invoke(ResourceMethodInvoker.java:419) at org.jboss.resteasy.core.ResourceMethodInvoker.invoke(ResourceMethodInvoker.java:393) at org.jboss.resteasy.core.ResourceMethodInvoker.invoke(ResourceMethodInvoker.java:68) at org.jboss.resteasy.core.SynchronousDispatcher.invoke(SynchronousDispatcher.java:492) at org.jboss.resteasy.core.SynchronousDispatcher.lambda$invoke$4(SynchronousDispatcher.java:261) at org.jboss.resteasy.core.SynchronousDispatcher.lambda$preprocess$0(SynchronousDispatcher.java:161) at org.jboss.resteasy.core.interception.jaxrs.PreMatchContainerRequestContext.filter(PreMatchContainerRequestContext.java:364) at org.jboss.resteasy.core.SynchronousDispatcher.preprocess(SynchronousDispatcher.java:164) at org.jboss.resteasy.core.SynchronousDispatcher.invoke(SynchronousDispatcher.java:247) at io.quarkus.resteasy.runtime.standalone.RequestDispatcher.service(RequestDispatcher.java:73) at io.quarkus.resteasy.runtime.standalone.VertxRequestHandler.dispatch(VertxRequestHandler.java:138) at io.quarkus.resteasy.runtime.standalone.VertxRequestHandler.access$000(VertxRequestHandler.java:41) at io.quarkus.resteasy.runtime.standalone.VertxRequestHandler$1.run(VertxRequestHandler.java:93) at io.quarkus.runtime.CleanableExecutor$CleaningRunnable.run(CleanableExecutor.java:231) at java.base/java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:515) at java.base/java.util.concurrent.FutureTask.run(FutureTask.java:264) at org.jboss.threads.EnhancedQueueExecutor$Task.run(EnhancedQueueExecutor.java:2415) at org.jboss.threads.EnhancedQueueExecutor$ThreadBody.run(EnhancedQueueExecutor.java:1452) at org.jboss.threads.DelegatingRunnable.run(DelegatingRunnable.java:29) at org.jboss.threads.ThreadLocalResettingRunnable.run(ThreadLocalResettingRunnable.java:29) at java.base/java.lang.Thread.run(Thread.java:834) at org.jboss.threads.JBossThread.run(JBossThread.java:501) Resulted in: org.jboss.resteasy.spi.UnhandledException: java.lang.UnsatisfiedLinkError: 'io.quarkus.qute.TemplateInstance com.app.subscriber.SubscriberResource$Templates.new()' at org.jboss.resteasy.core.ExceptionHandler.handleApplicationException(ExceptionHandler.java:106) at org.jboss.resteasy.core.ExceptionHandler.handleException(ExceptionHandler.java:372) at org.jboss.resteasy.core.SynchronousDispatcher.writeException(SynchronousDispatcher.java:218) at org.jboss.resteasy.core.SynchronousDispatcher.invoke(SynchronousDispatcher.java:519) ... 18 more
Finally figured out a solution, adding @JvmStatic
to the external object function solves it:
@CheckedTemplate
object Templates {
@JvmStatic
external fun new(): TemplateInstance
}