spring boot project as dependency inside another spring-boot project - spring-boot

I have a spring boot project(project-lib) which I am including as maven dependency in another spring boot project(my-project).
now the project-lib uses logback and i want to exclude the logback dependency in my-project.
Also currently project-lib is defined as dependency with classifier jar-with-dependencies
Is it possible to define project-lib as normal dependency instead of jar-with-dependencies.
I tried to define it as normal dependency assuming it will download all the required dependencies as project-lib/pom.xml has already defined the required dependencies to run project-lib but it did not work that way.
part of pom.xml of my-project
<dependency>
<groupId>com.xyz/groupId>
<artifactId>project-lib</artifactId>
<version>0.0.4-SNAPSHOT</version>
<classifier>jar-with-dependencies</classifier>
</dependency>

Related

Spring Boot autoconfigure and its dependencies

I checked the source code of module spring-boot-autoconfigure
It has configurations classes for plenty of technologies : data, redis, cassandra, JPA, LDAP etc...
How can this module can compile properly without including all theses technologies dependencies jar in its POM ?
If I take the example of HibernateJpaAutoConfiguration class :
It uses beans/classes from other Spring modules like spring-orm :
import org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean;
However spring-boot-autoconfigure has no dependency to spring-orm in its POM. So how is compilation possible ?
This is possible because they apply Maven's concept of optional dependencies:
Optional dependencies are used when it's not possible (for whatever reason) to split a project into sub-modules. The idea is that some of the dependencies are only used for certain features in the project and will not be needed if that feature isn't used. (...) However, since the project cannot be split up (again, for whatever reason), these dependencies are declared optional. If a user wants to use functionality related to an optional dependency, they have to redeclare that optional dependency in their own project.
In Maven, it would usually look like this:
<dependency>
<groupId>sample.ProjectA</groupId>
<artifactId>Project-A</artifactId>
<version>1.0</version>
<optional>true</optional>
</dependency>
In this example, the project is compiled with Project-A. However, Project-A is not shared as transitive dependency.
The developers of Spring Boot use Gradle instead of Maven. They wrote their own Gradle plugin to replicate this behavior. The result looks something like this:
dependencies {
...
optional("org.springframework:spring-orm")
(see spring-boot-autoconfigure/build.gradle)

Dependency listed in pom file not found in deployed project

I asked a question here that I think I may have found the root of. I have a Spring Boot app using a datasource, net.sourceforge.jtds.jdbc.Driver, that is supposed to be included transitively by Spring Boot 2.0.2 with spring-boot-starter-jpa. However, when I run
jar tf my.jar | grep jtds
the driver class isn't found (we don't have a maven executable on the server to list the classpath). Everything I do to inspect the classpath reflects that the jar isn't there.
I've done this in 2 scenarios: 1) When I didn't explicitly add the jar to my pom, I got the error reported in my previous post. 2) When I do add it explicitly to the pom, I get this error:
java.lang.IllegalStateException: Cannot load driver class: net.sourceforge.jtds.jdbc.Driver
Can someone tell me what's going on?? I am confounded as to why this class can't be found and loaded.
Please mind, that in the Spring Boot Parent POM the jtds dependency is only included in test scope.
If you want to use classes of this dependency also in your production code, please change the Maven scope to compile.
Ok, the problem was solved by adding the dependency with a runtime scope.
In child pom where jar is packaged, you should have
spring-boot-maven-plugin. and dependency as below:
<dependency>
<groupId>net.sourceforge.jtds</groupId>
<artifactId>jtds</artifactId>
</dependency>
In parent pom :
<dependency>
<groupId>net.sourceforge.jtds</groupId>
<artifactId>jtds</artifactId>
<version>${jtds.version}</version>
</dependency>

Maven/Spring multi module project logging

I am trying to convert a huge maven/spring webapp to a multi module project.
Logging is implemented with this method (http://docs.spring.io/spring/docs/4.0.2.RELEASE/spring-framework-reference/htmlsingle/#overview-logging-slf4j) in the huge project. What is the correct way to do this in a maven multi module project? Is it necessary to define this in every pom.xml or only in my main pom.xml.
My main pom.xml defines this dependency:
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-framework-bom</artifactId>
<version>4.0.2.RELEASE</version>
<type>pom</type>
<scope>import</scope>
</dependency>
Is it possibly to exclude commons-logging on this dependency?
Update:
The project structure:
Parent Project:
Project A: jar
Project B: jar
Project C: war
Project D: war
All projects using parts of the Spring framework. I am using SLF4J for logging. What is the correct way for including SLF4J in this project setup with maven?
It should only be necessary to exclude commons-logging from "spring-core", but some third-party libraries also include it, so that isn't always enough. You could try using Spring Boot starters to build up your Spring dependencies (even if you aren't using other Boot features), since the default logging system is logback and commons-logging has been carefully excluded.

Eclipse (STS) MVC 3.0.5 + Tiles 2.2.2 project dependency management issue

For some reason I cannot use maven or gradle dependecy management. I am trying to use Tiles with Spring MVC, I get the following Exception on tcserver startup:
java.lang.NoClassDefFoundError: org/apache/tiles/startup/BasicTilesInitializer
Here is my dependencies folder:
Also Eclipse points out this Error in my layout.jsp
The tag handler class for
"tiles:insertAttribute" (org.apache.tiles.jsp.taglib.InsertAttributeTag) was not found on the Java Build
Path
Can anyone point out what am I missing?
You put the SOURCE jars in you project lib folder. But you need to use the normal once with the compiled classes.
tiles-core-2.2.2.jar instead of tiles-core-2.2.2-sources.jar
If you use maven to manage dependency then add below to your pom.
<dependency>
<groupId>org.apache.tiles</groupId>
<artifactId>tiles-core</artifactId>
<version>2.2.2</version>
</dependency>
Else Download following jars and add it to /WEB-INF/lib
tiles-core.2.2.2.jar
tiles-api.2.2.2.jar
and also add this transitive dependency as tiles use on Slf4j
slf4j-jdk14.1.5.8.jar

Updating from Spring 3.0.5 to Spring 3.1.2 does not include aspectjrt as a dependency

I am updating from Spring 3.0.5 to Spring 3.1.2 and while updating spring security core is also updated to 3.1.2 which in turn has dependency on aspectjrt (mentioned in its pom) but after updating to 3.1.2 if i generate dependency tree using
dependency:tree
it does not list aspectjrt in the tree but if i generate the same tree using version 3.0.5 aspectjrt is listed in the dependency tree.
Also, as previously mentioned I have already verified that aspectjrt dependency exists in both poms (version 3.0.5 & 3.1.2).
Since aspectjrt in not listed as a dependency my code is not compiled as it requires classes from aspectjrt.
If i explicitly inlude aspectjrt dependency in my pom my code compiles successfully.
Does anybody have any idea why this issue is occuring after updating to 3.1.2? Why aspectjrt is not inluded as a dependency after updating to 3.1.2
Is there any workaround for this or i will have to work by including aspectjrt as explict dependency in my pom.
AspectJ is declared as optional dependency in spring POM. Which means that AspectJ is required to build Spring JAR but is not required to build your project when you include Spring as dependency. If you need AspectJ functionality, include it in your POM.
I have solved the issue. This is the expected behavior as spring security core 3.0.5 aspectjrt is not optional but in spring securoty core 3.1.2 they have marked aspectjrt as optional.
So,if you are using some piece of aspectjrt in your code you will have to include aspectjrt dependency in your pom.
Hope that helps.

Resources