управление зависимостями с maven - PullRequest
9 голосов
/ 07 января 2010

В последнее время я стал большим поклонником Maven для управления циклом сборки для моего приложения. Однако я столкнулся с некоторыми грубыми углами в управлении зависимостями Maven. Мне интересно, являются ли это ограничениями инструмента и парадигмы, необходимыми пороками управления зависимостями, или я просто неправильно использую инструмент.

  1. Первое - это вопрос переходных зависимостей. Насколько я понимаю, если вы предоставите зависимость, Maven, в свою очередь, найдет все зависимости этой зависимости. Это здорово, но для многих моих зависимостей это не сработало. Например, в том числе Hibernate в моем проекте:

    <dependency>
        <groupId>org.hibernate</groupId>
        <artifactId>hibernate-core</artifactId>
        <version>3.3.2.GA</version>
    </dependency>
    

    Результатом является отсутствие зависимости от slf4j. Мне нужно вручную добавить эту зависимость, которая, как я предполагал, будет работой Maven. То же самое касается весны. Если я добавлю Spring-MVC в качестве зависимости, разве мне не нужно добавлять все основные зависимости сервлета (потому что Spring-MVC будет нуждаться в этом)? Я имею в виду библиотеки сервлетов, jsp, jstl.

  2. Второе - управление хранилищами. Maven поставляется с основным репозиторием по умолчанию, но я обнаружил, что во многих случаях этот репозиторий не обновлен. Например, если вы хотите spring3, вам нужно вручную добавить репозиторий springsource, а если вы хотите hibernate 3.5+, вы должны добавить репозиторий jboss. Похоже, что это побеждает точку автоматического управления зависимостями, когда вам приходится искать правильные репозитории самостоятельно. Эта охота скоро усложняется. Например, чтобы добавить Spring3, вам может потребоваться репо с весенним выпуском, репо с внешними пружинами и репо с весенними вехами.

  3. Тесно связана с номером 2, это гарантирует, что у вас есть правильная версия артефакта. Я был сожжен несколько раз, включая неправильные версии зависимых артефактов для данного артефакта. Например, неправильная версия apis сервлета / jsp / jstl для spring3 или неправильная версия apis персистентности / аннотации для hibernate. Репозитории заполнены многими версиями, некоторые с запутанными названиями, такими как productx-3.ga, productx-3-rc1, productx-3-SNAPSHOT, productx-3-cr, product-3-beta и т. Д. Некоторые из них очевидны (rc = релиз-кандидат), но это может сбивать с толку, пытаясь определить порядок этих версий.

  4. Наконец, проблема типа зависимости. Я, наверное, просто недостаточно хорошо это понимаю, но многие артефакты репо относятся к типу «pom», а не «jar». Несколько раз я добавлял банку зависимостей в свой проект только для того, чтобы во время сборки выяснить, что банку репо на самом деле не существует (например, org.hibernate-ejb3-persistence в репозитории jboss).

С некоторыми экспериментами я обычно могу заставить работать сборку, но сложно ли вообще управлять зависимостями? Я по-прежнему предпочитаю этот подход ручному добавлению jar-файлов в свой проект, но мне было бы интересно узнать, как улучшить мои навыки управления зависимостями maven.

Ответы [ 4 ]

14 голосов
/ 08 января 2010

Не могу ответить на все части вопроса, но о некоторых из них:

  • Некоторые переходные зависимости помечены optional, поэтому люди, которые не нуждаются в этих функциях, не будут загружать их, но люди, которым это необходимо, должны явно устанавливать их в своих poms.

  • Репозиторий Maven Central содержит только выпуски. Следовательно, он не содержит Hibernate 3.5 (который является бета-версией), а также не содержит Spring 3 до его выпуска (кстати, вам больше не нужно указывать специальный репозиторий Spring для Spring 3 - release) уже в Maven Central)

  • slf4j - это особый вид зависимости - его поведение во время выполнения зависит от того, какую реализацию slf4j вы используете. Поэтому, чтобы контролировать его поведение, вы должны явно указать реализацию slf4j

  • Об управленческих навыках: чтобы получить полезную информацию для ведения вашего pom.xml, вы можете использовать mvn dependency:tree (особенно с -Dverbose=true) и mvn dependency:analyze. Также может быть полезно проверить pom-файл вашей зависимости, чтобы найти дополнительные зависимости.

3 голосов
/ 08 января 2010

Первое - это вопрос переходных зависимостей.Насколько я понимаю, если вы предоставите зависимость, Maven, в свою очередь, найдет все зависимости этой зависимости.Это здорово, но для многих моих зависимостей это не сработало.(...)

Как уже указывалось, некоторые зависимости могут быть помечены как необязательно (и не переносятся транзитивно).Идея состоит в том, что некоторые зависимости используются только для определенных функций и не потребуются, если эта функция не используется.Если пользователь хочет использовать функциональность, связанную с необязательной зависимостью, он должен будет повторно объявить эту необязательную зависимость в своем собственном проекте.Так что это просто работает как задумано:)

Вторым является управление репозиториями.Maven поставляется с основным репозиторием по умолчанию, но я обнаружил, что во многих случаях этот репозиторий не обновлен.(...)

Даже если идея концепции центрального репо благородна, вы не можете объективно ожидать, что она будет содержать все банки в мире.Одна из наиболее очевидных причин заключается в том, что загрузка артефактов в центральный репозиторий просто требует времени, а ресурсы не бесконечны.И поскольку таким компаниям, как RedHat JBoss или SpringSource или Sun или даже мне, нужна гибкость, реактивность (одним словом, контроль), неудивительно, что они используют свой собственный репозиторий.И, на самом деле, я очень счастлив, что они разоблачают их.Но на самом деле, проекты должны задокументировать, где найти свои артефакты, если они недоступны в central .На всякий случай вам может пригодиться Как найти зависимости от общедоступных репозиториев Maven? полезно.В корпоративной среде лучший способ справиться с этим - создать централизованный (корпоративный) прокси-сервер хранилища.См. на этой странице для таких решений.

Тесное отношение к номеру 2 гарантирует, что у вас есть правильная версия артефакта.(...)

Извините, но вам нужно немного узнать, что вы делаете.Проект не может догадаться, какую версию JSTL вы собираетесь использовать.Затем, что касается различных версий артефактов, соглашение об именах, используемое проектами, не имеет ничего общего с maven, это выбор проекта / поставщика (за исключением SNAPSHOT, который специально обрабатывает maven).FWIW, часто используемые схемы включают в себя: M1 = Milestone 1, RC1 = Release Candidate 1, GA = Общая доступность (финальная версия), CR = Customer Release (часто релиз с исправлением ошибок).Вы также можете увидеть альфа, бета.Это действительно зависит от жизненного цикла и соглашения проекта (хотя здесь нет ничего необычного).

Наконец, проблема типа зависимость.Я, наверное, просто недостаточно хорошо это понимаю, но многие артефакты репо относятся к типу «pom», а не «jar».(...)

Я думаю, что вам действительно не хватает опыта.Похоже, вы боретесь с зависимостями, в то время как для меня все идет гладко :) Возможно, использование поисковой системы хранилища поможет.

1 голос
/ 08 января 2010

Вы также можете исключить некоторые транзитивные зависимости, как в следующем примере:

<dependency>
        <groupId>log4j</groupId>
        <artifactId>log4j</artifactId>
        <version>1.2.15</version>
        <exclusions>
            <exclusion>
                <groupId>javax.mail</groupId>
                <artifactId>mail</artifactId>
            </exclusion>
            <exclusion>
                <groupId>javax.jms</groupId>
                <artifactId>jms</artifactId>
            </exclusion>
            <exclusion>
                <groupId>com.sun.jdmk</groupId>
                <artifactId>jmxtools</artifactId>
            </exclusion>
            <exclusion>
                <groupId>com.sun.jmx</groupId>
                <artifactId>jmxri</artifactId>
            </exclusion>
        </exclusions>
    </dependency>

Я не помню деталей, но, по-видимому, обнаруживались некоторые другие зависимости, когда мы хотели использовать log4j, и мы не интересовались (или не нуждались) в них в нашем случае, поэтому мой коровий помощник просто сказал: «Нет, спасибо к этим "и это работает.

0 голосов
/ 20 октября 2012
  1. Транзитивные зависимости существуют только в том случае, если они были явно закодированы в POM ваших прямых зависимостей. Иногда вы на самом деле не хотите их, потому что есть альтернативные реализации или вы используете только часть библиотеки, и вы не хотите перетаскивать зависимости для вещей, которые вы на самом деле не используете.

  2. Вы используете менеджер хранилища, такой как Nexus , не так ли? Я советую вам настроить его, даже если вы пишете один.

  3. Я считаю, что Мейвен действительно помогает с этой проблемой. Я не хотел бы выполнять эту методику проб и ошибок с FTP-сайтов и страниц загрузки.

  4. Да, я тоже это ненавижу: -)

Читайте книгу ! Я действительно узнал большую часть того, что знаю из этой другой книги , но, учитывая, что она исходит от тех же людей, я ожидаю, что они будут довольно взаимозаменяемыми.

...