The external jar files are placed under /Library/Java/Extensions on Mac OS X, i have multiple applications that depend on a group of jars such as JavaMail Api, if i dump all the jars in the folder java picks them up, but what i want to do is group them together such as all mail api jars go to the mail folder. But if group them under folders they are not picked up by java. Do i have to just dump them in to Extensions folder? It would make my life a lot easier when updating to group them.
No, they should resize directly under /Library/Java/Extensions/.
However, you can always pass -Djava.ext.dirs=... as an additional argument when you invoke Java programs.
As a sidenote: If you're about to manage dependencies for your projects, try look into build tools, which declaratively resolve dependencies, such as ant.apache.org/ivy or maven.apache.org.
You should not use the global extensions library unless you really, really have to.
Basically your programs should be self contained units with library code on top of a stock JVM, this will allow different programs to have different requirements regardring library code versions, and it will also work when used on other machines.
Pick a good IDE (Eclipse, NetBeans, perhaps Xcode but I have not used it) and learn to add jar files to your projects. It will make you a more attractive programmer to a future employer.
I do find this behaviour annoying myself, that you have to have a flat folder structure when referencing external jars (if you don't add the jars individually).
However, if you don't mind grouping them into jar files instead of grouping them into folders, I would recommend One-Jar.
Quoting: "One-JAR uses a classloader which knows how to load classes and resources from Jar files inside a Jar file. "
Related
Just for the sake of curiosity , I want to know is there a way I can edit/modify Java core classes inside rt.jar. I am searching everywhere in the internet but got no relevant answers. I have also referred to Covert Java(book) but I am unable to understand it.
Note: I don't want to distribute my app. I just want to do it for my curiosity.
Another answer suggested patching rt.jar
I believe this is not the best approach - you effectively cannot distribute your app (unless you have your app contenerized and you deliver Java with your app).
The way to go is to learn about bootstrap classpath
This should cover most of reasonable use cases.
The normal Java classloaders look for classes first in the bootstrap classpath, before checking for extensions and the application classpath. By default, the bootstrap classpath consists of the "rt.jar" file and some other important JAR files that are supplied by the JRE installation. These provide all of the classes in the standard Java SE class library, along with various "internal" implementation classes.
Under normal circumstances, you don't need to concern yourself with this. By default, commands like java, javac and so on will use the appropriate versions of the runtime libraries.
Very occasionally, it is necessary to override the normal behavior of the Java runtime by using an alternative version of a class in the standard libraries. For example, you might encounter a "show stopper" bug in the runtime libraries that you cannot work around by normal means. In such a situation, it is possible to create a JAR file containing the altered class and then add it to the bootstrap classpath which launching the JVM.
Better approach would be extending those Class and modifying the specific methods. This will not affect other project where you just wanted Java provided Class
Files in that jar are compiled .class files from .java source files. You cannot modify the binaries directly that easy, but if you have a source code (e.g. https://github.com/openjdk/) you can compile your own .class files and replace, since JAR is basically an archive with binaries.
Not the most scalable approach, but possible.
Let's imagine, I created a bunch of command line utilities, written in Scala and/or Java, and I'm using SBT to build them. They all use a couple of libraries, some of them pretty big, and in case of Scala, also the (not so small) Scala standard library.
I want to have these utilities in completely built form (runnable .jar files) to be able to instantly launch any of them and, if needed, also easily distribute them. But what I don't want is to include their dependencies in all of them, because they will be taking disk space. Instead I want them to get dependencies from a shared folder at runtime, and the application jar should contain only "my" classes.
The question is, is there a standard way to accomplish this? If so, where must be shared .jars located? Otherwise, what would you recommend to do?
You can set the CLASSPATH for this.
The JRE searched for classes in the .jar files named in the CLASSPATH.
Additionally all .jar files in the directory jre/lib/ext are used.
To find the complete serching in classpathes please consult the official documentation from Oracle.
Something you might like to consider (although it will require slightly changing what you plan to do) is to have a local Maven repository.
You could have SBT publish libraries to it when they're built. Instead of building runnable JARs, you could run your applications via SBT, which would pull libraries from the local repository as/when required.
The benefit of this is that all the plumbing to do this is built into SBT, and it would make distribution trivial.
The downside is that you would have to run your apps via SBT instead of building runnable JARs. Whether that will work for you, I don't know.
i am setting up a java project now. in the past, we always included everything (unzipped) from the 3rdparty, such as ant, junit, jfreechart, and others, inside our release. I am wondering is it possible just take those related .jar files but not everything with our software release? then we can get a smaller and neat release. Those 3rdparty library licenses don't allow us to do that way? what's your way? thanks,
You really want to retain the separate jars, if possible. Check out the maven appassembler plugin. It does a nice job of putting together an "unzippable" installation for you, in a controlled way. In the result you'll have a very straightforward "repo" directory filled with all of your dependencies.
I use the maven-assembly-plugin to build a single jar for each application. The plugin quickly handles the fuss of unzipping all the library jars and putting the whole lot back together as a single jar. It also supports writing a manifest with a main class specified which makes running the application simple from a command line (much simpler than specifying a classpath argument as long as your arm anyway).
If their licenses say that you should distribute derivatives with sources, then you are obliged to do that by law.
Another question is if they really force that. As far as I remember GPL, you shall distribute the sources if you want, but there is another way - you must make sources easily availiable to users. So you can drop sources in your distributables.
Any way, you should look at the licenses.
EDIT:
If you will decide to pack the whole program into single jar, I recommend Proguard. It is java optimiser, shrinker, and much more - all in one! To pack everything into one jar, just specify all your jars - program and libraries - as program jars, and specify only one jar as output. Usually it works just fine.
my application needs multiple jars to work. Since it is a desktop application i can not hold the user responsible of installing. So in my build script i unzip the jars content in to my build directory delete manifest files, compile my software and jar it again. Everything works as it should my question is are there any long term side effects to this process?
In the past, there were JARs with weird content (like the DB2 driver which contains com.ibm and com.IBM; after decompressing in a Windows filesystem, those two packages would be merged).
The only issue you need to be aware of are signed jars and other files in META-INF which might have the same name in multiple source JARs.
A simple solution for all these issues is to use One-JAR. It allows to wrap several JARs into one without unpacking them, first. And read this answer: Easiest way to merge a release into one JAR file
A simpler solution (IMO) is using Maven's assembly plugin, which is also described in one of the answers to another question which was linked to in a previous Q&A. This is provided you are using Maven (which is a recommended tool by its own right) as a build tool.
If you want a no fuss way for the end user to kick off a program with multiple jar dependencies you may want to look at Launch4j or Jsmooth (I prefer Launch4j). Both are programs that create executables that wrap jar(s) and the JRE together so that to the end user it appears no different then any other executable.
Another great option is ProGuard, which can also shrink and/or obfuscate the code too.
If your primary target platform is Windows desktop, then you could also consider generating an Windows native exe from the jars of your application
If some of the jars are signed you lose the signature by unpacking/repacking it.
Well you're throwing away the MANIFEST of your third party jars, so that could cause you problems. For example you could be causing security issues by throwing away the "Sealed" attribute.
Why not just create a simple installer and a script to launch your application which sets the CLASSPATH correctly?
One-JAR will do the job, and has a new release (0.97) which supports frameworks like Spring and Guice, which users are now packing into One-JAR archives. http://one-jar.sourceforge.net
Ference Hechler also did some great work inside Eclipse with the Eclipse export wizard: we worked together on FatJar/One-JAR from which the Eclipse work grew, and I can recommend that as an approach, though I don't know how well it handles the frameworks.
I'm trying to use an open source java library to visualize nodes and edges in a graph, but I'm completely lost.
I have a bunch of jar files in a folder. Clicking on some of the jar files makes java swing windows pop open with graphs displayed. Clicking other jar files does nothing.
If I figured that out, would I just stick the jar files in there with the other ones, or would that still not work?
And if I ever figure out how to use these files, does that mean that I have to include them if I transfer my java project to another computer? How would I go about doing that?
I believe if you put the jars in your classpath, you can import and use classes just like you would a standard library. Figuring out the classpath can be confusing, but you can just set it when you start your jvm. Your IDE may have options for it, too.
Most java problems are classpath problems.
Have you included those libraries in your classpath?
If you are using eclipse, you could
Project - > properties -> Java build path ->addJar.
And the Jar file should be placed in a directory inside your workspace (lib/ for example)
If you have to take your project to another computer, you could take these steps
Before doing anything, export your project (as a Jar file, for example).
Save it into your favorite drive (cd / usb drive/ diskette/ tape).
On "the other" computer, you can import this project into your workspace
In Eclipse, you need to add libraries to the project build path.
In general, you need to provide dependencies via the classpath mechanisms at compile time and runtime. The precise mechanisms vary, but, for example, if you used the javac compiler, you would provide your libraries on the command line:
javac -classpath C:\dir\lib1.jar;C:\dir\lib2.jar foo/MyClass.java
These dependencies would also be required to invoke the app:
java -classpath C:\dir\lib1.jar;C:\dir\lib2.jar;. foo.MyClass
This page gives some good info, though googling for the term "classpath" should provide alternative sources.
You use it by including it in the classpath of your java application, that way you can reference it from your code. Here is a starter document. The JDK 1.6 has some easier options (such as specifying multiple jar files as *.jar). It is definitely a little complicated, but it is very worth knowing.
You should have documentation for these Jars. Some sounds like examples, but one must be the core graph modelling and rendering Jar. Hopefully the examples have source included.
Just add that Jar to your project in Eclipse (e.g., in a /lib folder in your project, then add it to the build path) and use the documentation to use the code. You can also use Eclipse to look inside the Jar file.
Unless there is no alternative, it probably isn't worth using a load of third party code that isn't documented at least on the API level, and without any source examples definitely not.