web-dev-qa-db-fra.com

Redémarrez automatiquement mon application Heroku

Cette commande de terminal redémarre mon application Heroku:

heroku restart

Existe-t-il un moyen d'exécuter un script qui exécutera cette commande et redémarrera mon application toutes les heures?

63
Oded Harth

En fait, je devais juste résoudre ce problème pour mes applications et j'ai écrit un post dessus avec plus de détails. Fondamentalement, vous avez besoin de la gemme heroku-api maintenant car la gemme heroku est remplacée par la CLI. Ensuite, vous avez besoin d'une tâche de râteau, de quelques variables de configuration et du plugin Heroku Scheduler (gratuit sauf pour un temps de dyno minimal).

La tâche de râteau ressemble à ceci:

namespace :heroku do
  desc 'restarts all the heroku dynos so we can control when they restart'
  task :restart do
    Heroku::API.
      new(username: ENV['HEROKU_USERNAME'], password: ENV['HEROKU_PASSWORD']).
      post_ps_restart(ENV['HEROKU_APP_NAME'])
  end
end

Vous pouvez également le configurer pour utiliser votre jeton d'API au lieu de mettre votre nom d'utilisateur et votre mot de passe dans la configuration. Cela n'a d'importance que si vous ne voulez pas que vos co-contributeurs/collègues connaissent votre mot de passe ou le mot de passe de votre compte principal sur Heroku.

heroku config:set HEROKU_USERNAME=[username] HEROKU_PASSWORD=[password] HEROKU_APP_NAME=[app_name] -a [app_name]

Maintenant, allez-y, déployez et testez:

git Push [heroku_remote_name] [feature_branch]:master
heroku run rake heroku:restart -a [app_name]

Enfin, nous devons configurer la tâche pour exécuter cette tâche dans les délais. J'ai choisi d'utiliser le module complémentaire gratuit Heron cron:

heroku addons:add scheduler:standard -a [app_name]
heroku addons:open scheduler -a [app_name]

Cela ouvrira l'interface utilisateur du planificateur dans votre navigateur et vous pouvez créer un travailleur planifié pour exécuter la tâche de râteau à tout moment. Nous n'en avons besoin qu'une fois par jour et nous choisissons de l'exécuter avant notre premier travail planifié de la journée.

Mon post original avec CSS simplifié (voir update2 ci-dessous):

https://web.archive.org/web/20150612091315/http://engineering.korrelate.com/2013/08/21/restart-heroku-dynos-on-your-terms/

[~ # ~] mise à jour [~ # ~]

J'ai changé le nom de la tâche de "imploser" en "redémarrer" pour être bien plus clair sur ce qui se passe. Implode est un nom amusant mais à peu près inutile sinon.

MISE À JOUR2

Apparemment, mon entreprise a supprimé le blog. J'ajoute plus de code ici et j'ai mis à jour le lien, mais le CSS ressemble à un chien qui l'a lancé. Mes excuses.

33
WattsInABox

Vous pouvez créer un travail cron heroku qui utilise l'api Heroku sur votre application pour se redémarrer ...

Une question cependant - pourquoi?

14
John Beynon

Nous avons résolu ce problème en utilisant un buildpack pour obtenir la commande heroku disponible pour le dyno lui-même, puis en utilisant Heroku Scheduler.

Nous avons ajouté le https://github.com/gregburek/heroku-buildpack-toolbelt buildpack selon ses instructions:

heroku buildpacks:add https://github.com/gregburek/heroku-buildpack-toolbelt.git
heroku config:add HEROKU_TOOLBELT_API_EMAIL=`heroku whoami`
heroku config:add HEROKU_TOOLBELT_API_PASSWORD=`heroku auth:token`

Ensuite, assurez-vous que le slug de l'application a été reconstruit conformément aux instructions:

git Push heroku master

Dans Heroku Scheduler, nous avons ajouté ceci comme un travail horaire:

vendor/heroku-toolbelt/bin/heroku ps:restart -a $HEROKU_APP_NAME

Vous pouvez déterminer si cela fonctionne en recherchant la sortie du planificateur dans les journaux Heroku, et bien sûr par le graphique de la mémoire de l'application dans le tableau de bord Heroku (si vous redémarrez pour contourner une fuite de mémoire).

7
Henrik N

Un script n'est pas nécessaire, il suffit de "planter" votre application et Heroku la redémarrera.

Ne faites pas cela plus souvent qu'une fois toutes les dix minutes ou Heroku vous soumettra à un délai de 10 minutes.

Dans node.js, vous faites cela avec process.exit(0).

De Chris au support Heroku:

Un dynamo planté sera redémarré immédiatement. Si le dyno passe d'un état en panne à un état "up" (ce qui signifie que le dyno est lié à $ PORT), il est alors susceptible d'être un dyno en cours d'exécution normal. S'il se bloque à nouveau pendant le démarrage ou la séquence de "démarrage", il ne sera redémarré qu'après la période TIMEOUT. La période TIMEOUT est actuellement de 10 minutes, mais elle est susceptible de changer. Cela empêche les dynos qui se bloquent continuellement de mettre une charge étrangère sur la plate-forme.

Cependant, aussi bon que cela puisse paraître, cela ne fonctionne pas dans la pratique. Vous atteindrez le délai d'attente chaque heure à laquelle vous quittez, car le gestionnaire de dyno s'attend à ce que votre application soit opérationnelle:

Pour la gestion de vos processus de travail, vous quittez le processus proprement, mais la plate-forme s'attend à ce que le dyno soit en place. Il semble que vous plantiez le dyno en conséquence.

Encore une fois, si vous devez redémarrer périodiquement - et cette période peut être définie sur> 10 minutes - c'est un moyen facile et simple de gérer l'effacement de la mémoire. Si vous devez redémarrer dynamiquement (par exemple, lorsque l'inactivité est détectée) ou fréquemment, vous devrez explorer d'autres options.

Vous pouvez accéder au nom du dyno (ex. "Worker.3", "web.1") via la variable d'environnement "PS" et émettre une commande de redémarrage de l'API heroku par programmation.

6
DrFriedParts

Inspiré par https://www.stormconsultancy.co.uk/blog/development/Ruby-on-Rails/automatically-restart-struggling-heroku-dynos-using-logentries/

# Setup
heroku plugins:install https://github.com/heroku/heroku-oauth
heroku authorizations:create -s write
heroku config:add RESTART_API_KEY=<API KEY>
heroku config:add APP_NAME=<App Name>

heroku addons:add scheduler:standard -a <App Name>
heroku addons:open scheduler -a <App Name>
add `rake restart`

# Gemfile
gem 'platform-api', require: false

# Rakefile
task :restart do
  require 'platform-api'
  app_name = ENV.fetch('APP_NAME')
  key = ENV.fetch('RESTART_API_KEY')
  connection = PlatformAPI.connect_oauth(key)
  connection.dyno.list(app_name).map do |info|
    if info['type'] == 'web' && info['state'] == 'up'
      puts "Restarting #{info.inspect}"
      connection.dyno.restart(app_name, info['name'])
    else
      puts "Skipping #{info.inspect}"
    end
  end
end
4
grosser

J'ai résolu cela avec un script de commande curl très simple dans le référentiel qui est déclenché en utilisant le planificateur Heroku gratuit .

#!/bin/sh curl -X DELETE "https://api.heroku.com/apps/${HEROKU_APP_NAME}/dynos" \ --user "${HEROKU_CLI_USER}:${HEROKU_CLI_TOKEN}" \ -H "Content-Type: application/json" \ -H "Accept: application/vnd.heroku+json; version=3"

Voir https://Gist.github.com/mattheworiordan/f052b7693aacd025f025537418fa5708 .

2
Matthew O'Riordan