Как исключить зависимость от родительского проекта в Maven?
Например, у меня есть 2 проекта Maven. Один из них - "родитель проекта". Другой - "проект-ребенок". Очевидно, что "project-child" является подпроектом "project-parent" .
"project-parent" имеет зависимость от log4j. Но я хочу исключить его из "проекта-ребенка". Есть ли способ?
Можно сказать, что я должен переместить log4j из "project-parent" в "project-child". Это совершенно правильно. Но предположение: я НЕ МОГУ ИЗМЕНИТЬ POM-проект-родительский.
Спасибо заранее.
Ответы
Ответ 1
Я думаю, что в Maven2 невозможно достичь этого, потому что это то, что наследует POM для
, Однако есть один трюк, о котором я могу думать:
Предположим, вы имеете право загружать артефакт в свой внутренний репозиторий артефактов. Вы можете создать пустой JAR, развернуть его как log4j: log4j с явно ненормальной версией (например, log4j: log4j: 9999). Добавьте такую зависимость в проект-ребенок. Тогда он будет переопределять зависимость родительского объекта от зависимости от пустого JAR-факта.
Ответ 2
Я не знаю способа фактического исключения зависимости, но вы можете исключить его из целевого дистрибутива, но это немного взломан. Вам нужно изменить область зависимости на то, что вы можете исключить в конечном дистрибутиве.
Итак, скажите, что у моего родителя была зависимость от junit 4.8, в моем пом, вы говорите:
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>4.8</version>
<scope>provided</scope>
</dependency>
Итак, мы меняем область действия. Для объяснения того, как это работает, см. Мой ответ на NoClassDefFoundError: org/junit/AfterClass при обработке аннотаций. К сожалению, это не влияет на сборку, но когда вы копируете зависимости для окончательного распространения, вы можете использовать элемент конфигурации excludeScope
, чтобы не копировать зависимость в окончательный дистрибутив:
<plugin>
<artifactId>maven-dependency-plugin</artifactId>
<executions>
<execution>
<id>copy-libs</id>
<phase>package</phase>
<goals>
<goal>copy-dependencies</goal>
</goals>
<configuration>
<outputDirectory>${project.build.directory}/lib</outputDirectory>
<excludeScope>provided</excludeScope>
</configuration>
</execution>
Ответ 3
Если я понимаю вопрос, вам нужно что-то вроде следующего. Он затягивает зависимость и исключает зависимость от добавления в список зависимостей. Часто это используется, если вы хотите вставить более новую версию пакета вместо той, что указана в другом пакете.
<dependency>
<groupId>log4j</groupId>
<artifactId>log4j</artifactId>
<version>1.2.15</version>
<exclusions>
<exclusion>
<groupId>com.sun.jmx</groupId>
<artifactId>jmxri</artifactId>
</exclusion>
...
</exclusions>
...
Если вы говорите об отношениях <parent>
, то я не уверен, что есть способ сделать это. Можете ли вы перейти от <parent>
к <dependency>
?
Ответ 4
Я встретил тот же вопрос, что и вы.
В моем проекте позвоните родительскому pom parent.pom. parent определил log4j, slf4j следующим образом:
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-api</artifactId>
<version>${slf4j-api.version}</version>
</dependency>
<dependency>
<groupId>log4j</groupId>
<artifactId>log4j</artifactId>
<version>${log4j.version}</version>
</dependency>
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>jcl-over-slf4j</artifactId>
<version>${slf4j-api.version}</version>
</dependency>
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-log4j12</artifactId>
<version>${slf4j-log4j12.version}</version>
</dependency>
дочерний проект вызывает некоторую зависимость в child.pom. Но я не хочу зависимости log4j-1.2.x и хочу увеличить версию slf4j.
Итак. Я добавляю зависимость родительского
<dependency>
<groupId>parent</groupId>
<artifactId>myartifactId</artifactId>
<version>${my parent version}</version>
</dependency>
и используйте исключения, чтобы удалить log4j
<dependency>
<groupId>parent</groupId>
<artifactId>myartifactId</artifactId>
<version>${my parent version}</version>
<exclusions>
<exclusion>
<groupId>log4j</groupId>
<artifactId>log4j</artifactId>
</exclusion>
</exclusions>
</dependency>
и явно добавить зависимость slf4j и log4j2 в дочернем pom
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-api</artifactId>
<version>1.7.6</version>
</dependency>
<dependency>
<groupId>org.apache.logging.log4j</groupId>
<artifactId>log4j-slf4j-impl</artifactId>
<version>2.8.2</version>
</dependency>
<dependency>
<groupId>org.apache.logging.log4j</groupId>
<artifactId>log4j-api</artifactId>
<version>2.8.2</version>
</dependency>
<dependency>
<groupId>org.apache.logging.log4j</groupId>
<artifactId>log4j-core</artifactId>
<version>2.8.2</version>
</dependency>
<dependency>
<groupId>com.lmax</groupId>
<artifactId>disruptor</artifactId>
<version>3.3.4</version>
</dependency>
затем используйте mvn dependency: tree, чтобы отобразить список зависимостей, все еще видите log4j
[INFO] +- org.apache.kafka:kafka_2.10:jar:0.8.2.0:compile
[INFO] | +- com.yammer.metrics:metrics-core:jar:2.2.0:compile
[INFO] | +- org.scala-lang:scala-library:jar:2.10.4:compile
[INFO] | +- org.apache.zookeeper:zookeeper:jar:3.4.6:compile
[INFO] | | +- org.slf4j:slf4j-log4j12:jar:1.7.5:compile
[INFO] | | +- log4j:log4j:jar:1.2.17:compile
ну, добавьте исключения на эту зависимость... удалите этого парня.
<dependency>
<groupId>org.apache.kafka</groupId>
<artifactId>kafka-clients</artifactId>
<version>0.10.1.1</version>
<exclusions>
<exclusion>
<groupId>log4j</groupId>
<artifactId>log4j</artifactId>
</exclusion>
</exclusions>
</dependency>
затем снова запустите команду, чтобы проверить список зависимостей. ОК! ясно ~
Надеюсь, что может вам помочь: >
Ответ 5
Один из хакерских способов добиться этого - указать зависимость в проекте-ребенке, но с областью "test" (или любой доступной с небольшим весом областью). Это "скроет" область, указанную в родительском проекте, чтобы она была доступна только для проверки кода и недоступна для не-тестового кода как при компиляции, так и во время выполнения.
Я наткнулся на эту ошибку, главным образом, по ошибке. В моем случае у моего проекта-ребенка был дочерний проект с зависимостью "компиляции", в то время как у родителя проекта была указана такая же зависимость (фактически унаследована от прародителя) с "предоставленной" областью. project-child был исполняемым, однако это зависело от проекта-брата, и поэтому NoClassDefFoundError был запущен во время выполнения из проекта-брата, поскольку использовался путь класса времени выполнения проекта-child, который не включал зависимость "предоставленный". Я исправил это, переместив "скомпилировать" зависимость от проекта-брата к родительскому проекту, чтобы "компиляция" "спрятала" предоставленную.
Ответ 6
Переопределите зависимость (в дочернем помпе) с системой scope
, указывающей на пустую банку:
<dependency>
<groupId>dependency.coming</groupId>
<artifactId>from.parent</artifactId>
<version>0</version>
<scope>system</scope>
<systemPath>${project.basedir}/empty.jar</systemPath>
</dependency>
Банку может быть только пустой файл jar:
touch empty.txt
jar cvf empty.txt
Ответ 7
Мне удалось исключить переходную зависимость от родительского пом. Повторно импортируя его в <dependencymanagement>
и затем устанавливая исключение для зависимости, которую я хотел удалить. как это например:
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<version>${spring-boot.version}</version>
<scope>test</scope>
<exclusions>
<exclusion>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
</exclusion>
</exclusions>
</dependency>