Spring boot maven executable jar not running with Double click - spring

Created a maven jar of a simple spring boot application.
If I try and execute the jar file from the command line using java -jar x.jar and it runs ok, even see all the traces of spring boot..booting up..
If try to execute it just by double clicking it with the mouse, it wont run. A command window pops up for a milli second and vanishes and if I try to get to an exposed endpoint (HTTP Rest - Get)..site cant be reached error..
The project is a sample Eureka server, so contains cloud dependencies..
Any ideas what could be the problem, is it just some environment setting?!
Regards,
From the POM:
<groupId>example.demo</groupId>
<artifactId>EurekaServiceDiscovery</artifactId>
<version>0.0.1-SNAPSHOT</version>
<packaging>jar</packaging>
.
.
.
.
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.0.3.RELEASE</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
.
.
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>
Basic Spring Eureka example, virtually no code except:
#EnableEurekaServer
#SpringBootApplication
public class EurekaServiceApplication {
public static void main(String[] args) {
SpringApplication.run(EurekaServiceApplication.class, args);
}

Did you follow this?
https://docs.spring.io/spring-boot/docs/current/reference/html/deployment-install.html
To create a ‘fully executable’ jar with Maven, use the following plugin configuration:
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
<configuration>
<executable>true</executable>
</configuration>
</plugin>
The following example shows the equivalent Gradle configuration:
bootJar {
launchScript()
}
You can then run your application by typing ./my-application.jar (where my-application is the name of your artifact). The directory containing the jar is used as your application’s working directory.

There is no problem at all
Doubble click on jar fie and executing by command are not same
java -jar x.jar
Either execute from eclipse or from command prompt.
Else change Windows(operating system) setting or change execution setting in maven config to execute from command prompt

Related

Spring dev tool class is not found at run time

I have created a SpringBoot app which has spring-boot-devtools in Maven pom
I can run it without issue in Intellji. But if I run it from the jar being built, it throws the following exception. It gives the following exception. It looks like the devtool jars are not packaged?!
org.springframework.beans.factory.BeanDefinitionStoreException: Failed to parse configuration class [com.x.x.x.TestApplication]; nested exception is java.io.FileNotFoundException: class path resource [org/springframework/boot/devtools/filewatch/FileChangeListener.class] cannot be opened because it does not exist
Devtools is excluded from a packaged jar by default to avoid it being accidentally used in a production deployment. If you want to include Devtools in your packaged jar you can opt-in. To do so, set excludeDevtools to false in your plugin configuration:
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
<configuration>
<excludeDevtools>false</excludeDevtools>
</configuration>
</plugin>
</plugins>
</build>

How to create/find application jar to deploy your spring boot maven application using embedded tomcat?

I want to deploy my application using the embedded tomcat in spring -boot. I figured that I have to run the java -jar spring-boot-app.jar command, but I cannot find the jar file for the application anywhere.
On running mvn clean package I am able to generate a war file to deploy externally, how can I do the same with embedded tomcat ?
You need to remove following line from pom.xml
<packaging>war</packaging>
or replace war packaging with jar. Make sure you have spring-boot-maven-plugin in maven build plugins
The jar should then be available in target folder
To create an executable jar, we need to add the spring-boot-maven-plugin to our pom.xml. To do so, insert the following lines just below the dependencies section:
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>
For more information,refer this :
https://docs.spring.io/spring-boot/docs/current/reference/html/getting-started.html

Spring Boot's spring-boot:run doesn't honor specified profile

I am upgrading my old spring boot 1.5.x to latest 2.0.4, and I found mvn spring-boot:run doesn't honor the profile specified in command line:
I have an application.properties which stores common properties, and application-dev.properties and application-prod.properties specifying their db connections and tomcat ports.
It means, I have two profiles: dev and prod. I lookup the document, I have to specify profiles in pom.xml
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
<configuration>
<profiles>
<profile>dev</profile>
<profile>prod</profile>
</profiles>
</configuration>
</plugin>
And I want to execute the dev profile, I run:
mvn spring-boot:run -Dspring-boot.run.profiles=dev
And I see console outputs
boot.SpringApplication - The following profiles are active: dev
It seems Ok, but then I found it connects to wrong database and open different port, which is specified in prod profile.
It seems all values specified in prod override the dev ones.
And if I comment the values in prod, the dev ones are pickup (so, there is no typo in dev profile).
I tried the following combos:
mvn spring-boot:run -Dspring-boot.run.profiles=dev
mvn spring-boot:run -Dspring-boot.run.profiles="dev"
mvn spring-boot:run -Pdev -Dspring-boot.run.profiles=dev
mvn spring-boot:run -Pdev -Dspring-boot.run.profiles="dev"
All show The following profiles are active: dev but connect to prod DB and open wrong tomcat port.
I then tried:
mvn spring-boot:run -Pdev -Dspring.profiles.active=dev
mvn spring-boot:run -Pdev -Dspring.profiles.active="dev"
mvn spring-boot:run -Dspring.profiles.active="dev"
mvn spring-boot:run -Dspring.profiles.active=dev
mvn spring-boot:run -Drun.jvmArguments="-Dspring.profiles.active=dev"
All the 5 above show The following profiles are active: dev,prod (which is incorrect, I just want dev) and still connect to prod DB
What may go wrong here?
This was easy in spring boot 1.5.x but became a WTF in 2.0.x . I feel frustrated here.
env:
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.0.4.RELEASE</version>
<relativePath/>
</parent>
------- updated -------
As #Jayesh said , maybe there's something wrong hidden, which leads default to prod. I renamed my application-prod.properties to application-prod2.properties. I am sure there's no prod2 string in the whole project code.
after mvn clean compile install,
Rerun with
mvn spring-boot:run -Dspring-boot.run.profiles=dev
Same result (The following profiles are active: dev but still opens to wrong DB specified in prod2)
And...
mvn spring-boot:run -Dspring.profiles.active=dev
Same result: The following profiles are active: dev,prod, connects to wrong DB, opens wrong port specified in prod2
It seems spring boot picks whatever application-*.properties and load the last one
I even set log level to TRACE
logging.level.org.springframework=TRACE
But still found no prod2 string in the output log...
Solved
The problem is solved.
There is another spring's XML containing this line:
<context:property-placeholder location="classpath*:*.properties"/>
It is the culprit. After commenting out this line, everything works fine.
P.S.: This is an evolving app, from pure spring app, with spring's XML setting, and the above line. Then wrapped in MVC, and then spring-boot . Everything works fine in 1.5.x, but in 2.x, boot truly loaded all .properties files and override all value one by one.
Please update your pom.xml without the profiles section. As per boot maven plugin doc, you should only provide active profile in the section.
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
<configuration>
<profiles>
<!--<profile>dev</profile>
<profile>prod</profile> you are setting active profile via command line args-->
</profiles>
</configuration>
</plugin>
Since, you are passing via command line args you dont need to give it there.. You may look at these beautiful tutorials.
https://www.mkyong.com/spring-boot/spring-boot-profiles-example/
https://www.baeldung.com/spring-profiles
Please let me know if it works.
I tried with the latest Spring Boot(v2.0.4.RELEASE) and the profile are getting loaded as expected.
pom.xml :
<?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>com.example</groupId>
<artifactId>demo</artifactId>
<version>0.0.1-SNAPSHOT</version>
<packaging>jar</packaging>
<name>demo</name>
<description>Demo project for Spring Boot</description>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.0.4.RELEASE</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
<java.version>1.8</java.version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
<configuration>
<profiles>
<profile>dev</profile>
<profile>prod</profile>
</profiles>
</configuration>
</plugin>
</plugins>
</build>
</project>
TestController.java:
package com.example.demo.TestController;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
/**
* Created by Raj Rathore on 27-Aug-18
*/
#RestController
#RequestMapping("/test")
public class TestController {
#Value("${profile}")
String profile;
#GetMapping("/profile")
public String getProfile() {
return profile;
}
}
application-dev.poperties:
profile=dev profile
application-pord.poperties:
profile=prod profile
Then by using the mvn spring-boot:run -Dspring-boot.run.profiles=dev the dev profile is loaded :
com.example.demo.DemoApplication : The following profiles are active: dev
Output : (http://localhost:8080/test/profile)
dev profile
OK , The problem is solved.
There is another spring's XML containing this line :
<context:property-placeholder location="classpath*:*.properties"/>
It is the culprit. After commenting out this line , everything works fine.
P.S. : This is an evolving app , from pure spring app , with spring's XML setting , and the above line. Then wrapped in MVC , and then spring-boot . Everything works fine in 1.5.x , but in 2.x , boot truly loaded all .properties files and override all value one by one.
Maybe there are some subtle changes on parsing .properties from spring boot 1.5.x to 2.x.

How to create a complete `.war` file with pom.xml

I have a web service project (SOAP) implemented in Java, as a Maven project. I want to create a .war to deploy into a Tomcat.
To create the .war, I always used the Eclipse Juno interface (Right click -> Export -> WAR File). The Eclipse is configured with Tomcat 7 and Axis 1.5.6. Using this method I deploy the .war file created and everything is fine! The main page of the application looks like below:
[![Web Service main page][1]][1]
In this page, I can explore the services, methods and WSDL files. This is what I call complete .war file.
Now, I migrated my web service to Maven, in order to use it with Jenkins, to automate the deploys, tests, etc.
I tried for two full days create a pom.xml which will create the same .war file that was created with Eclipse, but I was not successful. When I deploy the .war created using the pom.xml on a Tomcat and access the localhost:8080/SOAPExample/, it shows Error 404. The Maven build of the .war and the Tomcat deploy was successful. I understood that the service page was not created, but the web service was deployed successfuly.
I used some of the tutorials available in the internet, like the below, but in all cases the .war created by Maven is incomplete:
http://crunchify.com/how-to-create-a-war-file-from-eclipse-using-maven-plugin-apache-maven-war-plugin-usage/
https://www.mkyong.com/maven/how-to-deploy-maven-based-war-file-to-tomcat/
It looks like I'm missing some dependency configuration into the pom.xml, or something like that. Here is my pom.xml. I also think it is missing some axis2 configuration.
<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>com.test</groupId>
<artifactId>SOAPExample</artifactId>
<version>0.0.1</version>
<packaging>war</packaging>
<name>SOAPExample</name>
<build>
<sourceDirectory>src</sourceDirectory>
<plugins>
<plugin>
<artifactId>maven-compiler-plugin</artifactId>
<version>3.1</version>
<configuration>
<source>1.7</source>
<target>1.7</target>
</configuration>
</plugin>
<plugin>
<artifactId>maven-war-plugin</artifactId>
<version>2.4</version>
<configuration>
<warSourceDirectory>WebContent</warSourceDirectory>
<failOnMissingWebXml>false</failOnMissingWebXml>
</configuration>
</plugin>
</plugins>
</build>
<dependencies>
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>servlet-api</artifactId>
<version>2.5</version>
</dependency>
</dependencies>
Here is my project sctructure:
[[![Project Folder Structure]][2][2]]
There is no tutorial in the internet explaining how to configure a pom.xml to create a complete .war file. Could some good soul help me?

Springboot: Unable to start EmbeddedWebApplicationContext due to missing EmbeddedServletContainerFactory bean [duplicate]

I have a spring-boot application that needs to:
Be deployable as a war in a servlet container
Be runnable via `mvn spring-boot:run``
I'd also like to be able to run this application in my IDE (Eclipse or IntelliJ IDEA Community) by right clicking on the main and running it.
Here are the interesting parts of my pom.xml (Note that I do not inherit from spring-boot-starter-parent pom):
...
<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>
...
<build>
<plugins>
<plugin>
<artifactId>maven-war-plugin</artifactId>
<version>2.6</version>
<configuration>
<failOnMissingWebXml>false</failOnMissingWebXml>
</configuration>
</plugin>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
<version>${spring.boot.version}</version>
<executions>
<execution>
<goals>
<goal>repackage</goal>
</goals>
</execution>
</executions>
</plugin>
</plugins>
</build>
Here's my SpringBootServletInitializer:
#Configuration
#EnableAutoConfiguration
#ComponentScan("com.company.theproject")
public class Application extends SpringBootServletInitializer
{
private static final Logger logger = LoggerFactory.getLogger(Application.class);
#Override
protected SpringApplicationBuilder configure(SpringApplicationBuilder application)
{
return application.sources(Application.class);
}
public static void main(String[] args)
{
SpringApplication.run(Application.class, args);
}
}
When running the main inside an IDE I get the following error:
org.springframework.context.ApplicationContextException: Unable to start EmbeddedWebApplicationContext due to missing EmbeddedServletContainerFactory bean.
at org.springframework.boot.context.embedded.EmbeddedWebApplicationContext.getEmbeddedServletContainerFactory(EmbeddedWebApplicationContext.java:183) ~[spring-boot-1.2.3.RELEASE.jar:1.2.3.RELEASE]
at org.springframework.boot.context.embedded.EmbeddedWebApplicationContext.createEmbeddedServletContainer(EmbeddedWebApplicationContext.java:156) ~[spring-boot-1.2.3.RELEASE.jar:1.2.3.RELEASE]
at org.springframework.boot.context.embedded.EmbeddedWebApplicationContext.onRefresh(EmbeddedWebApplicationContext.java:130) ~[spring-boot-1.2.3.RELEASE.jar:1.2.3.RELEASE]
... 12 common frames omitted
Seems like mvn spring-boot:run does some more magic that does not happen when running the main directly.
Removing the provided scope from the spring-boot-starter-tomcat dependency fixes this issue but causes trouble when the war is run inside a servlet container.
Right now the only "fix" I've found is to run mvn spring-boot:run within IntelliJ IDEA instead of running the main directly. While this is an acceptable workaround, I'd still like to know why this doesn't work and if it can be fixed.
A workaround that is strongly inspired from https://youtrack.jetbrains.com/issue/IDEA-140041 is to start your main class with the test classpath (which includes the embedded servlet.)
Steps (IntelliJ 16):
Run -> Edit Configurations -> Add new configuration -> Pick Application type.
Set Main class to <your.main.class>
Set Use classpath of module to <*>_test (the test module!)
Ok and Run it!
I believe this could be related to https://youtrack.jetbrains.com/issue/IDEA-107048
IntelliJ IDEA is not injecting the provided dependencies into the CLASSPATH and as Andy stated this is why spring is unable to create the embedded servlet container.
They have a feature request since 2005 about this: https://youtrack.jetbrains.com/issue/IDEABKL-99
Workarounds mentioned in the comments includes having a fake module with the necessary libs and using it as classpath, using the -Xbootclasspath JVM argument or using custom maven profiles for running (compiled) vs building (provided).
I had the same problem using IntelliJ 2018.
Initially, Make sure that you have added the maven library for the spring project in your IntelliJ.
My solution is:
Go to Run -> Edit Configurations.
Select Application && choose your current project.
Check Include dependencies with "Provided" scope.
OK -> RUN
I was able to make this work by changing the scope of the spring-boot-starter-tomcat dependency to "compile" under Project structure->Dependencies tab. This doesn't effect pom.xml but allows this dependencies to be available to spring boot run configuration
Click here for image on where to change this setting in idea
mvn spring-boot:run includes provided dependencies when it's creating the classpath. It sounds like IntelliJ IDEA does not. Without Tomcat on the classpath, Spring Boot's unable to create an embedded servlet container which causes the exception you're seeing. Arguably this is a bug in IntelliJ as, if there's no container to provide the dependency, then it really needs to be on the classpath.
You may be able to fix the problem by overriding the default classpath that IntelliJ uses when running the main method to include the spring-boot-starter-tomcat dependency.
I find this page, and use the maven profile to manage the profiles.
<profiles>
<profile>
<id>PROD</id>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-tomcat</artifactId>
<scope>provided</scope>
</dependency>
</dependencies>
</profile>
<profile>
<id>DEV</id>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-tomcat</artifactId>
<scope>TEST</scope>
</dependency>
</dependencies>
</profile>
</profiles>
and config the main class beforeLanuce,set the command
mvn clean compile -Pdev
I was able to work around this problem in Intellij IDEA 2017.2 by adding the provided libaray (spring-boot-starter-tomcat) to the project configuration.
Select File -> Project Structure. Select Libraries and add a new project library (type = From Maven...). Search for spring-boot-starter-tomcat using the dialog, select the correct version and add it by clicking on OK. The library is added to the list of external libraries.
The disadvantage is that if the Spring Boot version is changed then you will have to remember to delete this library and add the new version.
Using the profile and instructions below, you can add a profile to maven that allows development in IntelliJ without changing things for other environments.
<!-- Leave original dependency as-is -->
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-tomcat</artifactId>
<scope>provided</scope>
</dependency>
</dependencies>
<profiles>
<!-- Enable this profile to run in IntelliJ. IntelliJ excludes provided dependencies from compile by default. -->
<profile>
<id>intellij</id>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-tomcat</artifactId>
<scope>compile</scope>
</dependency>
</dependencies>
</profile>
</profiles>
Click the Maven Projects button on the right side of IntelliJ, and under Profiles, select intellij.
Follow these steps:
On the top right side of intellij window, click the drop down and select edit configuration and a new window will open.
In this window, on top left side, click "+" button and select sprint boot.
Then add you main class, and other details as shown in screenshot.
Now Run the application.

Resources