Как автоматически перезапустить delayed_job при развертывании проекта рельсов на Amazon Elastic Beanstalk? - программирование
Подтвердить что ты не робот

Как автоматически перезапустить delayed_job при развертывании проекта рельсов на Amazon Elastic Beanstalk?

У меня есть проект рельсов на Amazon Elastic Beanstalk, и я пытаюсь настроить container для автоматического перезапуска рабочего delayed_job на сервере после каждого развертывания.

Я попытался с этим:

container_commands:
  restartdelayedjob:
    command: "RAILS_ENV=production script/delayed_job --pid-dir=/home/ec2-user/pids start"
    cwd: /var/app/current

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

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

Есть ли у вас идеи о том, как я могу справиться с этим?

Спасибо

4b9b3361

Ответ 1

В соответствии с Документация Amazon для container_commands:

Они запускаются после того, как приложение и веб-сервер были настроены, и файл версии приложения был извлечен, но до развертывания версии приложения.

(акцент мой)

Это означает, что в этой точке /var/app/current, которую вы устанавливаете как cwd для вашей команды, все еще указывается на предыдущую версию. Однако по умолчанию из документов снова cwd:

- это каталог распакованного приложения.

Это означает, что если вы хотите запустить delayed_job из каталога приложения, которое только что было извлечено (но еще не развернуто), не переопределяйте cwd и он должен запустить delayed_job для приложения, которое развертываться.

Ссылка: http://docs.aws.amazon.com/elasticbeanstalk/latest/dg/customize-containers-ec2.html#customize-containers-format-container_commands

Обновление:

Теперь я сам установил это и обнаружил, что существует ограничение на выполнение с помощью стандартного container_commands - в основном delayed_job будет запущен, пока он все еще находится в каталоге /var/app/ondeck. Обычно это нормально, но у меня были некоторые проблемы с некоторыми заданиями, потому что этот путь застрял вокруг, это вызовет ошибки, поскольку приложение теперь находится в /var/app/current.

Я нашел недокументированный подход (так предупреждаю!), что вы можете добавлять скрипты, которые будут запускаться ПОСЛЕ перезапуска сервера приложений (а ваше новое развертывание находится в /var/app/current).

В основном Elastic Beanstalk будет выполнять любые скрипты в /opt/elasticbeanstalk/hooks/appdeploy/post после перезапуска веб-сервера. Это означает, что если вы отпустите скрипты оболочки в этом каталоге, они будут запущены.

Я создал оболочку script следующим образом:

#!/usr/bin/env bash
. /opt/elasticbeanstalk/support/envvars
cd $EB_CONFIG_APP_CURRENT
su -c "RAILS_ENV=production script/delayed_job --pid-dir=$EB_CONFIG_APP_SUPPORT/pids restart" $EB_CONFIG_APP_USER

Я загрузил этот script в ведро S3 и убедился, что он был "общедоступным". Затем вы можете использовать опцию script в каталоге .ebextensions (например, 99delayed_job.config) для развертывания этого script как части развертывания приложения, принимая во внимание, что каталог post может не существовать:

commands:
  create_post_dir:
    command: "mkdir /opt/elasticbeanstalk/hooks/appdeploy/post"
    ignoreErrors: true
files:
  "/opt/elasticbeanstalk/hooks/appdeploy/post/99_restart_delayed_job.sh":
    mode: "000755"
    owner: root
    group: root
    source: http://YOUR_BUCKET.s3.amazonaws.com/99_restart_delayed_job.sh

При развертывании вы должны увидеть что-то вроде этого в /var/log/eb-tools.log:

2013-05-16 01:20:53,759 [INFO] (6467 MainThread) [directoryHooksExecutor.py-29] [root directoryHooksExecutor info] Executing directory: /opt/elasticbeanstalk/hooks/appdeploy/post/
2013-05-16 01:20:53,760 [INFO] (6467 MainThread) [directoryHooksExecutor.py-29] [root directoryHooksExecutor info] Executing script: /opt/elasticbeanstalk/hooks/appdeploy/post/99_restart_delayed_job.sh
2013-05-16 01:21:02,619 [INFO] (6467 MainThread) [directoryHooksExecutor.py-29] [root directoryHooksExecutor info] Output from script: delayed_job: trying to stop process with pid 6139...
delayed_job: process with pid 6139 successfully stopped.

2013-05-16 01:21:02,620 [INFO] (6467 MainThread) [directoryHooksExecutor.py-29] [root directoryHooksExecutor info] Script succeeded.

Как я уже сказал, размещение материала в этом "post" каталоге недокументировано - но, надеюсь, в какой-то момент Amazon добавит фактическую поддержку сценариям .options для запуска команд после развертывания, в этом случае вы можете перенести это на официально поддерживаемый подход.

Ответ 2

В 64-разрядной версии Amazon Linux 2014.09 v1.1.0 с Ruby 2.1 (автономный автономный режим), благодаря работе этот пост.

Обратите внимание, что этот script запускается как root, но ваши рабочие должны запускаться как пользователь webapp.

# Adds a post-deploy hook such that after a new version is deployed
# successfully, restarts the delayed_job workers.
#
# http://stackoverflow.com/questions/14401204/how-to-automatically-restart-delayed-job-when-deploying-a-rails-project-on-amazo
# http://www.dannemanne.com/posts/post-deployment_script_on_elastic_beanstalk_restart_delayed_job
files:
  "/opt/elasticbeanstalk/hooks/appdeploy/post/50_restart_delayed_job.sh":
    mode: "000755"
    owner: root
    group: root
    encoding: plain
    content: |
      #!/usr/bin/env bash

      EB_SCRIPT_DIR=$(/opt/elasticbeanstalk/bin/get-config container -k script_dir)
      EB_APP_CURRENT_DIR=$(/opt/elasticbeanstalk/bin/get-config container -k app_deploy_dir)
      EB_APP_USER=$(/opt/elasticbeanstalk/bin/get-config container -k app_user)
      EB_SUPPORT_DIR=$(/opt/elasticbeanstalk/bin/get-config container -k support_dir)
      EB_APP_PIDS_DIR=$(/opt/elasticbeanstalk/bin/get-config container -k app_pid_dir)

      . $EB_SUPPORT_DIR/envvars
      . $EB_SCRIPT_DIR/use-app-ruby.sh

      cd $EB_APP_CURRENT_DIR

      # Switch to the webapp user.  Worker shouldn't be run as root.
      su -s /bin/bash -c "bundle exec bin/delayed_job --pid-dir=$EB_APP_PIDS_DIR restart" $EB_APP_USER

Ответ 3

В случае, если кто-то хочет получить delayed_job, работающий в последнем ElasticBeanstalk (64-битный Amazon Linux 2014.09 v1.0.9 с Ruby 2.1 (Puma)): я получил его для работы с использованием кода ниже (спасибо damontorgerson). Этот файл находится в ruby.config в папке .ebextensions.

# Install git in order to be able to bundle gems from git
packages:
yum:
  git: []

files: 
  "/opt/elasticbeanstalk/hooks/appdeploy/post/50_restart_delayed_job":
    mode: "000777"
    owner: root
    group: root
    content: |
      EB_SCRIPT_DIR=$(/opt/elasticbeanstalk/bin/get-config container -k script_dir)
      EB_APP_STAGING_DIR=$(/opt/elasticbeanstalk/bin/get-config container -k app_staging_dir)
      EB_CONFIG_APP_CURRENT=$(/opt/elasticbeanstalk/bin/get-config container -k app_deploy_dir)
      EB_CONFIG_APP_LOGS=$(/opt/elasticbeanstalk/bin/get-config container -k app_log_dir)
      EB_APP_USER=$(/opt/elasticbeanstalk/bin/get-config container -k app_user)
      EB_SUPPORT_DIR=$(/opt/elasticbeanstalk/bin/get-config container -k support_dir)
      EB_CONFIG_APP_PIDS=$(/opt/elasticbeanstalk/bin/get-config container -k app_pid_dir)

      . $EB_SUPPORT_DIR/envvars
      . $EB_SCRIPT_DIR/use-app-ruby.sh

      cd $EB_CONFIG_APP_CURRENT

      . $EB_SUPPORT_DIR/envvars.d/sysenv

      bin/delayed_job --pid-dir=/var/tmp restart

Ответ 4

У меня работала так, как будто с камнем "демонов":

commands:
  create_post_dir:
    command: "mkdir /opt/elasticbeanstalk/hooks/appdeploy/post"
    ignoreErrors: true
  webapp_pids:
    command: "mkdir /home/webapp/pids"
    ignoreErrors: true
files:
  "/opt/elasticbeanstalk/hooks/appdeploy/post/99_restart_delayed_job.sh":
    mode: "000755"
    owner: root
    group: root
    content: |
      #!/usr/bin/env bash
      . /opt/elasticbeanstalk/support/envvars
      chown webapp:webapp /home/webapp/pids
      su -l -c "$EB_CONFIG_APP_CURRENT/bin/delayed_job --pid-dir=/home/webapp/pids restart" $EB_CONFIG_APP_USER
      echo "worker starting" >> /var/log/directory-hooks-executor.log