Wyczyść Memcached na Heroku Deploy
Jaki jest najlepszy sposób na automatyczne wyczyszczenie Memcached podczas wdrażania aplikacji rails do Heroku?
Buforuję stronę główną, a kiedy wprowadzam zmiany i redeploy, strona jest serwowana z pamięci podręcznej, a aktualizacje nie są włączone.
Chcę, żeby to było całkowicie zautomatyzowane. Nie chcę czyścić pamięci podręcznej w konsoli heroku za każdym razem, gdy wdrażam.
Dzięki!
9 answers
Wdrażam moje aplikacje za pomocą skryptu bash, który automatyzuje push GitHub & Heroku, migrację bazy danych, aktywację trybu konserwacji aplikacji i akcję czyszczenia pamięci podręcznej.
W tym skrypcie polecenie wyczyszczenia pamięci podręcznej brzmi:
heroku run --app YOUR_APP_NAME rails runner -e production Rails.cache.clear
To działa z seledynowym cedrem z pakietem Heroku Toolbelt. Wiem, że nie jest to rozwiązanie oparte na grabie, ale jest dość wydajne.
Uwaga: Upewnij się, że ustawiłeś environment
/ -e
opcja polecenia runner
na production
Jak będzie stracony na development
jeden inaczej.
Edit: od kilku dni mam problemy z tą komendą na Heroku (Rails 3.2.21). Nie miałem czasu, aby sprawdzić pochodzenie problemu, ale usunięcie -e production
zrobił sztuczkę, więc jeśli polecenie nie powiedzie się, Uruchom ten zamiast:
heroku run --app YOUR_APP_NAME rails runner Rails.cache.clear
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-06-10 09:44:22
[na stosie cedru seledynowego]
-- [Aktualizacja 18 czerwca 2012 -- to już nie działa, zobaczę czy uda mi się znaleźć inne obejście]
Najczystszym sposobem, jaki znalazłem, aby poradzić sobie z tymi hookami po wdrożeniu, jest zablokowanie zadania assets:precompile, które jest już wywołane podczas kompilacji Sluga. Z ukłonem w stronę asset_sync za pomysł:
Rake::Task["assets:precompile"].enhance do
# How to invoke a task that exists elsewhere
# Rake::Task["assets:environment"].invoke if Rake::Task.task_defined?("assets:environment")
# Clear cache on deploy
print "Clearing the rails memcached cache\n"
Rails.cache.clear
end
Dodałem to do lib / tasks / heroku_deploy.zgarnij teczkę i ładnie ją podniesiesz.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2012-06-19 02:02:47
Skończyło się na stworzeniu nowego zadania rake, które zostało wysłane do heroku, a następnie wyczyszczone pamięć podręczną. Stworzyłem deploy.plik rake i to jest to:
namespace :deploy do
task :production do
puts "deploying to production"
system "git push heroku"
puts "clearing cache"
system "heroku console Rails.cache.clear"
puts "done"
end
end
Zamiast wpisywać git push heroku, wpisuję rake deploy:production.Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2012-08-06 06:55:45
25 styczeń 2013: to działa dla aplikacji Rails 3.2.11 działającej na Ruby 1.9.3 na Cedar
W twoim Gemfile
Dodaj następujący wiersz, aby wymusić ruby 1.9.3:
ruby '1.9.3'
Utwórz plik o nazwie lib/tasks/clear_cache.rake
o tej treści:
if Rake::Task.task_defined?("assets:precompile:nondigest")
Rake::Task["assets:precompile:nondigest"].enhance do
Rails.cache.clear
end
else
Rake::Task["assets:precompile"].enhance do
# rails 3.1.1 will clear out Rails.application.config if the env vars
# RAILS_GROUP and RAILS_ENV are not defined. We need to reload the
# assets environment in this case.
# Rake::Task["assets:environment"].invoke if Rake::Task.task_defined?("assets:environment")
Rails.cache.clear
end
end
Na koniec Zalecam również uruchomienie heroku labs:enable user-env-compile
w Twojej aplikacji, aby jej środowisko było dostępne dla Ciebie w ramach prekompilacji.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2013-01-25 15:15:00
Poza wszystkim, co możesz zrobić wewnątrz aplikacji, która działa na 'application start', możesz użyć heroku deploy hooks (http://devcenter.heroku.com/articles/deploy-hooks#http_post_hook), który trafi adres URL w aplikacji, która czyści pamięć podręczną
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2011-10-11 22:03:22
Dodałem config/initializers/expire_cache.rb
z
ActionController::Base.expire_page '/'
Działa słodko!Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2012-06-15 10:19:10
Ponieważ klejnot heroku jest przestarzały, zaktualizowana wersja Solomons bardzo elegancką odpowiedzią byłoby zapisanie następującego kodu w lib/tasks/heroku_deploy.rake
:
namespace :deploy do
task :production do
puts "deploying to production"
system "git push heroku"
puts "clearing cache"
system "heroku run rake cache:clear"
puts "done"
end
end
namespace :cache do
desc "Clears Rails cache"
task :clear => :environment do
Rails.cache.clear
end
end
Następnie zamiast git push heroku master
wpisujesz rake deploy:production
w wierszu poleceń.
Aby wyczyścić pamięć podręczną, możesz uruchomić rake cache:clear
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2013-01-16 03:39:10
Rozwiązanie, którego lubię używać, jest następujące:
Najpierw implementuję akcję deploy_hook, która szuka parametru, który ustawiam inaczej dla każdej aplikacji. Zazwyczaj po prostu robię to na kontrolerze "home" lub "public", ponieważ nie zajmuje to tyle kodu.
### routes.rb ###
post 'deploy_hook' => 'home#deploy'
### home_controller.rb ###
def deploy_hook
Rails.cache.clear if params[:secret] == "a3ad3d3"
end
I po prostu mówię heroku, aby skonfigurował hak wdrożenia, aby wysyłał do tej akcji, gdy tylko będę wdrażał!
heroku addons:add deployhooks:http \
--url=http://example.com/deploy_hook?secret=a3ad3d3
Teraz, za każdym razem, gdy wdrażam, heroku zrobi Post HTTP z powrotem na stronę, aby dać mi znać, że rozmieszczenie zadziałało dobrze.
Działa jak urok dla mnie. Oczywiście tajny token nie jest "wysoki poziom bezpieczeństwa" i nie powinien być używany, jeśli istniał dobry wektor ataku do usuwania witryny, jeśli pamięci podręczne zostały wyczyszczone. Ale szczerze mówiąc, jeśli strona jest tak krytyczna do ataku, nie Hostuj jej na Heroku! Jeśli jednak chcesz nieco zwiększyć bezpieczeństwo, możesz użyć zmiennej konfiguracyjnej Heroku i w ogóle nie mieć 'tokena' w kodzie źródłowym.Hope people Uznaj to za przydatne.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2014-07-21 11:20:27
Ja też miałem ten problem, ale chciałem trzymać się wdrożenia git bez dodatkowego skryptu jako wrappera.
Więc moim podejściem jest zapisanie pliku podczas generowania slug z uuid, który oznacza bieżącą prekompilację. To jest impelmentowane jako hak w assets:precompile
.
# /lib/tasks/store_asset_cacheversion.rake
# add uuidtools to Gemfile
require "uuidtools"
def storeCacheVersion
cacheversion = UUIDTools::UUID.random_create
File.open(".cacheversion", "w") { |file| file.write(cacheversion) }
end
Rake::Task["assets:precompile"].enhance do
puts "Storing git hash in file for cache invalidation (assets:precompile)\n"
storeCacheVersion
end
Rake::Task["assets:precompile:nondigest"].enhance do
puts "Storing git hash in file for cache invalidation (assets:precompile:nondigest)\n"
storeCacheVersion
end
Drugi jest inicjalizatorem, który sprawdza ten identyfikator względem wersji buforowanej. Jeśli różnią się, nastąpiła kolejna prekompilacja i pamięć podręczna zostanie unieważniona.
Więc nie ważne, jak często aplikacja obraca się w górę lub w dół lub na ile węzłów będzie rozprowadzany worker, ponieważ generowanie ślimaka zdarza się tylko raz.
# /config/initializers/00_asset_cache_check.rb
currenthash = File.read ".cacheversion"
cachehash = Rails.cache.read "cacheversion"
puts "Checking cache version: #{cachehash} against slug version: #{currenthash}\n"
if currenthash != cachehash
puts "flushing cache\n"
Rails.cache.clear
Rails.cache.write "cacheversion", currenthash
else
puts "cache ok\n"
end
Musiałem użyć losowego identyfikatora, ponieważ o ile wiem, nie ma sposobu na uzyskanie Git hash lub innego użytecznego identyfikatora. Być może ENV[REQUEST_ID]
, ale jest to również losowy identyfikator.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2014-12-30 01:29:26