JAR(Java ARchive) Files

JARmanifest

In the previous blog we learned about the concept of Packages in Java. If you want to visit the previous blog visit Introduction to Packages. In this blog, we will learn about the JAR files used in Java. Basically, JAR stands for Java ARchive. The main purpose of the JAR files was to give users a single file, not a directory that contained multiple class files. JAR File can contain class files as well as other files like image and sound files. JAR is a file format based on the popular ZIP file format and is used for combining many files into one. We can use JAR files for lossless data compression, archiving, decompression, etc. We will learn more about the JAR files in the below sections:

Creation of JAR Files

To make JAR files we can use the jar tool. The following command can be used to make a new JAR File.

jar cvf jarFileName file1 file2 file3 . . .

e.g.

jar cvf CalculatorClasses.jar *.class icon.gif

jar command follows the below format:

jar options file1 file2 file3 . . .

We can use the following options for jar

OptionsDescription
cOption c creates a new or empty archive and adds files to it.
CIt changes the directory temporemporarily e.g jar cvf jarFileName.jar -C classes *.class using the above command we can change the classes subdirectory to add class files.
eOption e can be used to create an entry point in the manifest
iIt creates an index file.
MIt doesn’t create a manifest file for the entries.
tIt displays the table of contents.
uIt is used for updating an existing JAR file.
vIt generates the verbose output
OOption O stores without ZIP compression

Application programs and code libraries can be packaged into JAR files. For example if we want to send mail in Java, then we use the library javax.mail.jar.


Manifest

JAR Files contains the manifest files which describe the special feature of the archive. The Manifest File is located in the META-INF subdirectory of the JAR File and the Manifest File is called MANIFEST.MF. Some Manifests are complex having more entries. The Manifest entries are divided into sections. The first section is known as the main section. It is applicable to the whole JAR file. Subsequent entries can define the properties of named entities like individual files, URLs or packages. The entries must start with a Name entry. Blank lines can be used to separate the sections.

e.g.

Manifest-Version: 1.0

Name: Atrowel.class
Name: com/example/atrowelpackage/

In order to edit the manifest, we can place the lines which we want to add to the manifest into the text file and then we run the following command

jar cfm jarFileName manifestFileName1 . . .

For example, if we want to make a new JAR file then we can run the following command

jar cfm MyArchive.jar manifest.mf com/example/atrowelpackage/*.class

If we want to update the manifest of an existing JAR file, then we can place the addition into the text file and run the command.

jar ufm AtrowelArchive.jar manifest-additions.mf

Executable JAR Files

In order to specify the entry point of the program, we can use the option ‘e’ of the jar commands.

jar cvfe AtrowelProgram.jar com.example.atrowelpackage.AtrowelMainAppClass files to add

The alternate way is to specify the main class of the program in the manifest. We can do it by using the following statement.

Main-Class: com.exampe.atrowelpackage.AtrowelMainAppClass

We must make sure that we do not add a .class extension to the main class name. With either method we can start the program using the following command.

java -jar AtrowelProgram.jar

We can even launch the application by just double-clicking the JAR file icon depending on the operating system configuration. Below is the behavior for some OS.

  1. For Windows, the Java runtime installer creates a file association for the “.jar” extension that launches the file with the javaw -jar command.
  2. For Mac OS X, the operating system recognizes the “.jar” file extension and executes the Java program when we double-click a JAR file

But a Java program in a JAR file does not have the same feel just like a native application. On Windows, third-party wrapper utilities can be used that turn JAR files into Windows executables. A wrapper is a Windows is nothing but a program with the familiar .exe extension which locates and launches the Java virtual machine (JVM) or tells us what should be done when no JVM is found.


Executable JAR Files

There may be situations where previously accessible internal APIs are no longer available. For example, JavaFX 8 had an internal class com.sun.javafx.css.CssParser. If we use it to parse a style sheet, then we will see that the program will not be compiled. The solution for it is simple. We will just need to switch to javafx.css.CssParser available in Java 9. But the problem here is we will need to distribute the applications for Java 8 and Java 9. To solve this problem Java 9 has introduced multi-release JARs that contain class files for different versions of Java. The additional class files are placed in the META-INF/versions directory for backward compatibility: Here is the example:...

Suppose if the AtrowelApplication class makes the use of CSSParser class, then the AtrowelApplicaation file can be compiled com.sun.javafx.css.CssParser, while the Java 9 version will use javafx.css.CssParser. Java 8 doesn’t know anything about the META-INF/versions directory and it will simply load the legacy classes. When the JAR file is read by Java 9, then the new version is used. We use --release flag to add the versioned class file:

jar uf AtrowelProgram.jar --release 9 AtrowelApplication.class

In order to build a multi-release JAR file from scratch, then we must use -C option and must switch to a different class file directory for each version:

jar cf AtrowelProgram.jar -C bin/8 . --release 9 -C bin/9 AtrowelApplication.class

For compiling different releases, we can use --release flag and -d flag to specify the output directory:

javac -d bin/8 --release 8 . . .

According to Java 9, the -d option creates the directory if it doesn’t exist. The --release fag is also new in Java 9. In older versions, we used to use -source, -target, and bootclasspath flags. Multi-release JARs are not aimed for different versions of a program or library. The main purpose of multi-release JARs is to enable a particular version of the program or library to work with multiple JDK releases. Suppose if we change the API to add functionality, then we should provide a new version of JAR to it.

Get in Touch

Atrowel will be pleased to receive your feedback and suggestions. Those of you who would like to contribute, please send us an email.