- PVSM.RU - https://www.pvsm.ru -
Прочитав статью об упаковке JVM приложения в Docker [1], я остался в смятении. Я, как и любой разработчик, хочу чтоб мои волосы развевались на ветру контейнер собирался за одну команду, сразу, без лишних телодвижений. Чтобы конфигурация проекта и сборки была собрана в одном файле, и чтобы не было зависимостей от внешних систем.
Далее последует альтернативный способ сборки Java-приложений в Docker контейнер используя Maven.
Для сборки нам понадобится Java проект, Maven и немного терпения, чтоб все это завести.
В это раз, мы будем использовать Maven-плагин от fabric8io [2].
Предположим, что у нас микро-сервис, который упаковывается в jar-файл, содержащий main метод, который и надо запустить для старта приложения. Добавляем плагин в build секцию:
<plugin>
<groupId>io.fabric8</groupId>
<artifactId>docker-maven-plugin</artifactId>
<version>0.16.4</version>
<executions>
<execution>
<id>Build docker container</id>
<phase>package</phase>
<goals>
<goal>build</goal>
</goals>
</execution>
<execution>
<id>Push docker container</id>
<phase>deploy</phase>
<goals>
<goal>push</goal>
</goals>
</execution>
</executions>
<configuration>
<images>
<image>
<name>${project.artifactId}</name>
<registry>registry.io</registry>
<build>
<from>java:8</from>
<tags>
<tag>${project.version}</tag>
</tags>
<ports>
<port>8080</port>
</ports>
<cmd>
<shell>java -cp 'jars/*' com.myapp.MainClass '/config.file'</shell>
</cmd>
<assembly>
<basedir>/</basedir>
<inline>
<dependencySet>
<outputDirectory>jars</outputDirectory>
</dependencySet>
<files>
<file>
<source>${project.build.directory}/${project.build.finalName}.jar</source>
<outputDirectory>jars</outputDirectory>
</file>
<file>
<source>${project.basedir}/src/main/config/config.yml</source>
<outputDirectory>/</outputDirectory>
</file>
</files>
</inline>
</assembly>
</build>
</image>
</images>
</configuration>
</plugin>
И, в общем то, все. Разберем поподробнее, что у нас там написано.
В начале идёт типичное определение плагина с версией. Далее идёт определение в какие фазы луны сборки мы хотим собирать и пушить наш контейнер. В моем случае сборка контейнера (build) будет происходить во время упаковки проекта (phase: package).
Пуш (push) контейнера в репозиторий будет происходить во время фазы деплой (deploy).
<executions>
<execution>
<id>Build docker container</id>
<phase>package</phase>
<goals>
<goal>build</goal>
</goals>
</execution>
<execution>
<id>Push docker container</id>
<phase>deploy</phase>
<goals>
<goal>push</goal>
</goals>
</execution>
</executions>
Если это ваш случай, то секция исполнения схлопывается до следующей:
<executions>
<execution>
<id>Build & Push docker container</id>
<phase>deploy</phase>
<goals>
<goal>build</goal>
<goal>push</goal>
</goals>
</execution>
</executions>
Также можно перенести сбоку на фазу install. Может кто знает, как заставить Maven исполнять плагины в нужном порядке?
Определяем имя образа и репозиторий:
<name>${project.artifactId}</name>
<registry>registry.io</registry>
Если репозиторий не указан, то будет использоваться репозиторий Docker-а. Документация [3] для дальнейшего чтения.
Описание сборки образа осуществляется в секции <build>. По сути это отражение Docker файла в Maven.
from — базовый образ
tags — теги с которыми будет собран образ
ports — открытые порты
cmd — строка запуска, так же можно указать entryPoint, о все доступных опциях можно почитать в документации [4].
В моем примере:
<shell>java -cp 'jars/*' com.myapp.MainClass '/config.file'</shell>
Это типичная строка запуска Java приложения, завернутая в shell форму Docker-а, в представлении Maven-а.
assembly — самая интересная часть плагина. Она определяет, что будет упаковано в образ контейнера и как. Есть несколько вариантов как можно описать упаковку, я выбрал inline, но есть и другие варианты [5].
В примере, я хочу взять все зависимости проекта и сложить в папку «jars»:
<dependencySet>
<outputDirectory>jars</outputDirectory>
</dependencySet>
А так же, артефакт проекта, собственно наше приложение, туда же, а конфигурационный файл в корень контейнера.
<files>
<file>
<source>${project.build.directory}/${project.build.finalName}.jar</source>
<outputDirectory>jars</outputDirectory>
</file>
<file>
<source>${project.basedir}/src/main/config/config.file</source>
<outputDirectory>/</outputDirectory>
</file>
</files>
Подробнее о возможностях ассемблирования в документации [6], на этот раз Maven-а.
И все! В результате:
Несколько слов о плагине: разработка идет активно, мейнтейнер оперативно отвечает и охотно мерджит пул-реквесты.
» Сам плагин может ещё много чего: возможности [7]
» Пример проекта выложен на github-е [8]
Автор: osigida
Источник [9]
Сайт-источник PVSM.RU: https://www.pvsm.ru
Путь до страницы источника: https://www.pvsm.ru/java/193026
Ссылки в тексте:
[1] JVM приложения в Docker: https://habrahabr.ru/post/310530/
[2] fabric8io: https://github.com/fabric8io/docker-maven-plugin
[3] Документация: https://dmp.fabric8.io/#registry
[4] документации: https://dmp.fabric8.io/#misc-startup
[5] варианты: https://dmp.fabric8.io/#build-assembly
[6] документации: http://maven.apache.org/plugins/maven-assembly-plugin/examples/index.html
[7] возможности: https://dmp.fabric8.io/#maven-goals
[8] github-е: https://github.com/osigida/maven-docker-demo
[9] Источник: https://habrahabr.ru/post/311156/?utm_source=habrahabr&utm_medium=rss&utm_campaign=sandbox
Нажмите здесь для печати.