Как запустить docker-compose up -d при запуске системы?

115

Чтобы контейнеры автоматически запускались при запуске, я попытался добавить команду:

cd directory_has_docker-compose.yml && docker-compose up -d в /etc/rc.local.

но затем после перезагрузки машины контейнеры не работают.

Как запустить docker-compose up -dпри запуске системы?

user39544
источник
3
используйте --restart alwaysили --restart unless-stoppedили в docker-compose.yml используйте restart: always-> Ссылка . Но, возможно, не сработало на некоторых контейнерах!
Беньямин Джафари

Ответы:

133

Когда мы используем crontabили устаревший /etc/rc.localфайл, нам нужна задержка (например sleep 10, в зависимости от машины), чтобы убедиться, что системные службы доступны. Обычно systemd(или upstart) используется для управления запуском служб при загрузке системы. Вы можете попробовать использовать для этого аналогичную конфигурацию:

# /etc/systemd/system/docker-compose-app.service

[Unit]
Description=Docker Compose Application Service
Requires=docker.service
After=docker.service

[Service]
Type=oneshot
RemainAfterExit=yes
WorkingDirectory=/srv/docker
ExecStart=/usr/local/bin/docker-compose up -d
ExecStop=/usr/local/bin/docker-compose down
TimeoutStartSec=0

[Install]
WantedBy=multi-user.target

Или, если вы хотите запустить без -dфлага:

# /etc/systemd/system/docker-compose-app.service

[Unit]
Description=Docker Compose Application Service
Requires=docker.service
After=docker.service

[Service]
WorkingDirectory=/srv/docker
ExecStart=/usr/local/bin/docker-compose up
ExecStop=/usr/local/bin/docker-compose down
TimeoutStartSec=0
Restart=on-failure
StartLimitIntervalSec=60
StartLimitBurst=3

[Install]
WantedBy=multi-user.target

Измените WorkingDirectoryпараметр, указав путь к документированному проекту. И включите автоматический запуск службы:

systemctl enable docker-compose-app
Олег Белостоцкий
источник
Есть ли простой способ проверить, работает ли он без перезапуска малины?
dmigo
3
Это самый элегантный ответ ИМО
кузын
2
@dmigo, systemctl start docker-compose-appи systemctl status docker-compose-appя думаю, это то, что вы ищете.
HectorJ
не сработало у меня, когда я бежал, systemctl start docker-compose-appстолкнулся с этим:Job for docker-compose-app.service failed because the control process exited with error code. See "systemctl status docker-compose-app.service" and "journalctl -xe" for details
Беньямин Джафари
1
@dmigo: протестируйте запуск вашей службы с помощью:, service docker-compose-app startстатус с service docker-compose-app status, остановка сservice docker-compose-app stop
BarryPye
96

Вы должны иметь возможность добавить:

restart: always 

для каждой службы, которую вы хотите перезапустить, в файле docker-compose.yml

MaxiReglisse
источник
6
Имейте в виду, что они должны быть запущены при перезагрузке, поэтому не останавливайте их вручную перед перезагрузкой.
Tom
некоторые службы, такие как Nginx, даже не запускаются с этой опцией.
Benyamin Jafari
15
Это правильный ответ на вопрос. Существует продуманный способ перезапуска контейнеров, зачем заниматься cron и другими способами изобретать велосипед.
Таха Рехман Сиддики
Это правильный ответ. Когда вы начнете использовать Kubernetes вместо cron, вы будете счастливы, что использовали его.
pferrel
9
@TahaRehmanSiddiqui Обратите внимание, что в нем restart: alwaysесть несколько серьезных ошибок: например, при перезагрузке не будут прикреплены крепления хоста. На мой взгляд, велосипед лучше изобретать, если имеющееся колесо квадратное.
okdewit 08
74

Если ваш docker.serviceвключен при запуске системы

$ sudo systemctl enable docker

и ваши услуги в вашем docker-compose.ymlесть

restart: always

все службы запускаются при перезагрузке системы, если вы запустите команду ниже только один раз

docker-compose up -d
Масуд Ватандуст
источник
2
это должно быть самое элегантное решение
Карл Чунг
35

Я пробовал restart: always, он работает в некоторых контейнерах (например, php-fpm), но я столкнулся с проблемой, что некоторые контейнеры (например, nginx) все еще не перезагружаются после перезагрузки.

Решил проблему.

crontab -e

@reboot (sleep 30s ; cd directory_has_dockercomposeyml ; /usr/local/bin/docker-compose up -d )&
user39544
источник
2
Почему за этот ответ проголосовали против? Ответ бесполезен? Это неправильно в каком-то смысле? Комментарий будет полезен, чтобы дать ответчику и другим понять, что не так.
Ayushya
5
Вы должны с подозрением относиться к голому сну, поскольку он вводит недетерминированное поведение: martinfowler.com/articles/…
giorgiosironi
@giorgiosironi в этом случае подойдет сон. Запуск контейнера в любом случае должен уметь обрабатывать недетерминированное поведение.
z0r
4
Он также обеспечивает задержку до 30 секунд, которая может не понадобиться.
giorgiosironi
@ z0r спать не в порядке! Сон может «работать», но любая последовательность запуска должна быть детерминированной. Службы Linux используют зависимости для обеспечения доступности таких вещей, как сеть и т. Д., До их запуска. Вам следует поступить так же.
colm.anseo
25

Используйте перезапуск: всегда в вашем файле компоновки докеров.

Docker-compose up -dснова запустит контейнер из образов. Используется docker-compose startдля запуска остановленных контейнеров, никогда не запускает новые контейнеры из образов.

nginx:   
    restart: always   
    image: nginx   
    ports:
      - "80:80"
      - "443:443"   links:
      - other_container:other_container

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

Vaseem007
источник
1
Возможно, вы не захотите использовать always, но возможно unless-stopped. Другие варианты - on-failureи no. Это известно как политика перезапуска .
Пол
5

В дополнение к user39544ответу еще один тип синтаксиса для crontab -e:

@reboot sleep 60 && /usr/local/bin/docker-compose -f /path_to_your_project/docker-compose.yml up -d
TitanFighter
источник
У меня это сработало в марте 2018 года на RPi3 под управлением Raspian. Я работал crontab -eкак пользователь pi, а pi был членом группы docker ...
Скотт Вейрс