Настроить Docker для работы с Maven и Gradle? - PullRequest
0 голосов
/ 03 мая 2020

Я новичок в docker и впервые пробую контейнеризацию.

Видел Java проектов на Github, которые разработчики настроили как проекты gradle и maven.

Создана следующая структура проекта:

HelloDocker
│
├── Dockerfile
├── README.md
├── build.gradle
├── gradle
│   └── wrapper
│       ├── gradle-wrapper.jar
│       └── gradle-wrapper.properties
├── gradlew
├── gradlew.bat
├── mvnw
├── mvnw.cmd
├── pom.xml
├── settings.gradle
└── src
    ├── main
    │   ├── java
    │   │   └── com
    │   │       └── hellodocker
    │   │           ├── HelloDockerApplication.java
    │   │           ├── controller
    │   │           │   └── HelloController.java
    │   │           └── model
    │   │               └── User.java
    │   └── resources
    │       ├── application.properties
    │       ├── static
    │       └── templates
    └── test
        └── java
            └── com
                └── hellodocker
                    └── HelloDockerApplicationTests.java

Maven pom. xml:

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>
    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>2.2.6.RELEASE</version>
        <relativePath/> <!-- lookup parent from repository -->
    </parent>
    <groupId>com.hellodocker</groupId>
    <artifactId>hellodocker</artifactId>
    <version>0.0.1-SNAPSHOT</version>
    <name>hellodocker</name>
    <description>Spring Boot Docker Example</description>

    <properties>
        <java.version>11</java.version>
    </properties>

    <dependencies>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-test</artifactId>
            <scope>test</scope>
            <exclusions>
                <exclusion>
                    <groupId>org.junit.vintage</groupId>
                    <artifactId>junit-vintage-engine</artifactId>
                </exclusion>
            </exclusions>
        </dependency>
    </dependencies>

    <build>
        <plugins>
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
            </plugin>
        </plugins>
    </build>

</project>

build.gradle:

plugins {
    id 'org.springframework.boot' version '2.2.6.RELEASE'
    id 'io.spring.dependency-management' version '1.0.9.RELEASE'
    id 'java'
}

group = 'com.hellodocker'
version = '0.0.1-SNAPSHOT'
sourceCompatibility = '11'

repositories {
    mavenCentral()
}

dependencies {
    implementation 'org.springframework.boot:spring-boot-starter-web'
    testImplementation('org.springframework.boot:spring-boot-starter-test') {
        exclude group: 'org.junit.vintage', module: 'junit-vintage-engine'
    }
}

test {
    useJUnitPlatform()
}

Dockerfile:

FROM openjdk:11
VOLUME /tmp
ADD target/hellodocker-0.0.1-SNAPSHOT.jar hellodocker-app.jar
ENTRYPOINT ["java", "-jar", "/hellodocker-app.jar" ]

Как вы можете видеть, это зависит от проекта, встроенного в jar-файл из maven (из-за зависимости каталога target в строке 3 (сборка gradle) полагаться / зависеть от каталога build/lib.


Вопрос (ы):

  1. Можно настроить файл Docker для размещения обоих типов сценариев сборки ?

  2. Это плохая практика (например, с точки зрения непрерывной интеграции DevOps) полагаться на два сценария сборки? Например, должны ли Java проекты, которые будут развернуты в CircularCI, Jenkins, Travis и / или GitLab используют только один тип сценариев сборки DSL?

Причина, по которой я sh использую оба, заключается в том, чтобы будущие разработчики, которые получают доступ к моим проектам, могли легко выбрать либо gradle, либо maven (конечно, это создает трудности при поддержке двух разных сценариев сборки, в будущее) ...

Ответы [ 3 ]

0 голосов
/ 03 мая 2020

Выбор - Немезида принятия решения, и кажется, что вы проигрываете эту битву. Выберите один инструмент сборки, который каждый может легко набросать asp, и структурируйте свой конвейер CI / CD вокруг этого инструмента. Я не вижу, чтобы оба помогали кому-либо; это кажется более запутанным, чем полезным.

Большинство инструментов CI / CD настроены на автоматическое определение типа создаваемого вами проекта и выполнение большинства базовых c команд для достижения sh цели тестирования CI .

Это означает, что в проектах gradle они обычно запускаются gradle check, а для maven - mvn test.

Наличие обоих в одном проекте приводит к путанице как для инструмент CI и для вашей команды, и в конечном итоге один из них станет раздутым в вашем проекте, потому что все будут стремиться к одной системе сборки, которую они все любят / понимают.


Что касается вашего вопроса о Docker, вы должны начать с изображения, которое уже создано для одного из инструментов, а затем установить другой инструмент внутри этого нового образа. Я бы начал с изображения gradle, а затем apk add maven, чтобы получить Maven.

0 голосов
/ 03 мая 2020

Механически, есть только один путь через Dockerfile, и он не поддерживает условные выражения, кроме условных выражений оболочки в одиночных командах RUN. Вы не можете условно COPY файл, основываясь, например, на том, существует он или нет.

Как показывают другие ответы на этот вопрос, я бы выбрал один способ построения изображение, и я бы, вероятно, go, чтобы удалить управляющие файлы другой системы сборки. Это позволяет избежать проблем, когда официальные сборки используют Maven, но тот разработчик, который использует Gradle, не обновил файл POM. Если вам все еще нужны эти файлы, они будут в истории контроля версий.

Если вы действительно не можете выбирать, вы можете обойти это с помощью многоэтапной сборки ... но это довольно хакерски. (Обратите внимание, что сама оболочка logi c пытается найти файл jar сама по себе вдвое дольше, чем весь Dockerfile, который у вас был ранее.)

# First stage just finds the jar file wherever it may be.
FROM busybox AS staging
WORKDIR /staging

# Copy the _entire_ build context here.
COPY ./ ./

# Now we can look for the jar file using shell commands.
RUN if [ -f target/hellodocker-0.0.1-SNAPSHOT.jar ]; then \
      cp target/hellodocker-0.0.1-SNAPSHOT.jar /hellodocker-app.jar; \
    else if [ -f build/lib/hellodocker-0.0.1-SNAPSHOT.jar ]; then \
      cp build/lib/hellodocker-0.0.1-SNAPSHOT.jar /hellodocker-app.jar; \
    else \
      echo "Could not find jar file" >&2; \
      exit 1; \
    fi

# This is the actual image, which is essentially what you had before.
FROM openjdk:11
COPY --from=staging /hellodocker-app.jar /hellodocker-app.jar
CMD ["java", "-jar", "/hellodocker-app.jar"]
0 голосов
/ 03 мая 2020

Кажется плохой практикой иметь Maven и Gradle, так как вы должны поддерживать согласованность используемых версий зависимостей в обеих.

Что касается Dockerfile, то он будет одинаковым для обоих, поскольку Dockerfile просто берет артефакт, созданный любым из них.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...