Назначить docker контейнер внешней ссылкой через API - PullRequest
0 голосов
/ 08 марта 2020

У меня есть приложение, которое, помимо прочего, позволяет раскручивать docker контейнеров с нестандартным исполняемым кодом с помощью API, который также докеризуется.

Итак, из контейнера API я делаю:

exec(`curl --unix-socket /var/run/docker.sock -H "Content-Type: application/json" -d \'{"Image": "botimage", "ExposedPorts": {"${PORT}/tcp": {"HostPort": "${PORT}"}}, "HostConfig": {"Binds": ["${dirPath}/bots/api/bots/strategies:/usr/src/bots/strategies", "${dirPath}/bots/api/database:/usr/src/bots/database", "${dirPath}/postgres/data:/usr/src/bots/data"], "NetworkMode": "bitmex_backend"}, "PortBindings": { "${PORT}/tcp": [{ "HostPort": "${PORT}" }] }, "Env": ["TOPIC=${TOPIC}","BOTNAME=${BOT_NAME}","EXEC_ENV=${EXEC_ENV}","BITMEX_KEYS=${BITMEX_KEYS}","TIME_FRAME=${TIME_FRAME}","PORT=${PORT}"], "Cmd": ["node", "app.js"]}\' -X POST http:/v1.24/containers/create?name=${BOT_NAME}`,
  (err, stdout, stderr) => {
    if (err) {
      console.error(err)
      return;
    }

    var id = JSON.parse(stdout).Id;
    //  Would this work with the name too? 
    logEvent(LOG_LEVELS.info, RESPONSE_CODES.LOG_MESSAGE_ONLY, `Initializing containerised strategy `)
    exec(`curl --unix-socket /var/run/docker.sock -X POST http:/v1.24/containers/${id}/start`, (err, stdout, stderr) => {
      if (err) {
        console.error(err)
        return;
      }
    });
  });

И он снова динамически разворачивает новый контейнер.

Мне интересно, как я могу вывести этот новый контейнер из другого контейнера.

С локального хоста я могу просто сделать:

curl --unix-socket /var/run/docker.sock -X POST http:/v1.24/containers/test/stop
curl --unix-socket /var/run/docker.sock -X DELETE http:/v1.24/containers/test

Как только я попытаюсь сделать это из другого docker контейнера:

exec(`curl --unix-socket /var/run/docker.sock -X POST http:/v1.24/containers/test/stop`)
exec(`curl --unix-socket /var/run/docker.sock -X DELETE http:/v1.24/containers/test`)

Я получу следующая ошибка:

{Ошибка: команда не выполнена: curl - unix -socket /var/run/docker.sock -X POST http: /v1.24/containers/test/ stop curl: (7) Не удалось подключиться к серверу

at ChildProcess.exithandler (child_process.js:299:12)
at ChildProcess.emit (events.js:193:13)
at maybeClose (internal/child_process.js:999:16)
at Process.ChildProcess._handle.onexit (internal/child_process.js:266:5)   killed: false,   code: 7,  

сигнал: ноль, cmd:

Я думаю, что получение чего-то подобного должно быть адресуемым с помощью external_links done когда я строю контейнер.

Есть идеи, если это правильный вызов? или как я могу решить проблему? DeFF. выглядит как проблема с сетью.

1 Ответ

0 голосов
/ 09 марта 2020

Единственный способ позволить docker контейнерам управлять другими docker контейнерами, как вы описываете, - это открыть сокет docker (/var/run/docker.sock) для "управляющего" контейнера. Вы можете сделать это следующим образом:

darkstar:~$ docker run \
                  -v /var/run/docker.sock:/var/run/docker.sock \  
                  <my_image>
darkstar:~$ docker exec -u root -it <container id> /bin/bash

Теперь, когда root внутри контейнера, вы можете установить docker CLI (Это не является строго необходимым, в зависимости от того, как вы планируете манипулировать docker изнутри контейнера. Также я предполагаю, что Debian-подобен Linux, YMMV):

root@guest:/# apt-get update
root@guest:/# apt-get -y install apt-transport-https \
                                ca-certificates \
                                curl \
                                gnupg2 \
                                software-properties-common
root@guest:/# rel=$(. /etc/os-release; echo "$ID")
root@guest:/# curl -fsSL https://download.docker.com/linux/${rel}/gpg > /tmp/dkey
root@guest:/# apt-key add /tmp/dkey
root@guest:/# add-apt-repository \
             "deb [arch=amd64] https://download.docker.com/linux/${rel} \
              $(lsb_release -cs) stable"
root@guest:/# apt-get update
root@guest:/# apt-get -y install docker-ce

Я бы предложил сделать docker commit здесь (от хоста, а не из контейнера) для сохраните состояние изображения, чтобы вам не нужно было повторять вышеописанные шаги каждый раз, когда происходит перестройка.

Теперь контейнер должен иметь доступ к сокету:

root@guest:/# docker ps -a

CONTAINER ID        IMAGE                 COMMAND                  CREATED       ...
69340bc13bb2        my_image              "/sbin/tini -- /usr/…"   8 minutes ago ...

Будь это это хорошая идея или нет, является спорным. Я бы предложил не делать этого, если есть способ избежать этого. Это дыра в безопасности, которая по существу выбрасывает в окно некоторые основные преимущества использования контейнеров: изоляция и контроль над повышением привилегий.

...