Я начну с признания, что я довольно новичок в Docker, и, возможно, я подхожу к этой проблеме из-за неправильного набора предположений ... дайте мне знать, если это так. Я видел много дискуссий о том, как Docker полезен для развертывания, но нет примеров того, как это на самом деле делается.
Вот как я думал, что это будет работать:
- создайте контейнер данных для хранения постоянных данных на компьютере A
- создайте контейнер приложения, который использует тома из контейнера данных
- сделать некоторую работу, потенциально изменяя данные в контейнере данных
- остановите контейнер приложения
- зафиксировать и пометить контейнер данных
- отправить контейнер данных в (частный) репозиторий
- потяните и запустите образ из шага 6 на машине B
- забрать, где вы остановились на машине B
Ключевым шагом здесь является шаг 5, который, как я думал, сохранит текущее состояние (включая содержимое файловой системы). Затем вы можете передать это состояние в хранилище и извлечь его из другого места, предоставив вам новый контейнер, который по сути идентичен оригиналу.
Но, похоже, это не работает. Я обнаружил, что либо шаг 5 не выполняет то, что я думаю, либо шаг 7 (извлечение и запуск изображения) «сбрасывает» контейнер в его исходное состояние.
Для проверки я собрал набор из трех изображений и контейнеров Docker: контейнер данных, модуль записи, который каждые 30 с записывает случайную строку в файл в контейнере данных, и средство чтения, которое просто echo
определяет значение в данных. контейнерный файл и выходы.
Контейнер данных
Создано с
docker run \
--name datatest_data \
-v /datafolder \
myrepository:5000/datatest-data:latest
Dockerfile:
FROM ubuntu:trusty
# make the data folder
#
RUN mkdir /datafolder
# write something to the data file
#
RUN echo "no data here!" > /datafolder/data.txt
# expose the data folder
#
VOLUME /datafolder
писатель
Создано с
docker run \
--rm \
--name datatest_write \
--volumes-from datatest_data \
myrepository:5000/datatest-write:latest
Dockerfile:
FROM ubuntu:trusty
# Add script
#
ADD run.sh /usr/local/sbin/run.sh
RUN chmod 755 /usr/local/sbin/*.sh
CMD ["/usr/local/sbin/run.sh"]
run.sh
#!/bin/bash
while :
do
sleep 30s
NEW_STRING=$(cat /dev/urandom | tr -dc 'a-zA-Z0-9' | fold -w 32 | head -n 1)
echo "$NEW_STRING" >> /datafolder/data.txt
date >> /datafolder/data.txt
echo "wrote '$NEW_STRING' to file"
done
Этот сценарий записывает случайную строку и дату / время /datafolder/data.txt
в контейнер данных.
читатель
Создано с
docker run \
--rm \
--name datatest_read \
--volumes-from datatest_data \
myrepository:5000/datatest-read:latest
Dockerfile:
FROM ubuntu:trusty
# Add scripts
ADD run.sh /run.sh
RUN chmod 0777 /run.sh
CMD ["/run.sh"]
run.sh:
#!/bin/bash
echo "reading..."
echo "-----"
cat /datafolder/data.txt
echo "-----"
Когда я собираю и запускаю эти контейнеры, они работают нормально и работают так, как я ожидаю:
Stop & Start на машине разработки:
- создать контейнер данных
- запустить писателя
- запустите ридер немедленно, смотрите «нет данных здесь!» сообщение
- подождите немного
- запустить читатель, увидеть случайную строку
- остановить писателя
- перезапустить писателя
- запустить читатель, увидеть ту же случайную строку
Но совершение и толкание не делают то, что я ожидаю:
- создать контейнер данных
- запустить писателя
- запустите ридер немедленно, смотрите «нет данных здесь!» сообщение
- подождите немного
- запустить читатель, увидеть случайную строку
- остановить писателя
- зафиксировать и пометить контейнер данных
docker commit datatest_data myrepository:5000/datatest-data:latest
- подтолкнуть к хранилищу
- удалить все контейнеры и воссоздать их
На этом этапе я ожидал запустить программу чтения и увидеть ту же самую случайную строку, поскольку контейнер данных был зафиксирован, передан в хранилище, а затем воссоздан из того же изображения в хранилище. Тем не менее, на самом деле я вижу «здесь нет данных!» сообщение.
Может кто-нибудь объяснить, где я здесь не так? Или, в качестве альтернативы, укажите на пример того, как развертывание выполняется с помощью Docker?