Контейнер Jenkins Docker не может загрузить артефакт в контейнер Nexus Docker

#maven #jenkins #docker-compose

#maven #дженкинс #docker-compose

Вопрос:

У меня есть следующая настройка для моей среды DevOps, организованная с помощью Docker Compose:

(упрощенный) docker-compose.yml :

 version: '3.7'
services:
  nexus:
    build: ./nexus/.
    expose:
      - 8081
    networks:
      - devops-network
  jenkins:
    build: ./jenkins/.
    expose:
      - 8080
    depends_on:
      - nexus
    networks:
      - devops-network
  nginx:
    image: nginx:1.19.5
    ports:
      - 80:80
    depends_on:
      - nexus
      - jenkins
    networks:
      - devops-network
networks:
  devops-network:
 

(упрощенный) nginx.conf :

 http {
    upstream docker-jenkins {
        server jenkins:8080;
    }
    upstream docker-nexus {
        server nexus:8081;
    }

    server {
        server_name  jenkins.homenetwork.dns;

        location / {
            proxy_pass http://docker-jenkins;
        }
    }

    server {
        server_name  nexus.homenetwork.dns;

        location / {
            proxy_pass http://docker-nexus;
        }
    }
}
 

Дженкинс может взаимодействовать с Nexus через сеть Docker. Если я войду в контейнер Jenkins, тогда ping nexus и curl http://nexus:8081 дайте мне положительные ответы (я получаю отзывы от Nexus).

Но когда я запускаю конвейер Jenkins с вложенным агентом Docker для Maven:

 pipeline {
    agent {
        docker {  // successfully pulls image
            image 'maven:3.6.3-openjdk-11'
            args '-v /root/.m2:/root/.m2'
        }
    }
    stages {
        stage('Maven build') {
            steps {
                mavenBuildStep()
            }
        }
        stage('Upload'){
            steps {
                withMaven(mavenSettingsConfig: 'cdb64ca9-d8e1-4d19-b486-e86c0ee75f50')
                    {
                        echo 'uploading Maven artifacts'
                        sh 'mvn deploy -DskipTests'   // fails because it can't find nexus
                    }

            }
        }
    }
}
 

и maven settings.xml с указанным выше идентификатором:

 <servers>
    <server>
        <id>nexus-snapshots</id>
        <username>jenkins</username>
        <password>${JENKINS_NEXUS_PASSWORD}</password>
    </server>
</servers>
 

and this in my pom.xml :

 <distributionManagement>
    <snapshotRepository>
        <id>nexus-snapshots</id>
        <url>http://nexus:8081/repository/maven-snapshots/</url>
    </snapshotRepository>
</distributionManagement>
 

then it says:

[ОШИБКА] Не удалось выполнить цель org.apache.maven.plugins:maven-deploy-plugin: 2.8.2: развертывание (по умолчанию-развертывание) в родительском проекте: не удалось получить удаленные метаданные … из / в nexus-snapshots (http://nexus:8081/repository/maven-snapshots /): Передача не удалась для http://nexus:8081/repository/maven-snapshots/…/1.0.0-SNAPSHOT/maven-metadata.xml : Неизвестный узел связи: Нетадрес, связанный с именем хоста

Когда я меняю URL-адрес репозитория в pom.xml на сетевой IP-адрес контейнера Nexus:

 <distributionManagement>
    <snapshotRepository>
        <id>nexus-snapshots</id>
        <url>http://172.26.0.2:8081/repository/maven-snapshots/</url>
    </snapshotRepository>
</distributionManagement>
 

затем истекает время ожидания:

[ОШИБКА] Не удалось выполнить цель org.apache.maven.plugins:maven-deploy-plugin:2.8.2: развертывание (по умолчанию-развертывание) в родительском проекте : … Не удалось подключиться к 172.26.0.2: 8081 [/ 172.26.0.2]: время ожидания соединения истекло

Что происходит? Я сопоставил демон Docker хоста с контейнером Jenkins setfacl -m user:jenkins:rw /var/run/docker.sock , поэтому он должен иметь возможность доступа к контейнеру Nexus? Когда я извлекаю изображение Docker в конвейере, изображение добавляется в мою хост-систему и его не нужно загружать снова в следующий раз, так что, похоже, все в рабочем состоянии. Это потому, что «Docker внутри Docker» не имеет доступа к devop-network ?

В идеале я мог бы вместо этого указать http://nexus.homenetwork.dns/repository/maven-snapshots/ URL-адрес в своем pom, но это кажется невозможным. У кого-нибудь есть опыт работы с такого рода настройками?

Обновить

Чтобы подтвердить свои подозрения, я использовал agent any вместо агента Docker в конвейере Jenkins и установил maven в контейнер Jenkins. При такой настройке запуск конвейера Jenkins корректно загружает снимки с URL http://nexus:8081/repository/maven-snapshots/ .

Это неплохое решение, но мне остается только гадать, как заставить его работать с агентом Docker из чистого любопытства.

Комментарии:

1. Мой первый вопрос: почему у вас есть прокси перед вашим менеджером репозитория nexus? Какой цели служит nginx?

2. @khmarbaise Является ли красивый URL-адрес правильным ответом на ваш вопрос? Я впервые пытаюсь настроить среду devops, поэтому я могу делать избыточные / странные вещи. Эти контейнеры размещены на моем ноутбуке, пока я разрабатываю на своем настольном ПК. Я хотел бы перейти к удобочитаемому URL-адресу и получить доступ к приложениям с моего ноутбука. Если я не использую прокси, мне нужно будет размещать приложения на разных портах с локального хоста моего ноутбука. С nginx все находится под localhost: 80.

Ответ №1:

Эй, у меня была такая же проблема, и я уже довольно давно искал решение. Сначала я тоже этого не понял. Однако в конце я понял, что это довольно простая вещь для докеров. Агент docker в основном запускает новый контейнер docker. Если вы хотите, чтобы он получил доступ к другому, уже существующему, используя только «nexus», вы должны добавить его в ту же мостовую сеть. В вашем случае вам необходимо добавить

 pipeline { agent { docker {
...
args  '--net="devops-network"'
}
}
 

По крайней мере, это решило проблему для меня.