2015-09-02 9 views
79

Я хотел бы запустить остановленный контейнер Docker с другой командой, поскольку команда по умолчанию сбрасывается - это означает, что я не могу запустить контейнер, а затем использовать «docker exec».Как запустить остановленный контейнер Docker с другой командой?

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

К счастью, я создал контейнер с опцией -it!

ответ

131

Найдите свой остановил контейнер ID

docker ps -a 

Commit остановленное контейнер:

Эта команда сохраняет измененную состояние контейнера в новое изображение user/test_image

docker commit $CONTAINER_ID user/test_image 

Start/запустить с другой записи точка:

docker run -ti --entrypoint=sh user/test_image 

Entrypoint Описание аргумента: https://docs.docker.com/engine/reference/run/#/entrypoint-default-command-to-execute-at-runtime

Примечание:

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

шаги для запуска остановленного контейнера были заимствованы здесь: (последний комментарий) https://github.com/docker/docker/issues/18078

+0

Это подразумевает изменение изображения? – nicooga

+0

нет, изображения доступны только для чтения. Он сохраняет измененное состояние контейнера в новое изображение. Test_image – Dmitriusan

+0

Я попытался сделать это с помощью изображения [Docker] (https://github.com/SonarSource/docker-sonarqube/blob/master/6.3.1/Dockerfile) 'sonarqube : 6.3.1 и, к сожалению, это приводит к ошибке **: 'docker: ссылка на разбор ошибок:« entrypoint = sh »не является допустимым репозиторием/тегом: неверный ссылочный формат.« – BigDong

70

Редактировать этот файл (соответствующий вашему остановленного контейнера):

vi /var/lib/docker/containers/923...4f6/config.json 

Изменить параметр «Path», чтобы указать на вашей новой команды, например,/Бен/Баш. Вы также можете установить параметр «Args» для передачи аргументов команды.

Перезапустите службу докер:

service docker restart 

Список ваших контейнеров и убедитесь, что команда изменилась:

docker ps -a 

Запустить контейнер и прикрепить к нему, теперь вы должны быть в вашей оболочке!

docker start -ai mad_brattain 

Работает на Fedora 22 с использованием Docker 1.7.1.

ПРИМЕЧАНИЕ: Если ваша оболочка не является интерактивной (например, вы не создали оригинальный контейнер с опцией -it), вы можете вместо этого изменить команду на «/ bin/sleep 600» или «/ bin/tail», f/dev/null ", чтобы дать вам достаточно времени, чтобы сделать« docker exec -it CONTID/bin/bash »другим способом получения оболочки.

+17

мои глаза. мои глаза. Я надеюсь, что это запрос функции где-нибудь, чтобы правильно это обработать в Docker. – gertvdijk

+0

мой bash не является интерактивным, он запускается и выходит сразу (выход 0) –

+2

@AlexeyStrakh вы можете попробовать запустить «/ usr/bin/sleep 600», а затем выполнить «docker exec -it/bin/bash», чтобы получить оболочку , Хотя я не уверен, как поместить параметры в эту переменную Path. В противном случае попробуйте найти другую команду, которая останется в живых достаточно долго, чтобы вы могли сделать exec, или посмотреть ответ от Dmitriusan. – aaa90210

-8

Я на самом деле не согласен с обоими из этих ответов. Если вы просто хотите посмотреть, что находится в контейнере, вы можете запустить эту команду, чтобы получить оболочку. Не нужно менять точку входа вообще или любые конфиги.

docker run -it <image_name> bash 
+9

Это не работает, так как оператор спрашивает о контейнере, а не о изображении. –

+0

Я полагаю, ваше право, но не вижу причин для этого. Вы можете подключать журналы к stdout, а 'docker logs --follow' предоставит вам то, что вам нужно. Другой альтернативой является использование команды выше, а затем запуск службы сбоев на этом изображении с помощью той же команды в файле docker и отладки оттуда. – deadbabykitten

+2

Команда run создает новый контейнер из изображения. Он не запускает остановленный контейнер. –

0

Не указано, выходит ли контейнер, только если ваш код сработает, и вам нужно посмотреть, что происходит в контейнере. Если это не выход, вот еще одно потенциальное решение.

Получить идентификатор контейнера с docker ps

docker exec -it 665b4a1e17b6 /bin/sh

Если точка входа установлена ​​на то проблемного, он также может быть изменено, как предложено в ответ Dmitriusan в. Следует также отметить, что вы можете прикрепить к любому запущенному контейнеру с помощью docker attach. Так много решений разных решений. Я просто не вижу необходимости фиксировать изображение. Это кажется ненужным.

Документы для Докер Exec - https://docs.docker.com/engine/reference/commandline/exec/

Docs для Докер присоединять - https://docs.docker.com/engine/reference/commandline/attach/

6

Добавить проверку в верхней части сценария Entrypoint

Docker действительно необходимо реализовать это в качестве новой функции, но вот еще один вариант обходного пути для ситуаций, в которых у вас есть точка входа, которая заканчивается после успеха или неудачи, что может затруднить отладку.

Если у вас еще нет сценария точки входа, создайте тот, который выполнит все команды, необходимые для вашего контейнера. Затем, в верхней части этого файла, добавьте эти строки в entrypoint.sh:

# Run once, hold otherwise 
if [ -f "already_ran" ]; then 
    echo "Already ran the Entrypoint once. Holding indefinitely for debugging." 
    cat 
fi 
touch already_ran 

# Do your main things down here 

Чтобы убедиться, что cat держит соединение, возможно, потребуется предоставить TTY. Я бегу контейнер с моим Entrypoint сценарий следующим образом:

docker run -t --entrypoint entrypoint.sh image_name 

Это заставит скрипт запускать один раз, создав файл, который указывает, что уже работать (в виртуальной файловой системе контейнера). Затем вы можете перезапустить контейнер для выполнения отладки:

docker start container_name 

При перезапуске контейнера файл already_ran будет найден, в результате чего сценарий Entrypoint в стойло с cat (который только ждет навсегда для ввода, который никогда не придет, но держит контейнер в живых). Затем можно выполнить отладку bash сессии:

docker exec -i container_name bash 

В то время как контейнер работает, вы можете также удалить already_ran и вручную запустить скрипт entrypoint.sh перезапускать его, если вам нужно отладить таким образом.

+1

Кроме того, вы можете сделать запуск точки входа '/ bin/sh' вместо' cat' - тогда вы всегда можете просто перезапустить. Ваше решение скалы! –

0

Запустите команду вручную внутри контейнера докера.

Я запускаю докер версии 7.03.1-ce, и я не могу найти config.json.

Я пытаюсь отредактировать файл config.v2.json, но он не работает, и мне не нужен метод фиксации, потому что я не хочу создавать новое изображение. Я нашел альтернативу, выполнив команду вручную внутри контейнера.

Запускать контейнер

docker start <container> 

Баш Доступ

docker exec -ti <container> bash 

команду Выполнить вручную

[email protected]<container_id># service <command> start 

или

docker exec -d <container> service <command> start 
#Note: run this in another terminal while docker exec is attach. 
+0

Похоже, вы задаете новый вопрос, а не пытаетесь ответить на этот вопрос. Вместо размещения здесь вы должны [задать вопрос] (https://stackoverflow.com/questions/ask). –

+0

Прошу прощения, если вы не поняли моего ответа. Английский язык - это не мой родной язык, но, чтобы обобщить мой ответ, если вы не хотите, чтобы метод фиксации выполнял вашу команду желания вручную в запущенном контейнере. –

+2

Как @NeilLunn говорит, это не поможет OP, который не может запустить контейнер (он сбой), поэтому нельзя использовать docker exec. Перечитайте его первое предложение: «Я хотел бы запустить остановленный контейнер Docker с другой командой, поскольку команда по умолчанию сбрасывается - значит * я не могу запустить контейнер, а затем использовать« docker exec »*.» (мой акцент) –

0

Я взял @ ответ Dmitriusan и сделал его в качестве псевдонима:

псевдоним Докер-бежать-предыдущая-контейнер = 'prev_container_id = "$ (докер пс -aq | голова -n1)»& & докер совершить "$ prev_container_id" "prev_container/$ prev_container_id" & & докер бег -это --entrypoint = Баш "prev_container/$ prev_container_id"»

Добавьте это в ваш файл ~/.bashrc алиасы , и вы будете иметь изящные новые docker-run-prev-container псевдонимов which'll высадить вас в оболочку в предыдущем контейнере.

Полезно для отладки не удался docker build с.

-3
docker container start <CONTAINER_ID> 
+0

OP хочет запустить контейнер с другой командой. – srigi

Смежные вопросы