2012-05-24 6 views
9

Con ERB è possibile frammentare della cache singoli record in un elenco in questo modo:Rails frammento di caching reso template liquido

<% @items.each do |item| %> 
    <% cache item do %> 
    <%= item.name %> 
    <% end %> 
<% end %> 

Così, la seconda volta la lista è visto, ogni elemento reso verrà caricato dalla cache. È possibile utilizzare questo stesso approccio quando si usano i modelli Liquid? Il modello potrebbe essere simile:

{% for item in items %} 
    {{ item.name }} 
{% endfor %} 

e reso con:

template = Liquid::Template.parse(template) 
template.render('items' => @items) 

Quando loop sulle voci, mi piacerebbe essere in grado di frammentare cache di ciascuno di essi. Qualche indicazione?

risposta

8

È possibile definire tag personalizzati in un liquido, per esempio se si mette questo in un inizializzatore

class Cacher < Liquid::Block 
    def initialize(tag_name, markup, tokens) 
    super 
    @key= markup.to_s 
    end 

    def render(context) 
    Rails.cache.fetch(@key) do 
     super 
    end 
    end 
end 

Liquid::Template.register_tag('cache', Cacher) 

allora si può fare

{% cache "some_key" %} 
    ... 
{% endcache %} 

essere molto attenzione a come si costruisce la cache chiave. Ovviamente vuoi evitare gli scontri, ma probabilmente non vuoi che le persone siano in grado di leggere le chiavi arbitrarie dal tuo store memcache (come fa questo codice). La corrispondenza dipende da chi ha accesso a questo nella tua app. Una strategia sarebbe per le chiavi della cache dello spazio dei nomi.

+0

+1 per la nota su come prestare attenzione alla denominazione dei tasti. Molto importante quando si danno agli inquilini (in un'applicazione multi-tenant) la possibilità di modificare i modelli Liquid. –

+0

Risposta stupenda !! Funziona alla grande. Molte grazie. – Ivangrx

+0

Molto carino, grazie –