I\'m developing a web service which is using native code via JNI.
Could I pack those dll\'s into my war?
I\'ve tired to manage them independently...
PS I\'m usin
If your dependency does not have <scope>provided</scope>
, it will get included in the war file no matter the type (jar, zip, etc, unless it's another war).
While this is true, there is however the problem that you need to have the native library (.so
, .dll
) on your java.library.path
. EJP's concerns are valid. However, if you play around with the assembly plugin and have the dll placed under the /META-INF
directory of your war file, you can easily knock up some code that extracts that dll from the classpath /META-INF/my.dll
and places it in a directory on the java.library.path
.
This is far from being anything remotely close to good practice, but I believe you can hack it like this.
@carlspring: You'll have to be lucky to have write access to any directory in java.library.path. (i.e. Program Files\Java etc) A better practice might be to unpack the dll's to a temp directory and add this directory to java.library.path at runtime. This is possible: http://fahdshariff.blogspot.nl/2011/08/changing-java-library-path-at-runtime.html
Yes, but there are a bunch of issues that you're going to run into.
DLLs are loaded from the filesystem, not the classpath
This is not a serious problem: simply store the DLL in your WAR as a resource, and copy it to a location on the filesystem. The property java.io.tmpdir
should point you at a writable directory, or you can use File.createTempFile()
(just be sure to call deleteOnExit()
on that file). Then you call System.load()
, not System.loadLibary()
.
You have to manage different copies of the DLL for different architectures
If you have complete control over the deployment, and know that you'll only ever deploy to one machine, then this isn't a problem. Otherwise, you'll need to write code to figure out which library to load.
You can only load a shared library once
This is the thing that will hurt you: when you load a shared library it is linked into the executable code of the JVM. You can't reload the same library, which means that you can't redeploy.
When I last had to load a shared library to support a web app, I ended up putting it in the app-servers shared directory. It was much easier that way.
The DLL files are not loaded via class path. Classpath mechanism is only for loading java resources like class files and other properties files.
One way is to specify the complete path of the DLL OR specify it using java.library.path
system variable. Please check this link for further details.
No you can't. DLLs have to be loaded from the file system. You would need (1) a cast-iron guarantee that the application server will unpack WARs to the file system, and (2) a knowledge of exactly where the DLL would be unpacked to on the file system so you can call System.load()
with the correct filename.
All from src/main/webapp
is packed to war in root, all from src/main/resources
is packed to WEB-INF/classes
. You can pack what you want