Как Maven работает с зависимостями при скачивании
Что проверяют
Понимаете ли вы, откуда Maven берёт артефакты и по какому правилу выбирает версию, когда одна библиотека приходит с разных сторон. Следом почти всегда просят объяснить конфликт версий и показать, как его найти.
Как отвечать
Опишите путь одной зависимости:
- координаты:
groupId:artifactId:version, иногда ещёclassifierиtype. По ним вычисляется путь к файлу в репозитории; - локальный репозиторий: сначала Maven смотрит в
~/.m2/repository(путь меняется вsettings.xml). Нашёл, значит в сеть не идёт; - удалённые репозитории: по умолчанию Maven Central из super POM, плюс свои
<repositories>. В компаниях обычно всё идёт через Nexus или Artifactory, прописанный как<mirror>вsettings.xml; - скачивание: сначала
.pomзависимости, чтобы узнать её собственные зависимости, затем сам.jarс проверкой контрольных сумм. Так рекурсивно строится граф транзитивных зависимостей; - выбор версии: правило «ближайший побеждает». Берётся версия, которая ближе к вашему проекту в дереве, а при равной глубине та, что объявлена первой. Самая новая не выбирается автоматически;
- управление:
dependencyManagementфиксирует версии, в том числе транзитивные, BOM подключается через<scope>import</scope>, лишнее отрезаетсяexclusions; - scope: зависимости со scope
testиprovidedтранзитивно не передаются, как и помеченныеoptional.
Про кеш: релизная версия скачивается один раз и больше не перепроверяется, SNAPSHOT по умолчанию проверяется раз в сутки. Флаг -U заставляет обновить снапшоты и повторить неудачные загрузки, -o включает офлайн-режим.
Диагностика: mvn dependency:tree, для жёсткой проверки правило dependencyConvergence в maven-enforcer-plugin.
Где спотыкаются
Говорят, что при конфликте Maven берёт самую свежую версию. Потом не могут объяснить NoSuchMethodError в рантайме: победила старая версия, стоявшая ближе.
Думают, что mvn clean чистит скачанные зависимости. Он удаляет только target.
Не знают про файлы .lastUpdated: неудачная загрузка кешируется, и Maven не повторяет её до конца интервала обновления, пока не запустить сборку с -U или не удалить каталог артефакта.