Я пытаюсь вызвать нативную функцию JNI из моего веб-приложения.В прошлом это всегда работало, но мне пришлось изменить способ работы, потому что мы добавляем дополнительное веб-приложение, которое также использует ту же динамическую библиотеку.К сожалению, библиотека не может быть загружена в двух отдельных загрузчиках классов.
Для достижения этой цели я загрузил библиотеку в общий загрузчик классов Tomcat 8.Я использую этот ответ в качестве шаблона.Я считаю, что у меня есть веские доказательства того, что это действительно работает.Я использую этот фрагмент , чтобы проверить, загружены ли мои библиотеки, и посмотреть, в какой загрузчик классов.
Classloader: java.net.URLClassLoader@26b418
Loaded:
C:\Program Files (x86)\Java\jdk1.8.0_202\jre\bin\zip.dll
C:\Program Files (x86)\Java\jdk1.8.0_202\jre\bin\management.dll
C:\Program Files (x86)\Java\jdk1.8.0_202\jre\bin\net.dll
C:\Program Files (x86)\Java\jdk1.8.0_202\jre\bin\nio.dll
C:\Program Files (x86)\Java\jdk1.8.0_202\jre\bin\sunec.dll
C:\Program Files (x86)\Java\jdk1.8.0_202\jre\bin\sunmscapi.dll
C:\Repositories\binaries\build\release\myAppJni.dll
Classloader: ParallelWebappClassLoader
context: myApp-display
delegate: false
----------> Parent Classloader:
java.net.URLClassLoader@26b418
C:\Program Files (x86)\Java\jdk1.8.0_202\jre\bin\zip.dll
C:\Program Files (x86)\Java\jdk1.8.0_202\jre\bin\management.dll
C:\Program Files (x86)\Java\jdk1.8.0_202\jre\bin\net.dll
C:\Program Files (x86)\Java\jdk1.8.0_202\jre\bin\nio.dll
C:\Program Files (x86)\Java\jdk1.8.0_202\jre\bin\sunec.dll
C:\Program Files (x86)\Java\jdk1.8.0_202\jre\bin\sunmscapi.dll
C:\Repositories\binaries\build\release\myAppJni.dll
Это заставляет меня поверить, что моя JNI-DLL действительно загружена во всемприложение, и что оно должно быть доступно для веб-приложения и других библиотек, которые я использую как зависимости.
Однако, когда я пытаюсь это сделать.Я получаю исключение UnsatisfiedLinkException, похожее на это:
java.lang.UnsatisfiedLinkError: org.my.application.printer_create_handle(Ljava/lang/String;Ljava/lang/String;Ljava/lang/String;)V
at org.my.application.Printer.printer_create_handle(Native Method)
Что более или менее напоминает поведение, которое я вижу, когда вообще не загружаю библиотеку.
Когда я возвращаюсь к загрузке библиотекив статическом блоке, кажется, все работает правильно.Но когда я добавляю второе приложение, я получаю сообщение already loaded in another classloader
.Это имеет смысл для меня, но это не дает мне дальнейшего развития.
Я думаю, что я действительно не понимаю, как это работает правильно.Кто-нибудь может пролить свет на это?
Единственный способ обойти это - развернуть мою библиотеку в каталоге lib
Tomcat8, но я бы предпочел этого избежать.