На основе репозитория discourse_docker я написал небольшой скрипт для автоматизации его использования внутри машины Vagrant (запускайте с опцией set -x, чтобы видеть, что именно происходит)
Неправильно ли я скопировал резервную копию в указанное место?
И что означает строка лога: Making sure /var/www/discourse/tmp/restores/default/2020-05-13-190832 exists...
~/infra/discourse on master! ⌚ 21:14:07
$ pwd
/home/pihentagy/infra/discourse
~/infra/discourse on master! ⌚ 21:01:14
$ ./wl.sh start
+ set -e
+ VAGRANT_MACHINE_NAME=guest
+ cd discourse
+ case "$1" in
+ init
+ printf 'Checking out and updating repo…\n'
Checking out and updating repo…
+ cd ..
+ git clone https://github.com/discourse/discourse_docker.git discourse
fatal: destination path 'discourse' already exists and is not an empty directory.
+ printf 'Repo already there\n'
Repo already there
+ cd discourse
+ printf 'Updating repo…\n'
Updating repo…
+ git pull -r
remote: Enumerating objects: 6, done.
remote: Counting objects: 100% (6/6), done.
remote: Compressing objects: 100% (4/4), done.
remote: Total 6 (delta 2), reused 5 (delta 2), pack-reused 0
Unpacking objects: 100% (6/6), done.
From https://github.com/discourse/discourse_docker
3e465a2..49ed141 master -> origin/master
Created autostash: 36aae80
HEAD is now at 3e465a2 Remove all pg12 traces so pg_wrapper doesn't get confused
First, rewinding head to replay your work on top of it...
Fast-forwarded master to 49ed14152971f7f4a7437657987952be44c33c0a.
Applying autostash resulted in conflicts.
Your changes are safe in the stash.
You can run "git stash pop" or "git stash drop" at any time.
+ printf 'Copying config file…\n'
Copying config file…
+ cp ../resources/discourse.yml containers/
+ echo 'Starting Vagrant machine...'
Starting Vagrant machine...
+ vagrant up
Bringing machine 'dockerhost' up with 'virtualbox' provider...
==> dockerhost: Checking if box 'ubuntu/xenial64' is up to date...
==> dockerhost: Machine already provisioned. Run `vagrant provision` or use the `--provision`
==> dockerhost: flag to force provisioning. Provisioners marked to run always will still run.
+ vagrant ssh -c 'cd /vagrant;sudo ./launcher start discourse'
2627afdfbaac
Nothing to do, your container has already started!
Connection to 127.0.0.1 closed.
+ exit 0
~/infra/discourse on master! ⌚ 21:07:56
$ ./wl.sh restore /home/pihentagy/infra/icontest-2020-05-12-033823-v20200506044956.tar.gz
+ set -e
+ VAGRANT_MACHINE_NAME=guest
+ cd discourse
+ case "$1" in
+ shift
+ backup=/home/pihentagy/infra/icontest-2020-05-12-033823-v20200506044956.tar.gz
+ discourse_backup_dir=shared/standalone/backups/default
+ mkdir --parents shared/standalone/backups/default
+ rsync -P --verbose /home/pihentagy/infra/icontest-2020-05-12-033823-v20200506044956.tar.gz shared/standalone/backups/default
icontest-2020-05-12-033823-v20200506044956.tar.gz
390,774,609 100% 317.41MB/s 0:00:01 (xfr#1, to-chk=0/1)
sent 390,870,133 bytes received 35 bytes 156,348,067.20 bytes/sec
total size is 390,774,609 speedup is 1.00
+ vagrant ssh -c 'sudo docker exec -w /var/www/discourse -i discourse discourse enable_restore'
Restore are now permitted. Disable them with `disable_restore`
Connection to 127.0.0.1 closed.
+ vagrant ssh -c 'sudo docker exec -w /var/www/discourse -i discourse discourse restore'
You must provide a filename to restore. Did you mean one of the following?
Connection to 127.0.0.1 closed.
+ vagrant ssh -c 'sudo docker exec -w /var/www/discourse -i discourse discourse restore icontest-2020-05-12-033823-v20200506044956.tar.gz'
Starting restore: icontest-2020-05-12-033823-v20200506044956.tar.gz
[STARTED]
'system' has started the restore!
Marking restore as running...
Making sure /var/www/discourse/tmp/restores/default/2020-05-13-190832 exists...
Copying archive to tmp directory...
EXCEPTION: lib/discourse.rb:90:in `exec': Failed to copy archive to tmp directory.
cp: cannot stat '/var/www/discourse/public/backups/default/icontest-2020-05-12-033823-v20200506044956.tar.gz': No such file or directory
lib/discourse.rb:100:in `execute_command'
lib/discourse.rb:90:in `exec'
lib/discourse.rb:40:in `execute_command'
/var/www/discourse/lib/backup_restore/local_backup_store.rb:42:in `download_file'
/var/www/discourse/lib/backup_restore/backup_file_handler.rb:61:in `copy_archive_to_tmp_directory'
/var/www/discourse/lib/backup_restore/backup_file_handler.rb:21:in `decompress'
/var/www/discourse/lib/backup_restore/restorer.rb:42:in `run'
script/discourse:143:in `restore'
/var/www/discourse/vendor/bundle/ruby/2.6.0/gems/thor-1.0.1/lib/thor/command.rb:27:in `run'
/var/www/discourse/vendor/bundle/ruby/2.6.0/gems/thor-1.0.1/lib/thor/invocation.rb:127:in `invoke_command'
/var/www/discourse/vendor/bundle/ruby/2.6.0/gems/thor-1.0.1/lib/thor.rb:392:in `dispatch'
/var/www/discourse/vendor/bundle/ruby/2.6.0/gems/thor-1.0.1/lib/thor/base.rb:485:in `start'
script/discourse:284:in `<top (required)>'
/usr/local/lib/ruby/gems/2.6.0/gems/bundler-2.1.4/lib/bundler/cli/exec.rb:63:in `load'
/usr/local/lib/ruby/gems/2.6.0/gems/bundler-2.1.4/lib/bundler/cli/exec.rb:63:in `kernel_load'
/usr/local/lib/ruby/gems/2.6.0/gems/bundler-2.1.4/lib/bundler/cli/exec.rb:28:in `run'
/usr/local/lib/ruby/gems/2.6.0/gems/bundler-2.1.4/lib/bundler/cli.rb:476:in `exec'
/usr/local/lib/ruby/gems/2.6.0/gems/bundler-2.1.4/lib/bundler/vendor/thor/lib/thor/command.rb:27:in `run'
/usr/local/lib/ruby/gems/2.6.0/gems/bundler-2.1.4/lib/bundler/vendor/thor/lib/thor/invocation.rb:127:in `invoke_command'
/usr/local/lib/ruby/gems/2.6.0/gems/bundler-2.1.4/lib/bundler/vendor/thor/lib/thor.rb:399:in `dispatch'
/usr/local/lib/ruby/gems/2.6.0/gems/bundler-2.1.4/lib/bundler/cli.rb:30:in `dispatch'
/usr/local/lib/ruby/gems/2.6.0/gems/bundler-2.1.4/lib/bundler/vendor/thor/lib/thor/base.rb:476:in `start'
/usr/local/lib/ruby/gems/2.6.0/gems/bundler-2.1.4/lib/bundler/cli.rb:24:in `start'
/usr/local/lib/ruby/gems/2.6.0/gems/bundler-2.1.4/exe/bundle:46:in `block in <top (required)>'
/usr/local/lib/ruby/gems/2.6.0/gems/bundler-2.1.4/lib/bundler/friendly_errors.rb:123:in `with_friendly_errors'
/usr/local/lib/ruby/gems/2.6.0/gems/bundler-2.1.4/exe/bundle:34:in `<top (required)>'
/usr/local/bin/bundle:23:in `load'
/usr/local/bin/bundle:23:in `<main>'
Trying to rollback...
There was no need to rollback
Cleaning stuff up...
Removing tmp '/var/www/discourse/tmp/restores/default/2020-05-13-190832' directory...
Unpausing sidekiq...
Marking restore as finished...
Notifying 'system' of the end of the restore...
Finished!
[FAILED]
Restore done.
Connection to 127.0.0.1 closed.
Vagrant не поддерживается, но вот несколько советов на всякий случай.
Не совсем уверен, как работает rsync. Нужно ли, чтобы путь заканчивался на косую черту? Если файл попал в правильную директорию, убедитесь, что сервер имеет права на чтение скопированного файла.
Значит ли это, что vagrant (virtualbox) может вызвать некоторые проблемы?
~/infra/discourse на master! ⌚ 23:22:23
$ tree discourse/shared
discourse/shared
└── standalone
└── backups
└── default
└── icontest-2020-05-12-033823-v20200506044956.tar.gz
3 директории, 1 файл
~/infra/discourse на master! ⌚ 23:22:27
$ ls discourse/shared/standalone/backups/default
icontest-2020-05-12-033823-v20200506044956.tar.gz
~/infra/discourse на master! ⌚ 23:22:36
$ ls -l discourse/shared/standalone/backups/default
total 381620
-rw-r--r-- 1 pihentagy pihentagy 390774609 May 13 21:08 icontest-2020-05-12-033823-v20200506044956.tar.gz
Похоже, что файл доступен для чтения всем и находится в правильном месте. Изнутри docker-контейнера discourse где я должен видеть резервную копию? Правильна ли мой скрипт автоматического восстановления, или мне нужно скопировать файл внутрь docker-контейнера? Если да, то куда? (Может быть, есть какие-либо руководства по автоматизации Discourse извне [docker?])
+ vagrant ssh -c 'sudo docker exec -w /var/www/discourse -i discourse discourse restore'
Вы должны указать имя файла для восстановления. Возможно, вы имели в виду один из следующих?
Соединение с 127.0.0.1 закрыто.
+ vagrant ssh -c 'sudo docker exec -w /var/www/discourse -i discourse discourse restore icontest-2020-05-12-033823-v20200506044956.tar.gz'
Запуск восстановления: icontest-2020-05-12-033823-v20200506044956.tar.gz
[
Это не обязательно, но отсутствие слэша в конце пути — плохая практика, так как результат зависит от того, существует ли уже целевая директория или нет.
Если целевая директория уже существует, слэш не нужен, и файл копируется внутрь этой директории.
Если целевая директория не существует и в конце нет слэша, файл копируется под именем ‘default’.
Если целевая директория не существует и в конце есть слэш, директория создаётся, и файл копируется внутрь неё.
В данном случае копирование, похоже, прошло успешно (по случайности).
Однако,
Поскольку после фразы «Вы имели в виду один из следующих?» никаких вариантов не предлагается, файл находится не в правильном месте. Похоже, диски неправильно смонтированы внутри контейнера Docker.
Вы можете запустить резервное копирование изнутри Docker (discourse backup) и посмотреть, куда файл попадает на вашей хостовой файловой системе.
Странно, что его не видно в файловой системе хоста. Должно ли оно быть там?
vagrant@ubuntu-xenial:~$ sudo docker exec -w /var/www/discourse -i discourse discourse backup
Запуск резервного копирования...
[НАЧАЛО]
Система начала создание резервной копии!
Пометка резервной копии как запущенной...
Проверка существования '/var/www/discourse/tmp/backups/default/2020-05-14-121930'...
Проверка существования '/var/www/discourse/public/backups/default'...
Обновление метаданных...
Приостановка sidekiq...
Ожидание завершения выполнения задач sidekiq...
Выгрузка публичной схемы базы данных...
…
Много всего из pg_dump"
…
Возобновление sidekiq...
Завершение резервного копирования...
Создание архива: discourse-2020-05-14-121930-v20200512064023.tar.gz
Проверка, что архив ещё не существует...
Создание пустого архива...
Добавление дампа данных в архив...
Добавление загрузок в архив...
Удаление временной директории '/var/www/discourse/tmp/backups/default/2020-05-14-121930'...
Сжатие архива в gzip, это может занять время...
Выполнение after_create_hook для резервной копии...
Удаление старых резервных копий...
Очистка...
Удаление остатков '.tar'...
Пометка резервной копии как завершённой...
Обновление статистики диска...
Готово!
[УСПЕХ]
Резервное копирование завершено.
Файл вывода находится в: /var/www/discourse/public/backups/default/discourse-2020-05-14-121930-v20200512064023.tar.gz
vagrant@ubuntu-xenial:~$ find / -name discourse-2020-05-14-121930-v20200512064023.tar.gz 2>/dev/null
vagrant@ubuntu-xenial:~$ sudo docer exec -w /var/www/discourse -i discourse discourse enable_restore
sudo: docer: команда не найдена
vagrant@ubuntu-xenial:~$ sudo docker exec -w /var/www/discourse -i discourse discourse enable_restore
Восстановление теперь разрешено. Отключите его с помощью `disable_restore`
vagrant@ubuntu-xenial:~$ sudo docker exec -w /var/www/discourse -i discourse discourse restore
Вы должны указать имя файла для восстановления. Возможно, вы имели в виду один из следующих?
discourse restore discourse-2020-05-14-121930-v20200512064023.tar.gz
discourse restore discourse-2020-05-14-121710-v20200512064023.tar.gz
discourse restore discourse-2020-05-14-120436-v20200512064023.tar.gz
Кстати: есть ли способ подсвечивать строки в блоках кода?
Обычно директория /var/discourse/shared/standalone/backups видна в вашем контейнере как /var/www/discourse/public/backups (отсюда и слово shared). Ваша команда rsync помещает резервную копию внутрь этой директории, чтобы сделать её доступной из контейнера.
И наоборот, если контейнер записывает данные в public/backups, они должны быть видны на хосте в общей директории.
Я указал выше путь /var/discourse/shared.... Но, похоже, вы работаете в ~/infra/discourse, поэтому вы копируете файлы в ~/infra/discourse/shared/standalone/backups/default.
Обычно контейнер мапится на /var/discourse/shared/....
В этом может быть проблема. Можете проверить, существует ли у вас директория /var/discourse/shared?
однако, если зайти внутрь контейнера Docker, файл там есть
root@ubuntu-xenial-discourse:/var/www/discourse/public/backups/default# ls
discourse-2020-05-14-120436-v20200512064023.tar.gz discourse-2020-05-14-121930-v20200512064023.tar.gz
discourse-2020-05-14-121710-v20200512064023.tar.gz discourse-2020-05-14-125606-v20200512064023.tar.gz
Так что мой вопрос: если я создаю резервную копию, должен ли я видеть её извне Docker?
Тем временем я просто создал виртуальную машину vagrant и выполнил git clone изнутри в стандартную директорию /var/discourse. Единственная “странность” в том, что у меня внутри контейнера есть файл discourse.yml, а не app.yml.
Да, и это то же самое, что и ваша первоначальная проблема:
«если у вас есть резервная копия вне Docker и вы поместите её в общую папку, вы должны видеть её внутри Docker» (а вы не видите).
Проблема связана с вашими общими директориями, и причина этого в следующем:
Я имел в виду: пока я создал новую машину Vagrant, без копирования каких-либо предыдущих резервных копий. Выполнил запуск и запуск контейнера Docker. Сделал резервную копию.
Внутри машины Vagrant ничего не видно за пределами машины Docker.
Кажется, я нашел проблему: я подключил эту общую папку Docker в машине Vagrant.