Краткое знакомство с Maven
Фрейворк Maven предназначен для автоматизации сборки проектов. Эта статья о том, как начать с ним работу и как забобраться в файле описания проекта pom.xml.
Maven — инструмент для автоматизации сборки проектов. С ним работают в основном Java-разработчики, хотя есть плагины для интеграции с C/C++, Ruby, Scala, PHP и другими языками. В статье будут рассмотрены особенности и область применения Maven, описан процесс установки и начала работы, а также разобрана структура файла описания проекта.
Назначение и особенности
Собрать на Java проект уровня «Hello, world!» можно и с помощью командной строки. Но чем сложнее разрабатываемое ПО и чем больше оно использует сторонних библиотек и ресурсов, тем сложнее будет команда для сборки. Maven разработан для облегчения этой работы.
Одна из главных особенностей фреймворка — декларативное описание проекта. Это значит, что разработчику не нужно уделять внимание каждому аспекту сборки — все необходимые параметры настроены по умолчанию. Изменения нужно вносить лишь в том объёме, в котором программист хочет отклониться от стандартных настроек.
Ещё одно достоинство проекта — гибкое управление зависимостями. Maven умеет подгружать в свой локальный репозиторий сторонние библиотеки, выбирать необходимую версию пакета, обрабатывать транзитивные зависимости.
Разработчики также подчёркивают независимость фреймворка от ОС. При работе из командной строки параметры зависят от платформы, но Maven позволяет не обращать внимания на этот аспект.
При необходимости систему сборки можно настроить под собственные нужды, используя готовые плагины и архетипы. А если ничего подходящего не нашлось — можно написать свои.
В этой статье мы будем работать с Maven с помощью командной строки, однако этот фреймворк также интегрирован в Eclipse, IntelliJ IDEA, NetBeans и другие IDE.
Установка, настройка и создание стандартного проекта
Скачать Maven можно с официальной страницы проекта. Там же вас познакомят с минимальными требованиями — на машине должен быть установлен JDK, а также потребуется свободное место на диске, около 500 мегабайт. Это место нужно не для самой установки, оно будет использовано для создания локального репозитория.
На странице скачивания вы найдёте несколько разных архивов, для первого раза лучше использовать готовые бинарники. Исходники потребуются, если захочется всё сломать покопаться в Maven.
Архив можно распаковать в любое удобное место. После этого нужно добавить путь к папке bin из распакованного архива в переменную среды PATH . В Windows нужно зайти в настройки параметров системы (вызывается комбинацией клавиш Win+Pause или щелчком правой кнопкой мыши по ярлыку «Мой / Этот компьютер» -> «Свойства»), и выбрать пункт «Дополнительные параметры системы». В правом нижнем углу нажмите кнопку «Переменные среды». Выберите переменную PATH , нажмите «Изменить», в открывшемся окне — «Создать» и добавьте путь. Обратите внимание, путь должен вести именно к папке bin .
В ОС на основе Unix переменную среды можно добавить консольной командной:
export PATH=/opt/apache-maven-3.6.0/bin:$PATH
Проверить, всё ли сделано правильно, можно с помощью консольной команды mvn -v . Вы должны увидеть что-то подобное:
Apache Maven 3.6.0 (97c98ec64a1fdfee7767ce5ffb20918da4f719f3; 2018-10-24T21:41:47+03:00) Maven home: C:\apache-maven-3.6.0\bin\.. Java version: 10.0.1, vendor: Oracle Corporation, runtime: C:\Program Files\Java\jdk-10.0.1 Default locale: ru_RU, platform encoding: Cp1251 OS name: "windows 10", version: "10.0", arch: "amd64", family: "windows"
Создаём папку для нового проекта и переходим в неё. Далее создаём новый проект. Для этого в консоли выполните команду:
mvn archetype:generate -DgroupId=com.mycompany.app -DartifactId=my-app -DarchetypeArtifactId=maven-archetype-quickstart -DarchetypeVersion=1.4 -DinteractiveMode=false
Выглядит довольно сложно, поэтому разберём её по порядку.
archetype:generate это так называемая цель. Она указывает Maven, что нужно создать проект из архетипа. Дальше с помощью -D мы указываем определённые параметры генерации.
- groupId=com.mycompany.app указывает на разработчика ПО, там вы можете указать доменное имя своей компании.
- artifactId=my-app — название проекта. Maven оперирует так называемыми артефактами. Это приложения, плагины, архетипы и другие проекты. И ваша разработка также будет считаться артефактом.
- archetypeArtifactId=maven-archetype-quickstart указывает, какой архетип использовать в качестве шаблона для создания приложения. Как видите, это тоже артефакт. Указанный архетип создаст простой проект, сгенерирует структуру каталогов и даже заботливо положит в папку исходников программу «Hello, world!», чтобы вам не пришлось самому писать её в двухсотый раз.
- archetypeVersion=1.4 указывает на версию артефакта «архетип».
- interactiveMode=false отключает создание проекта в интерактивном режиме. Вы можете запустить цель archetype:generate без параметров, и Maven предложит установить параметры в процессе генерации. В данном случае нам это не нужно. Кстати, отключить интерактивный режим можно параметром -B . Полный список параметров для mvn можно получить по команде mvn -h .
Выполнив команду, Maven сгенерирует следующую структуру проекта:
my-app |-- pom.xml `-- src |-- main | `-- java | `-- com | `-- mycompany | `-- app | `-- App.java `-- test `-- java `-- com `-- mycompany `-- app `-- AppTest.java
Исходники нашего проекта будут лежать в папке src/main/java (и сейчас там уже есть автоматически сгенерированный файл), но нам сейчас интереснее файл pom.xml в корневом каталоге. Это и есть тот самый файл описания проекта, на основе которого осуществляются все операции Maven. Он написан на языке POM, входящим в семейство XML:
4.0.0 com.mycompany.app my-app 1.0-SNAPSHOT my-app http://www.example.com UTF-8 1.7 1.7 junit junit 4.11 test
Разберёмся, что всё это значит.
Что значат теги в pom.xml
Тег project является базовым и содержит всю информацию о проекте. В заголовке указана информация, необходимая Maven для понимания файла pom.xml . Тег modelVersion указывает на текущую версию POM. Эти два тега обычно генерируются автоматически, менять их не нужно.
Затем идёт информация, формирующая уникальный идентификатор проекта, теги groupId и artifactId . Её мы задавали выше при генерации из архетипа. Тег version тоже входит в эту группу. Он обычно генерируется и обновляется автоматически. После номера версии идёт суффикс -SNAPSHOT . Это означает, что проект находится в стадии разработки. В процессе выпуска ПО фреймворк уберёт этот суффикс, а если разработка продолжится — автоматически увеличит номер версии. Вместе эти три тега позволяют однозначно идентифицировать артефакт.
name содержит отображаемое имя артефакта, а url — ссылку на сайт. Поскольку сайт не задан при генерации, pom.xml содержит напоминание об этом в виде комментария. Кроме того, можно добавить краткое описание в description . Эти три тега зачастую используются при формировании документации.
Дальше мы видим блок properties . Здесь указаны особые настройки, такие как кодировка файла и используемая версия компилятора Java. Без этого блока можно обойтись, положившись на настройки по умолчанию.
Следом идёт очень важный блок dependencies . В нём описываются все используемые в проекте зависимости. Каждую необходимо выделить тегом dependency и указать уникальные идентификационные данные: groupId , artifactId и version . Maven сам подгрузит транзитивные зависимости. Кроме того, с помощью тега scope можно указать этапы, на которых будет использован артефакт. Сейчас в pom.xml всего одна зависимость — артефакт JUnit, библиотека для модульного тестирования на Java, которая будет использоваться только на стадии тестирования.
Кстати, это хороший повод поговорить о жизненном цикле проекта. Maven выполняет сборку последовательными фазами. Приводим их названия на английском, так как они используются в качестве команд.
- Проверка — validate . Фреймворк проверяет, корректен ли проект и предоставлена ли вся необходимая для сборки информация.
- Компиляция — compile . Maven компилирует исходники проекта.
- Тест — test . Проверка скомпилированных файлов. В нашем случае будет использована библиотека JUnit.
- Сборка проекта — package . По умолчанию осуществляется в формате JAR. Этот параметр можно изменить, добавив в project тег packaging .
- Интеграционное тестирование — integration-test . Maven обрабатывает и при необходимости распаковывает пакет в среду, где будут выполняться интеграционные тесты.
- Верификация — verify . Артефакт проверяется на соответствие критериям качества.
- Инсталляция — install . Артефакт попадает в локальный репозиторий. Теперь его можно использовать в качестве зависимости.
- Размещение проекта в удалённом репозитории — deploy , — финальная стадия работы.
Эти фазы упорядочены и выполняются поочерёдно. Если необходимо собрать проект, система последовательно проведёт оценку, компиляцию и тестирование, и только после этого сборку. Помимо этого есть две фазы, выполняющиеся отдельно, только прямой командой. Это очистка — clean , удаляющая предыдущие сборки, и создание документации для сайта — site .
Закончим рассмотрение pom.xml секцией build . Она не является обязательной, в данном pom.xml в неё включены плагины из архетипа, однако можно обойтись и без них. Плагинов для Maven тысячи, освоившись с применением фреймворка вы сможете сами подобрать себе необходимые.
В проектах чуть серьёзнее, чем вычисление факториала, приходится использовать внешние ресурсы. Maven способен автоматически обрабатывать файлы ресурсов и размещать их в сборке проекта. Для этого их нужно разместить в папке src/main/resources . Файлы будут упакованы с сохранением внутренней структуры каталогов. Если же по какой-то причине нужно переопределить каталог, используйте вложенные теги resources , resource , directory в секции build :
src/main/another_resources_directory
Итак, с файлом описания мы разобрались. Попробуем собрать проект. Для этого перейдём в корневую папку и выполним команду нужной фазы, mvn package . Получим отчёт о сборке:
[INFO] ----------------------< com.mycompany.app:my-app >---------------------- [INFO] Building my-app 1.0-SNAPSHOT [INFO] --------------------------------[ jar ]--------------------------------- [INFO] [INFO] --- maven-resources-plugin:3.0.2:resources (default-resources) @ my-app --- [INFO] Using 'UTF-8' encoding to copy filtered resources. [INFO] skip non existing resourceDirectory C:\javaProjects\new_project\my-app\src\main\resources [INFO] [INFO] --- maven-compiler-plugin:3.8.0:compile (default-compile) @ my-app --- [INFO] Changes detected - recompiling the module! [INFO] Compiling 1 source file to C:\javaProjects\new_project\my-app\target\classes [INFO] [INFO] --- maven-resources-plugin:3.0.2:testResources (default-testResources) @ my-app --- [INFO] Using 'UTF-8' encoding to copy filtered resources. [INFO] skip non existing resourceDirectory C:\javaProjects\new_project\my-app\src\test\resources [INFO] [INFO] --- maven-compiler-plugin:3.8.0:testCompile (default-testCompile) @ my-app --- [INFO] Changes detected - recompiling the module! [INFO] Compiling 1 source file to C:\javaProjects\new_project\my-app\target\test-classes [INFO] [INFO] --- maven-surefire-plugin:2.22.1:test (default-test) @ my-app --- [INFO] [INFO] ------------------------------------------------------- [INFO] T E S T S [INFO] ------------------------------------------------------- [INFO] Running com.mycompany.app.AppTest [INFO] Tests run: 1, Failures: 0, Errors: 0, Skipped: 0, Time elapsed: 0.217 s - in com.mycompany.app.AppTest [INFO] [INFO] Results: [INFO] [INFO] Tests run: 1, Failures: 0, Errors: 0, Skipped: 0 [INFO] [INFO] [INFO] --- maven-jar-plugin:3.0.2:jar (default-jar) @ my-app --- [INFO] Building jar: C:\javaProjects\new_project\my-app\target\my-app-1.0-SNAPSHOT.jar [INFO] ------------------------------------------------------------------------ [INFO] BUILD SUCCESS [INFO] ------------------------------------------------------------------------ [INFO] Total time: 20.670 s [INFO] Finished at: 2019-02-17T02:25:07+03:00 [INFO] ------------------------------------------------------------------------
Теперь в корневом каталоге проекта вы обнаружите папку target, а в ней готовый файл my-app-1.0-SNAPSHOT.jar .
Запустите команду java -cp target/my-app-1.0-SNAPSHOT.jar com.mycompany.app.App — вы должны увидеть «Hello World!».
Поздравляем! Вы собрали проект с помощью Maven. Для более детального изучения инструмента советуем обратить внимание на эти книги и материалы.
Maven — жизненный цикл сборки
К примеру нам нужно создать jar проекта. Чтобы его создать набираем:
mvn package
Но перед созданием jar-файла будут выполняться все предыдущие фазы compile и test, а фазы integration-test, install, deploy не выполнятся. Если набрать
mvn deploy
, то выполнятся все приведённые выше фазы.
2. Фазы clean и site
Особняком стоят фазы clean и site. Они не выполняются, если специально не указаны в строке запуска.
clean — удаление всех созданных в процессе сборки артефактов: .class, .jar и др. файлов. В простейшем случае результат — просто удаление каталога target.
site — предназначена для создания документации.
Т.к. команда mvn понимает когда ему передают несколько фаз, то для сборки проекта создания документации «с нуля» выполняют:
mvn clean package site
- Преимущества и недостатки Maven
- Установка Maven
- Файл pom.xml
- Репозитории
- Плагины Maven
- Задания
Различия между «mvn clean package» и «mvn clean install»
При работе с Maven, инструментом для управления проектами на Java, часто используются команды «mvn clean package» и «mvn clean install». Они кажутся похожими, так как обе команды компилируют исходный код, выполняют тесты и упаковывают результат в jar или war файл. Однако между ними есть важное отличие.
Команда «mvn clean package» удаляет все файлы, созданные во время предыдущего сбора проекта (это делает часть «clean»), затем компилирует исходный код, выполняет тесты и упаковывает результат в jar или war файл (это делает часть «package»). Готовый артефакт остается внутри целевой директории проекта.
В отличие от этого, команда «mvn clean install» делает все то же самое, но еще и копирует упакованный файл в локальный репозиторий Maven, что позволяет использовать его как зависимость в других проектах на той же машине.
Таким образом, основное различие между этими командами в том, что «mvn clean install» делает артефакт доступным для других локальных проектов, в то время как «mvn clean package» просто упаковывает проект в файл, но не делает его доступным вне проекта.
Важно помнить, что если артефакт не предназначен для использования в других проектах, лучше использовать «mvn clean package», чтобы избежать ненужного засорения локального репозитория Maven.
Часть 4. Основы Maven


Этот материал — часть цикла “Введение в Enterprise-разработку”. Предыдущие статьи:
- о сети;
- об архитектуре ПО;
- о протоколах HTTP/HTTPS.
Maven — инструмент для управления и сборки проектов — настоящий помощник Java-программиста. Он облегчает жизнь девелоперу на всех стадиях работы: от создания структуры проекта и подключения необходимых библиотек до развертывания продукта на сервере. При работе с любым фреймворком придется использовать Maven. Поэтому давай сегодня разберем его основные функции и посмотрим, как их нужно использовать.
Пошаговая установка Maven
- Для начала нужно установить Maven, скачав его по этой ссылке.
- Далее необходимо распаковать скачанный архив и установить переменной окружения M2_HOME ссылку на местонахождение распакованного архива. Например, C:\Program Files\maven\
- Чтобы проверить, что все установилось, в командной строке пропиши: mvn -version
- Если отобразится информация о версии Maven, Java и т.д., все готово к работе.
- Теперь открой IntelliJIDEA и создай новый проект. В первом же окне выбери Maven:

- Нажми Next и заполни следующее диалоговое окно:

- Далее стандартно создай проект в необходимом месте. После того, как проект создался, обрати внимание на его структуру:

Это cтандартная структура для Maven-проекта :
- в папке src/main/java содержатся java-классы;
- в src/main/resources — ресурсы, которые использует наше приложение (HTML-страницы, картинки, таблицы стилей и тд);
- src/test — для тестов.
Еще обрати внимание на файл под название pom.xml . Это и есть главный файл для управления Мавеном . Все описание проекта содержится здесь. Пока там не слишком много информации, но сейчас мы будем ее добавлять.
Управление зависимостями в Maven
Возможно, ты встречал словосочетание “менеджер зависимостей” или “dependency manager”. Мавен все это умеет. Благодаря Мавену тебе не нужно тратить кучу времени на поиски нужной библиотеки в интернете, качать ее, а потом подключать к проекту: достаточно добавить необходимую в список зависимостей Мавена. Зависимости записываются в XML-ноду dependencies Скажем, тебе в проекте нужна библиотека Apache Commons IO для упрощенной работы с файлами. Чтобы добавить библиотеку, напиши пять строк в pom.xml:
commons-io commons-io 2.6
Теперь твой pom.xml должен выглядеть так:
4.0.0 example.com example 1.0-SNAPSHOT commons-io commons-io 2.6
После этого разреши IntelliJ IDEA импортировать зависимость (диалоговое окно должно появиться в правом нижнем углу). Теперь библиотека готова к использованию:
import org.apache.commons.io.FileUtils; import java.io.File; public class TestMaven < public static void main(String[] args) < File tempDirectory = FileUtils.getTempDirectory(); >>
- На сайте библиотеки. Если нам нужен Apache Commons IO, переходим на официальный сайт, выбираем вкладку Dependency Information. Здесь есть вся необходимая информация — ее можно просто скопировать и добавить в наш раздел dependencies.
- В Maven-репозитории. В поиске введи “apache commons io”, и ты увидишь все доступные версии библиотеки. После выбора нужной, просто скопируй:
commons-io commons-io 2.6
Виды Maven-репозиториев
Стоит еще раз упомянуть Мавен-репозиторий, потому что их на самом деле у нас два — внешний (глобальный) и локальный, у тебя на компьютере. Все библиотеки, которые ты добавляешь в свои проекты, сохраняются в локальном репозитории. Когда Maven добавляет необходимую зависимость в проект, он сначала проверяет локальный репозиторий на наличие такой библиотеки, и только если не находит ее там — обращается к внешнему. Как видишь, можно использовать Мавен для добавления зависимостей, но это не все, что он умеет делать.
Сборка Java-проекта с помощью Maven
Возможно, новичку эта возможность покажется бессмысленной. Зачем это нужно, если есть IDE? Но нет! Во-первых, на сервере, на котором придется собирать приложение, может не быть не то что среды разработки, но и графического интерфейса. Во-вторых, на больших проектах Мавен лучше справляется с задачами по сборке проекта. Поэтому не будем томить себя ожиданием, а рассмотрим процесс сборки приложения с использованием Maven.
Фазы
Процесс построения приложения называют жизненным циклом Maven-проекта, и состоит он из фаз (phase). Посмотреть на них ты можешь в IDEA, нажав на Maven>example>Lifecycle в правом верхнем углу:
Как видишь, существует 9 фаз:
- clean — удаляются все скомпилированные файлы из каталога target (место, в котором сохраняются готовые артефакты);
- validate — идет проверка, вся ли информация доступна для сборки проекта;
- compile — компилируются файлы с исходным кодом;
- test — запускаются тесты;
- package — упаковываются скомпилированные файлы (в jar, war и т.д. архив);
- verify — выполняются проверки для подтверждения готовности упакованного файла;
- install — пакет помещается в локальный репозиторий. Теперь он может использоваться другими проектами как внешняя библиотека;
- site — создается документация проекта;
- deploy — собранный архив копируется в удаленный репозиторий.
Все фазы выполняются последовательно: нельзя запустить, скажем, четвертую фазы, пока не завершены фазы 1-3. Выполнить запуск фазы можно двумя способами:
- через командную строку: mvn package

- используя Intellij IDEA:
До запуска package выполняются фазы validate, compile, test. Исключение — фаза clean. Ее желательно вызывать перед каждой новой сборкой проекта. Фазы можно перечислить через пробел: mvn clean package.
Также у каждой фазы есть пре- и пост-фазы: например, pre-deploy, post-deploy, pre-clean, post-clean, но используются они довольно редко. Кроме этого, у каждой фазы есть цели (goal). Стандартные цели заложены по умолчанию, дополнительные добавляются Maven-плагинами. Иногда во время какой-то фазы нужно выполнить дополнительный функционал. Для этого существуют Maven-плагины. Список официальных плагинов можно посмотреть на сайте Мавена. Но знай, что еще есть много пользовательских плагинов, которые можно найти на сторонних ресурсах. Ну и естественно, при какой-то экзотической необходимости, у тебя всегда остается возможность написать такой плагин самому .
Плагины
Чтобы добавить Мавен-плагин в проект, его описание, аналогично зависимостям, нужно поместить в pom.xml в тег
4.0.0 example.com example 1.0-SNAPSHOT com.soebes.maven.plugins uptodate-maven-plugin 0.2.0 dependency validate commons-io commons-io 2.6
Мы все так же можем продолжать работу над нашим проектом. Но давай попробуем поменять версию Apache Commons IO на 2.0 и запустить сборку проекта. Получим: [ERROR] Failed to execute goal com.soebes.maven.plugins:uptodate-maven-plugin:0.2.0:dependency (default) on project example: There is a more up-to-date version ( 2.6 ) of the dependency commons-io:commons-io:2.0 available. -> [Help 1] Здесь у нас ошибка сборки, вызванная плагином. В сообщении к ошибке указано, что мы используем 2.0 версию при наличии 2.6. Вообще, Мавен очень полезный инструмент. Возможно, поначалу он покажется трудным в использовании, но практикуйся, создавай свои проекты под управлением Мавена, и через некоторое время ты будешь очень доволен результатом. В этой статье нарочно упущено много деталей о Мавене — мы сконцентрировались на самом необходимом. Но совершенству нет предела: почитать больше о Maven можно на официальном сайте продукта. Часть 5. Сервлеты. Пишем простое веб-приложение Часть 6. Контейнеры сервлетов Часть 7. Знакомство с паттерном MVC (Model-View-Controller) Часть 8. Пишем небольшое приложение на spring-boot