Surya Teja Vemparala
Surya Teja Vemparala

Reputation: 499

Import and Dependency Management in Maven

I was learning about "import" scope in maven and did a sample project below,

Project_1 POM file :

    <dependencyManagement>  
    <dependencies>
        <dependency>
          <groupId>junit</groupId>
          <artifactId>junit</artifactId>
          <version>3.8.1</version>
          <scope>test</scope>
        </dependency>
      </dependencies> 
    </dependencyManagement>
</project>

project_2 POM file :

<parent>
<groupId>com.sample</groupId>
  <artifactId>project1</artifactId>
  <version>1.0-SNAPSHOT</version>
</parent>    
...
...
<dependencyManagement>  
      <dependencies>
        <dependency>
          <groupId>com.sample</groupId>
        <artifactId>project1</artifactId>
        <version>1.0-SNAPSHOT</version>
           <type>pom</type>
          <scope>import</scope>
        </dependency>
      </dependencies>
    </dependencyManagement>

However, this throws an error stating that the JUnit packages are not available in Project2. When I remove the dependencyManagement tag from project_1 POM file. Everything works fine. But as per the maven docs,

This scope is only supported on a dependency of type pom in the section. It indicates the dependency to be replaced with the effective list of dependencies in the specified POM's section. Since they are replaced, dependencies with a scope of import do not actually participate in limiting the transitivity of a dependency.

I've done as mentioned in the docs, what went wrong here?

Upvotes: 4

Views: 9555

Answers (2)

ck1
ck1

Reputation: 5443

It looks like you're trying to use a bill-of-materials (BOM) POM and import that.

Your Project_1 is the BOM POM in this case, and you include all your project's dependencies in the <dependencyManagement> element. It looks like you're doing this correctly.

To import a BOM POM in your project however, you need both <dependencyManagement> and <dependencies>.

For example, your Project_2 pom.xml should include:

<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/maven-v4_0_0.xsd">
    <modelVersion>4.0.0</modelVersion>

    <groupId>com.sample</groupId>
    <artifactId>project1</artifactId>
    <version>1.0-SNAPSHOT</version>
    <packaging>jar</packaging>

    <dependencyManagement>
        <dependencies>
            <!-- Imports the bill-of-materials POM. -->
            <dependency>
                <groupId>com.sample</groupId>
                <artifactId>bom</artifactId>
                <version>1.0-SNAPSHOT</version>
                <type>pom</type>
                <scope>import</scope>
            </dependency>
        </dependencies>
    </dependencyManagement>

    <dependencies>
        <!-- Add a dependency from the BOM POM.
        Note: no version or scope is required, it's inherited from the BOM POM! -->
        <dependency>
            <groupId>junit</groupId>
            <artifactId>junit</artifactId>
        </dependency>
    </dependencies>
</project>

Here is the BOM POM definition for the above example:

<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/maven-v4_0_0.xsd">
    <modelVersion>4.0.0</modelVersion>

    <groupId>com.sample</groupId>
    <artifactId>bom</artifactId>
    <version>1.0-SNAPSHOT</version>
    <packaging>pom</packaging>

    <dependencyManagement>
        <dependencies>
            <dependency>
                <groupId>junit</groupId>
                <artifactId>junit</artifactId>
                <version>3.8.1</version>
                <scope>test</scope>
            </dependency>
        </dependencies>
    </dependencyManagement>
</project>

There is documentation about this on the Apache Maven website (search for "bom").

Update:

BOM POMs and parent POMs are similar but different. BOM POMs are meant purely for importing dependencies into your project. Parent POMs are meant for multi-module projects, and allow you to define Maven coordinates, plugins, and dependencies that will be inherited by all of modules using the parent POM.

Here is an example of using an inherited dependency from a parent POM. Note that there are several elements included here that don't make sense in a BOM POM.

<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/maven-v4_0_0.xsd">
    <modelVersion>4.0.0</modelVersion>

    <parent>
        <groupId>com.sample</groupId>
        <artifactId>parent</artifactId>
        <version>1.0-SNAPSHOT</version>
    </parent>

    <artifactId>project1</artifactId>
    <packaging>jar</packaging>

    <dependencies>
        <!-- Inherited from the parent POM. -->
        <dependency>
            <groupId>junit</groupId>
            <artifactId>junit</artifactId>
        </dependency>
    </dependencies>
</project>

Here is the parent POM definition for the above example:

<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/maven-v4_0_0.xsd">
    <modelVersion>4.0.0</modelVersion>

    <groupId>com.sample</groupId>
    <artifactId>parent</artifactId>
    <version>1.0-SNAPSHOT</version>
    <packaging>pom</packaging>

    <modules>
        <module>child1</module>
        <module>child2</module>
    </modules>

    <dependencyManagement>
        <dependencies>
            <dependency>
                <groupId>junit</groupId>
                <artifactId>junit</artifactId>
                <version>3.8.1</version>
                <scope>test</scope>
            </dependency>
        </dependencies>
    </dependencyManagement>

    <dependencies>
        <!--Global dependencies...-->
    </dependencies>

    <build>
        <pluginManagement>
            <!--Plugins...-->
        </pluginManagement>
    </build>
</project>

Upvotes: 4

karthik006
karthik006

Reputation: 941

First Make sure you are using Maven version 2.0.9 or later that supports this functionality. Second your Project1 Pom.Xml is missing the attribute "packaging" Make sure your packaging and type are of the same name so that it inherits all the dependencies.

Also your artifact Id and group ID has to be the same as your project 1's Pom.xml file for it to import the dependency

When in doubt refer to this link https://maven.apache.org/guides/introduction/introduction-to-dependency-mechanism.html#Importing_Dependencies

Upvotes: 0

Related Questions