Introduction
This is a note on Spring Boot and JAR and WAR deployment.
Background
In the earlier note, I talked about Spring Boot and JAR deployment. In this note, I will explore the opportunity to pack a Sprint Boot application into both JAR and WAR bundles with a single implementation.
Typically if you use Spring Boot, you may want to pack your project into a JAR. But if you do want to use a servlet container, you can still do it.
- The "spring-boot-example-implementation" is a Maven project which has all the implementations of a Spring Boot application;
- The "spring-boot-example-jar-package" does not have its own source code. It is responsible to pack the application into an executable JAR bundle;
- The "spring-boot-example-war-package" does not have its own source code. It is responsible to pack the application into a WAR bundle to be deployed to a servlet container, such as Tomcat.
- All the 3 project share the same parent POM project "spring-boot-example" that provides the common basic configurations for all the child projects.
The "spring-boot-example" POM
The "spring-boot-example" is a simple POM project that declares the three module level projects and configures the compiler to target to Java 1.8.
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0
http://maven.apache.org/xsd/maven-4.0.0.xsd">
<properties>
<spring-boot.version>1.5.7.RELEASE</spring-boot.version>
</properties>
<modelVersion>4.0.0</modelVersion>
<groupId>com.song.example</groupId>
<artifactId>spring-boot-example</artifactId>
<version>0.0.1</version>
<packaging>pom</packaging>
<modules>
<module>spring-boot-example-implementation</module>
<module>spring-boot-example-jar-package</module>
<module>spring-boot-example-war-package</module>
</modules>
<build>
<finalName>${project.artifactId}</finalName>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>3.7.0</version>
<configuration><source>1.8</source><target>1.8</target></configuration>
</plugin>
</plugins>
</build>
</project
The "spring-boot-example-implementation"
The POM of the "spring-boot-example-implementation" is the following.
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0
http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>com.song.example</groupId>
<artifactId>spring-boot-example</artifactId>
<version>0.0.1</version>
</parent>
<artifactId>spring-boot-example-implementation</artifactId>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
<version>${spring-boot.version}</version>
</dependency>
</dependencies>
</project>
To save my time, this project has exactly the same content as my earlier note, except the POM file. You are encourage to take a look at it to get to know the critical pieces of a Spring Boot application.
The "spring-boot-example-jar-package"
The "spring-boot-example-jar-package" project has no source code. All that it does is to pack the "spring-boot-example-implementation" project into an executable JAR file that you can deploy.
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0
http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>com.song.example</groupId>
<artifactId>spring-boot-example</artifactId>
<version>0.0.1</version>
</parent>
<artifactId>spring-boot-example-jar-package</artifactId>
<properties>
<start-class>com.song.web.boot.ApplicationStart</start-class>
</properties>
<dependencies>
<dependency>
<groupId>com.song.example</groupId>
<artifactId>spring-boot-example-implementation</artifactId>
<version>0.0.1</version>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
<version>${spring-boot.version}</version>
<configuration>
<mainClass>com.song.web.boot.ApplicationStart</mainClass>
</configuration>
<executions>
<execution>
<goals><goal>repackage</goal></goals>
</execution>
</executions>
</plugin>
</plugins>
</build>
</project>
- Because the "spring-boot-example-implementation" project has declared all the dependencies required for a basic Spring Boot application, there is no need to declare any additional packages in this POM;
- We need to specify the "mainClass" in the "spring-boot-maven-plugin", so Java knows where to find the "static main()" method to start the program.
The "spring-boot-example-war-package"
The "spring-boot-example-war-package" project has no source code. All that it does is to pack the "spring-boot-example-implementation" project into a WAR file that you can deploy to a servlet container.
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0
http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>com.song.example</groupId>
<artifactId>spring-boot-example</artifactId>
<version>0.0.1</version>
</parent>
<artifactId>spring-boot-example-war-package</artifactId>
<packaging>war</packaging>
<dependencies>
<dependency>
<groupId>com.song.example</groupId>
<artifactId>spring-boot-example-implementation</artifactId>
<version>0.0.1</version>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-tomcat</artifactId>
<version>${spring-boot.version}</version>
<scope>provided</scope>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-war-plugin</artifactId>
<version>2.6</version>
<configuration>
<failOnMissingWebXml>false</failOnMissingWebXml>
</configuration>
</plugin>
</plugins>
</build>
</project>
- When we deploy the application to a servlet container, we do not need to pack the embedded tomcat into the WAR file. The "spring-boot-starter-tomcat" dependency is marked as "provided";
- Because we do not have a "web.xml" file in the project, we need to specify "failOnMissingWebXml" to false.
Debug and Run
If you load the project into Eclipse, you can directly run or debug the application on the "spring-boot-example-implementation" project.
In the "spring-boot-example-jar-package" project, you can use the following command to start the application.
mvn spring-boot:run
After a successful Maven build, you can launch the JAR file with the following command.
java -jar target/spring-boot-example-jar-package.jar
If you like, you can also attach a Tomcat server to the "spring-boot-example-war-package" to run and debug the application in Eclipse though the Tomcat server.
Of course, you need to test to deploy your WAR file to a stand-alone servlet container. I have tested my WAR in a stand-alone Tomcat server.
- When you start the application as a JAR, the port number that it listens to is "8090". The port number is configured in the "spring-boot-example-implementation" project. You can take a look at my earlier note for the details;
- When you start the application as a WAR, Tomcat will not honor this port number. It will listen to its own port number. In my case, it is "8080".
The following shows the result when we access the application from a browser when it is hosted in the Tomcat.
Points of Interest
- This is a note on Spring Boot and JAR and WAR deployment;
- I hope you like my postings and I hope this note can help you one way or the other.
History
First Revision - 12/12/2017