2009-08-09 2 views
2

J'ai une action que je cache à l'aideComment obtenir caches_action pour définir les en-têtes expirés lorsqu'il y a un hit dans memcached?

caches_action :my_action, :expires_in=>1.hours 

et également définir les expires têtes dans l'action elle-même en utilisant

def my_action 
    ... 
    expires_in 1.hours 
    send_data(...,:disposition => 'inline',:type => 'image/png',:filename => params[:title]+".png") 
end 

Cependant, quand je regarde l'en-tête de réponse de contrôle du cache d'un résultat vient à la suite d'un coup memcached, je reçois ceci:

Cache-Control: private, max-age=0, must-revalidate 

la première fois ronde, à savoir quand il n'y a rien dans le cache, il est wha t Je pense, i.e. .:

Cache-Control: max-age=3600, private 

Il ressemble à rails + memcached est ni la mise en cache les en-têtes de réponse d'origine, ni la mise en-têtes appropriés lui-même. Le résultat est que le client fait une requête au serveur chaque fois que le résultat (une image) n'a pas changé. Bien que l'action se termine rapidement quand elle reçoit un coup dans le cache, elle finit toujours par envoyer toutes les données, ce que je voudrais éviter.

Comment puis-je obtenir les en-têtes pour faire la bonne chose afin que le client ne fasse aucune demande en premier lieu, ou obtient une réponse «non modifié»?

Répondre

0

Assurez-vous que votre environnement est configuré pour prendre en charge la mise en cache. Ainsi, dans config/environnements/development.rb (ou si jamais) vous devriez voir:

config.action_controller.perform_caching = true 

En outre, la balise cache privée indique les serveurs de cache intermédiaires de ne pas stocker le contenu. C'est sécurisé par défaut. Si vous voulez modifier ce comportement, vient de mettre en cache comme ceci:

expires_in(1.hours, :private => false, :public => true) 

Pour ignorer le traitement coûteux sur le serveur si le contenu n'a pas changé, utilisez:

if stale?(:etag => @model, :last_modified => @model.updated_at.utc) 
    # Expensive stuff in here. 
    respond_to do |format| 
    ... 
    end 
end 
+0

oui la mise en cache est configurée et fonctionne correctement - le problème est le deuxième qui survient lorsqu'il y a un hit dans le memcache, les en-têtes ne sont pas configurés. aussi sur le second tour, l'action ne serait pas invoquée à cause du hit de memcache donc je suppose que le troisième fragment de code n'aura aucun effet. – frankodwyer

+0

Oh je vois. J'ai eu votre problème dans le mauvais sens. C'est étrange. Pouvez-vous poster les fragments pertinents des journaux? – askegg

+0

Selon ce post, Rails peut supposer un document HTML, la clé peut ne pas correspondre à votre requête. Juste une pensée. http://gilesbowkett.blogspot.com/2007/07/little-rails-image-caching-caveat.html – askegg

2

J'ai eu la même problème il y a quelques jours. Le débogage semble que les rails ne tiennent pas compte de expires_in pour caches_action.

Ce que j'ai trouvé qui fonctionne est de mettre le même dans un cache_path. Par exemple insted de faire

caches_action :monthly_sales_by_category, :expires_in => 10.minutes, :cache_path => proc { |c| 
    category = c.params[:category] 
    {:cat => category} 
} 

ce que je faisais était le suivant

caches_action :monthly_sales_by_category, :cache_path => proc { |c| 
    expires_in 10.minutes, :public => false 
    category = c.params[:category] 
    {:cat => category} 
} 

et fonctionne comme un charme. :)

+0

Merci, merci, merci d'avoir creusé cela. – Graeme

Questions connexes