Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

maven build failing when generating war package for spring boot application?

This is an extension to my previous question here at SO. As per this post, main method is NOT required to generate a deployable war

I am trying to generate a deployable war for this simple application of uploading files. The source code can be for this example application can be found here.

Following the instructions from spring boot for jar to war conversion, I changed my pom.xml to reflect the following. (Just added tomcat dependency with scope provided).

Reference: http://docs.spring.io/spring-boot/docs/current/reference/htmlsingle/#build-tool-plugins-maven-packaging

      <?xml version="1.0" encoding="UTF-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">
    <modelVersion>4.0.0</modelVersion>

    <groupId>org.springframework</groupId>
    <artifactId>gs-uploading-files</artifactId>
    <version>0.1.0</version>
    <packaging>war</packaging>

    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>1.2.3.RELEASE</version>
    </parent>


    <build>
        <plugins>
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
            </plugin>
        </plugins>
    </build>

    <dependencies>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-tomcat</artifactId>
            <scope>provided</scope>
        </dependency>

    </dependencies>

    <properties>
        <java.version>1.7</java.version>
    </properties>

    <repositories>
        <repository>
            <id>spring-releases</id>
            <name>Spring Releases</name>
            <url>https://repo.spring.io/libs-release</url>
        </repository>
    </repositories>
    <pluginRepositories>
        <pluginRepository>
            <id>spring-releases</id>
            <name>Spring Releases</name>
            <url>https://repo.spring.io/libs-release</url>
        </pluginRepository>
    </pluginRepositories>
</project>

Then I changed Application.java as follows

Reference: http://docs.spring.io/spring-boot/docs/current/reference/htmlsingle/#howto-create-a-deployable-war-file

@SpringBootApplication
public class Application extends SpringBootServletInitializer{

    @Override
    protected SpringApplicationBuilder configure(SpringApplicationBuilder application) {
        return application.sources(Application.class);
    }

    /*public static void main(String[] args) {
        SpringApplication.run(Application.class, args);
    } */
} 

I tried two scenarios. both fail with the following error (Unable to find main class).

  1. No main method (NOTE I have commented out main method above)
  2. No application.Java file (commented out everything from this file - not shown here)

Error:

[INFO] BUILD FAILURE
[INFO] ------------------------------------------------------------------------
[INFO] Total time: 9.218s
[INFO] Finished at: Thu Apr 23 11:46:24 PDT 2015
[INFO] Final Memory: 22M/222M
[INFO] ------------------------------------------------------------------------
[ERROR] Failed to execute goal org.springframework.boot:spring-boot-maven-plugin:1.2.3.RELEASE:repackage (default) on project gs-uploading-files: Execution default of goal org.springframework.boot:spring-boot-maven-plugin:1.2.3.RELEASE:repackage failed: Unable to find main class -> [Help 1]
[ERROR]
[ERROR] To see the full stack trace of the errors, re-run Maven with the -e switch.
[ERROR] Re-run Maven using the -X switch to enable full debug logging.
[ERROR]
[ERROR] For more information about the errors and possible solutions, please read the following articles:
[ERROR] [Help 1] http://cwiki.apache.org/confluence/display/MAVEN/PluginExecutionException

PS: when I have main method intact, the build is successful

like image 527
brain storm Avatar asked Apr 23 '15 18:04

brain storm


1 Answers

If you want to get both the benefits - i.e. standalone executable war with embedded Tomcat and the normal war deployable in external Tomcat - you need to have a class with main method. So,

  • Enable the main() method in your Application.java.
  • Configure spring-boot-maven-plugin to specify the class with the main class (Spring should find it anyway if you have one, but good to be explicit I guess): <plugin> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-maven-plugin</artifactId> <version>${spring-boot-version}</version> <configuration> <mainClass>the.package.of.Application</mainClass> </configuration> <executions> <execution> <goals> <goal>repackage</goal> </goals> </execution> </executions> </plugin>
  • Remove spring-boot-starter-tomcat dependency in your pom with provided scope. Spring boot magically knows how to enable/disable embedded Tomcat.

With this you should be able to launch your Spring app from IDE by just running the Application.java class as a normal Java app, build a war file that is both standalone executable and deployable in external Tomcat as usual too.

I am currently building REST APIs with Spring Boot 1.0.1.RELEASE with this kind of setup and it works great in all three modes.

like image 117
Naymesh Mistry Avatar answered Sep 21 '22 12:09

Naymesh Mistry