First, the compiler needs to compile .java text files into .class bytecode, and then the JVM executes the .class bytecode files. The process is not complicated; this article mainly records some of the related steps during compilation and runtime.
1. A Single Source File
- Create a text file Hello.java
| |
- Compile the source
| |
- Execute the bytecode
| |
2. Multiple Source Files
- Specify multiple files on the command line
| |
- Specify multiple files with a text file
| |
When running, you only need to run the class that contains the main function, for example, java M.
The compile command above generates .class bytecode files in the current directory; you can also use the -d parameter to specify the output directory. Managing these bytecode files becomes a tedious and troublesome affair, and Jar files simplify that process.
3. Jar Files
A Jar file is based on the Zip format and aggregates multiple files into one file. Jar files can be used not only for compression and distribution, but also for deployment, packaging libraries, components, and plugin programs, and they can also be run directly on the JVM. Jar packages provide the following features:
- Security. The file contents carry a digital signature
- Compresses files and reduces network transfer time
- Platform extension. Use Jar files to extend the core Java platform with additional functionality
- Package sealing. Packages stored in a Jar file can be sealed to strengthen version consistency and security
- Package versioning. Jar files can contain version and developer-related information
- Portability. The Java platform core standardizes how Jar files are handled
With IDE tools you can create a Jar file very conveniently, for example MyEclipse; you can try it yourself. Here we use the jar command directly to generate the Jar file.
3.1 Preparing the Java Source
Here we take multiple source files as an example, creating two files under the com/test directory:
A.java
| |
B.java
| |
3.2 Compiling the Java Source
| |
3.3 Packaging the Jar File
Use the jar command to package a Jar, similar to using the tar command.
| |
Reference documentation, Compiling the Example Programs
3.4 Running the Jar File
Running the Jar file directly reports an error:
| |
This is because the JVM cannot find the program’s entry point. There are two ways to specify the program entry point:
- Specify it in the META-INF/MANIFEST.MF file
Use the unzip command to extract the Jar file, and you will see that besides the .class files there is also a META-INF/MANIFEST.MF file. In the META-INF/MANIFEST.MF file, add:
| |
pointing to the class that contains public static void main(String[] args).
- Specify the class containing the main function on the command line
| |
4. Maven
If there are only one or two source files, the packaging process above is still acceptable. But for medium and large projects, this primitive approach cannot meet the needs of building and management, so some tooling is required.
Maven is a software project management and automated build tool, usable for building and managing various projects such as Java, Ruby, Scala, and so on. Maven is a project under the Apache Software Foundation.
Maven projects are configured using a Project Object Model (POM). The project object model is stored in a file named pom.xml.
4.1 Installing Maven
Here we take installing on CentOS as an example:
| |
Check the version:
| |
4.2 Creating a pom.xml File
Using the A.class and B.class above as an example, create a new pom.xml file. The artifactId is the filename generated after the build.
In a Maven project, the convention is to put the main code under the src/main/java directory without additional configuration. Here we create the src/main/java directory and move the com directory into it.
The newly created pom.xml file is as follows:
| |
The final directory structure is:
| |
Run the command to compile the project:
| |
Run the built package:
| |
The reason it can be run directly with java -jar is that the maven-jar-plugin plugin was added to pom.xml, and this plugin adds the Main-Class information to META-INF/MANIFEST.MF.
4.3 Packaging the Project into an Image
To deploy the project directly on a container platform, after compiling and building we still need to containerize the generated files. Here we use the docker-maven-plugin plugin to do this. Add the following content to the plugins tag in the pom.xml file:
| |
Run the compile command mvn package again, and you will see some additional log output.
[INFO] --- docker-maven-plugin:1.2.1:build (default) @ test ---
SLF4J: Failed to load class "org.slf4j.impl.StaticLoggerBinder".
SLF4J: Defaulting to no-operation (NOP) logger implementation
SLF4J: See http://www.slf4j.org/codes.html#StaticLoggerBinder for further details.
[WARNING] No entry found in settings.xml for serverId=docker-hub, cannot configure authentication for that registry
[INFO] Using authentication suppliers: [ConfigFileRegistryAuthSupplier]
[INFO] Copying /root/test-java/target/test-0.0.1-SNAPSHOT.jar -> /root/test-java/target/docker/test-0.0.1-SNAPSHOT.jar
[INFO] Building image shaowenchen/maven-hello-word:v1
Step 1/6 : FROM openjdk:8
---> 09df0563bdfc
Step 2/6 : ENV JAVA_OPTS -XX:+UnlockExperimentalVMOptions -XX:+UseCGroupMemoryLimitForHeap -XX:MaxRAMFraction=2 -XX:CICompilerCount=8 -XX:ActiveProcessorCount=8 -XX:+UseG1GC -XX:+AggressiveOpts -XX:+UseFastAccessorMethods -XX:+UseStringDeduplication -XX:+UseCompressedOops -XX:+OptimizeStringConcat
---> Running in b6dabde9580c
Removing intermediate container b6dabde9580c
---> 0664556506d3
Step 3/6 : ENV TZ Asia/Shanghai
---> Running in 954b264bfb35
Removing intermediate container 954b264bfb35
---> 334f644fa97e
Step 4/6 : WORKDIR /work
---> Running in 44e039f55452
Removing intermediate container 44e039f55452
---> 3572d77be94c
Step 5/6 : ADD test-0.0.1-SNAPSHOT.jar .
---> 904b5885f74a
Step 6/6 : CMD java ${JAVA_OPTS} -jar test-0.0.1-SNAPSHOT.jar
---> Running in b3f567a912a5
Removing intermediate container b3f567a912a5
---> cba070b2300d
ProgressMessage{id=null, status=null, stream=null, error=null, progress=null, progressDetail=null}
Successfully built cba070b2300d
Successfully tagged shaowenchen/maven-hello-word:v1
[INFO] Built shaowenchen/maven-hello-word:v1
[INFO] ------------------------------------------------------------------------
[INFO] BUILD SUCCESS
[INFO] ------------------------------------------------------------------------
[INFO] Total time: 4.017s
[INFO] Finished at: Fri Dec 20 16:27:48 CST 2019
[INFO] Final Memory: 31M/508M
[INFO] ------------------------------------------------------------------------
The log above is building the image; if you turn on the push switch, Maven will push the image to the dockerhub registry.
View the locally built image:
| |
