GithubHelp home page GithubHelp logo

cache_digests's Introduction

Welcome to Rails

What's Rails?

Rails is a web-application framework that includes everything needed to create database-backed web applications according to the Model-View-Controller (MVC) pattern.

Understanding the MVC pattern is key to understanding Rails. MVC divides your application into three layers: Model, View, and Controller, each with a specific responsibility.

Model layer

The Model layer represents the domain model (such as Account, Product, Person, Post, etc.) and encapsulates the business logic specific to your application. In Rails, database-backed model classes are derived from ActiveRecord::Base. Active Record allows you to present the data from database rows as objects and embellish these data objects with business logic methods. Although most Rails models are backed by a database, models can also be ordinary Ruby classes, or Ruby classes that implement a set of interfaces as provided by the Active Model module.

View layer

The View layer is composed of "templates" that are responsible for providing appropriate representations of your application's resources. Templates can come in a variety of formats, but most view templates are HTML with embedded Ruby code (ERB files). Views are typically rendered to generate a controller response or to generate the body of an email. In Rails, View generation is handled by Action View.

Controller layer

The Controller layer is responsible for handling incoming HTTP requests and providing a suitable response. Usually, this means returning HTML, but Rails controllers can also generate XML, JSON, PDFs, mobile-specific views, and more. Controllers load and manipulate models, and render view templates in order to generate the appropriate HTTP response. In Rails, incoming requests are routed by Action Dispatch to an appropriate controller, and controller classes are derived from ActionController::Base. Action Dispatch and Action Controller are bundled together in Action Pack.

Frameworks and libraries

Active Record, Active Model, Action Pack, and Action View can each be used independently outside Rails.

In addition to that, Rails also comes with:

  • Action Mailer, a library to generate and send emails
  • Action Mailbox, a library to receive emails within a Rails application
  • Active Job, a framework for declaring jobs and making them run on a variety of queuing backends
  • Action Cable, a framework to integrate WebSockets with a Rails application
  • Active Storage, a library to attach cloud and local files to Rails applications
  • Action Text, a library to handle rich text content
  • Active Support, a collection of utility classes and standard library extensions that are useful for Rails, and may also be used independently outside Rails

Getting Started

  1. Install Rails at the command prompt if you haven't yet:

    $ gem install rails
  2. At the command prompt, create a new Rails application:

    $ rails new myapp

    where "myapp" is the application name.

  3. Change directory to myapp and start the web server:

    $ cd myapp
    $ bin/rails server

    Run with --help or -h for options.

  4. Go to http://localhost:3000 and you'll see the Rails bootscreen with your Rails and Ruby versions.

  5. Follow the guidelines to start developing your application. You may find the following resources handy:

Contributing

We encourage you to contribute to Ruby on Rails! Please check out the Contributing to Ruby on Rails guide for guidelines about how to proceed. Join us!

Trying to report a possible security vulnerability in Rails? Please check out our security policy for guidelines about how to proceed.

Everyone interacting in Rails and its sub-projects' codebases, issue trackers, chat rooms, and mailing lists is expected to follow the Rails code of conduct.

License

Ruby on Rails is released under the MIT License.

cache_digests's People

Contributors

balexand avatar bricker avatar cmer avatar dasch avatar dhh avatar fgrehm avatar genezys avatar jamis avatar jeremy avatar latortuga avatar macournoyer avatar maspwr avatar mrship avatar rafaelfranca avatar rgarver avatar s12chung avatar shuber avatar splattael avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

cache_digests's Issues

How to calculate the render speed after using cache digest?

After I'm using cache digest, it works. The only thing confusing me, how the rails calculate the speed? Here's the rails back log in development environments.

All of the request no more than 100ms, most of them less than 10ms, but the final result is 1.7seconds. I can't understand why this happen. But if I'm using the FireFox browser to check it, the FireBug said it takes around 1.7s, that same as rails log. If anyone know the answer, some hints appreciated.

Started GET "/?locale=cn&page=2" for 127.0.0.1 at 2013-04-26 22:11:44 +0800
Processing by Dashboard::PostsController#latest as HTML
Parameters: {"locale"=>"cn", "page"=>"2"}
User Load (0.2ms) SELECT users.* FROM users WHERE users.id = 3 LIMIT 1
Cache digest for shared/dashboard/_user_info.zip: 141bc37bbbbd5089bfd6a55e349bac2f
Read fragment views/users/3-20130426024715/141bc37bbbbd5089bfd6a55e349bac2f (0.2ms)
Rendered shared/dashboard/_user_info.haml (6.7ms)
Post Load (0.2ms) SELECT posts.* FROM posts WHERE (is_deleted is NULL and (type is NULL or type = 'Fts' or type = 'Video' or type='Technology')) ORDER BY id desc LIMIT 10 OFFSET 10
(0.1ms) SELECT COUNT(*) FROM posts WHERE (is_deleted is NULL and (type is NULL or type = 'Fts' or type = 'Video' or type='Technology'))
Cache digest for shared/dashboard/_posts.zip: 9ab674810fd35b48e90f98369bd6752f
Read fragment views/posts/32043-20130406100115/9ab674810fd35b48e90f98369bd6752f (0.2ms)
Cache digest for shared/dashboard/_posts.zip: 9ab674810fd35b48e90f98369bd6752f
Read fragment views/posts/32042-20130406100057/9ab674810fd35b48e90f98369bd6752f (0.2ms)
Cache digest for shared/dashboard/_posts.zip: 9ab674810fd35b48e90f98369bd6752f
Read fragment views/posts/32041-20130411105752/9ab674810fd35b48e90f98369bd6752f (0.2ms)
Cache digest for shared/dashboard/_posts.zip: 9ab674810fd35b48e90f98369bd6752f
Read fragment views/posts/32040-20130406095956/9ab674810fd35b48e90f98369bd6752f (0.2ms)
Cache digest for shared/dashboard/_posts.zip: 9ab674810fd35b48e90f98369bd6752f
Read fragment views/posts/32039-20130405012009/9ab674810fd35b48e90f98369bd6752f (0.2ms)
Cache digest for shared/dashboard/_posts.zip: 9ab674810fd35b48e90f98369bd6752f
Read fragment views/posts/32038-20130405010127/9ab674810fd35b48e90f98369bd6752f (0.2ms)
Cache digest for shared/dashboard/_posts.zip: 9ab674810fd35b48e90f98369bd6752f
Read fragment views/posts/32037-20130405003931/9ab674810fd35b48e90f98369bd6752f (0.2ms)
Cache digest for shared/dashboard/_posts.zip: 9ab674810fd35b48e90f98369bd6752f
Read fragment views/posts/32035-20130404145421/9ab674810fd35b48e90f98369bd6752f (0.2ms)
Cache digest for shared/dashboard/_posts.zip: 9ab674810fd35b48e90f98369bd6752f
Read fragment views/posts/32034-20130404145501/9ab674810fd35b48e90f98369bd6752f (0.2ms)
Cache digest for shared/dashboard/_posts.zip: 9ab674810fd35b48e90f98369bd6752f
Read fragment views/posts/32031-20130403141950/9ab674810fd35b48e90f98369bd6752f (0.2ms)
default_url_options is passed options: {}

Rendered shared/dashboard/_posts.haml (41.3ms)
Rendered shared/common/_page_scroll.haml (0.8ms)
Rendered dashboard/users/dashboard.haml within layouts/application (58.0ms)
Rendered layouts/_title.haml (0.1ms)
Rendered shared/_top_bar.haml (7.1ms)
Rendered shared/common/_pm_dialog.haml (4.7ms)
Rendered layouts/_ban_ie.haml (0.2ms)
Rendered layouts/_footer.haml (0.5ms)
Rendered layouts/_cnzz.haml (0.2ms)
Completed 200 OK in 1930ms (Views: 1928.5ms | ActiveRecord: 0.5ms | Solr: 0.0ms)

Stack level too deep

See issue # 23 in which I was asked to open a new issue. This is still a problem.

Using JRuby 1.7.2 and rails 3.2.12. I am using the "closure_tree" gem that has some sort of recursion. Don't know if that is causing this.

SystemStackError - stack level too deep:
org/jruby/RubyProc.java:261:in call' org/jruby/RubyProc.java:249:incall'
org/jruby/RubyHash.java:681:in default' org/jruby/RubyHash.java:1070:in[]'
(gem) actionpack-3.2.12/lib/action_view/template/resolver.rb:127:in query' org/jruby/RubyArray.java:2595:inreject!'
org/jruby/RubyArray.java:2558:in reject' (gem) actionpack-3.2.12/lib/action_view/template/resolver.rb:126:inquery'
(gem) actionpack-3.2.12/lib/action_view/template/resolver.rb:117:in find_templates' (gem) actionpack-3.2.12/lib/action_view/template/resolver.rb:46:infind_all'
(gem) actionpack-3.2.12/lib/action_view/template/resolver.rb:77:in cached' (gem) actionpack-3.2.12/lib/action_view/template/resolver.rb:45:infind_all'
(gem) actionpack-3.2.12/lib/action_view/path_set.rb:65:in find_all' org/jruby/RubyArray.java:1613:ineach'
(gem) actionpack-3.2.12/lib/action_view/path_set.rb:64:in find_all' org/jruby/RubyArray.java:1613:ineach'
(gem) actionpack-3.2.12/lib/action_view/path_set.rb:63:in find_all' (gem) actionpack-3.2.12/lib/action_view/path_set.rb:58:infind'
(gem) actionpack-3.2.12/lib/action_view/lookup_context.rb:109:in find' (gem) cache_digests-0.2.0/lib/cache_digests/template_digestor.rb:79:insource'
(gem) cache_digests-0.2.0/lib/cache_digests/template_digestor.rb:43:in digest' (gem) cache_digests-0.2.0/lib/cache_digests/template_digestor.rb:32:indigest'
(gem) activesupport-3.2.12/lib/active_support/cache.rb:297:in fetch' (gem) activesupport-3.2.12/lib/active_support/cache.rb:520:ininstrument'
(gem) activesupport-3.2.12/lib/active_support/cache.rb:296:in fetch' (gem) cache_digests-0.2.0/lib/cache_digests/template_digestor.rb:31:indigest'
(gem) cache_digests-0.2.0/lib/cache_digests/template_digestor.rb:85:in dependency_digest' org/jruby/RubyArray.java:2348:incollect'
org/jruby/RubyArray.java:2356:in collect' (gem) cache_digests-0.2.0/lib/cache_digests/template_digestor.rb:84:independency_digest'
(gem) cache_digests-0.2.0/lib/cache_digests/template_digestor.rb:43:in digest' (gem) cache_digests-0.2.0/lib/cache_digests/template_digestor.rb:32:indigest'
(gem) activesupport-3.2.12/lib/active_support/cache.rb:297:in fetch' (gem) activesupport-3.2.12/lib/active_support/cache.rb:520:ininstrument'
(gem) activesupport-3.2.12/lib/active_support/cache.rb:296:in fetch' (gem) cache_digests-0.2.0/lib/cache_digests/template_digestor.rb:31:indigest'
(gem) cache_digests-0.2.0/lib/cache_digests/template_digestor.rb:85:in dependency_digest' org/jruby/RubyArray.java:2348:incollect'
org/jruby/RubyArray.java:2356:in collect' (gem) cache_digests-0.2.0/lib/cache_digests/template_digestor.rb:84:independency_digest'
(gem) cache_digests-0.2.0/lib/cache_digests/template_digestor.rb:43:in digest' (gem) cache_digests-0.2.0/lib/cache_digests/template_digestor.rb:32:indigest'
(gem) activesupport-3.2.12/lib/active_support/cache.rb:297:in fetch' (gem) activesupport-3.2.12/lib/active_support/cache.rb:520:ininstrument'
(gem) activesupport-3.2.12/lib/active_support/cache.rb:296:in fetch' (gem) cache_digests-0.2.0/lib/cache_digests/template_digestor.rb:31:indigest'
(gem) cache_digests-0.2.0/lib/cache_digests/template_digestor.rb:85:in dependency_digest' org/jruby/RubyArray.java:2348:incollect'
org/jruby/RubyArray.java:2356:in collect' (gem) cache_digests-0.2.0/lib/cache_digests/template_digestor.rb:84:independency_digest'
(gem) cache_digests-0.2.0/lib/cache_digests/template_digestor.rb:43:in digest' (gem) cache_digests-0.2.0/lib/cache_digests/template_digestor.rb:32:indigest'
(gem) activesupport-3.2.12/lib/active_support/cache.rb:297:in fetch' (gem) activesupport-3.2.12/lib/active_support/cache.rb:520:ininstrument'
(gem) activesupport-3.2.12/lib/active_support/cache.rb:296:in fetch' (gem) cache_digests-0.2.0/lib/cache_digests/template_digestor.rb:31:indigest'
(gem) cache_digests-0.2.0/lib/cache_digests/template_digestor.rb:85:in dependency_digest' org/jruby/RubyArray.java:2348:incollect'
org/jruby/RubyArray.java:2356:in collect' (gem) cache_digests-0.2.0/lib/cache_digests/template_digestor.rb:84:independency_digest'
(gem) cache_digests-0.2.0/lib/cache_digests/template_digestor.rb:43:in `digest'

Not having issues if I remove "cache_digests". It works without causing the "stack too deep" problem with just fragment caching

application.html.erb has:

<% root_children = Category.root.children %>
                    <% cache "menu" do %>
                        <ul class="nav">
                          <% root_children.each do |c| %>
                            <%= render partial: "categories/menu", locals: {category: c} %>
                          <% end %>
                        </ul>
                    <% end %>

category/_menu.html.erb

<% if not (category.leaf?) %>
    <li class="dropdown">
      <a data-toggle="dropdown" class="dropdown-toggle" href="#"><%= category.name %><span class="caret"></span></a>
      <ul class="dropdown-menu">
        <li>
            <%= link_to "All #{pluralize("", category.name)}'", items_path(category_id: category)  %>
        </li>
        <% category.children.each do |c| %>
            <%= render partial: "categories/menu", locals: {category: c} %>
        <% end %>
      </ul>
    </li>
<% else %>
    <%= render partial: "categories/menu_item", locals: {category: category} %>
<% end %>

category/_menu_item.html.erb

<li>
  <%= link_to "#{category.name}", items_path(category_id: category) %>
</li>

Issues with dynamic partial names

I have something like this:

<% cache [object] do %>
  <%= render partial: "item_features_#{object.profile}", locals: { object: object } %>
 ...
<% end %>

And in logs I see this from time to time:

Couldn't find template for digesting: objects/item_features_.html

Maybe I am doing it wrong, and should just cache item_features_* instead?

ActionMailer undefined method `perform_caching'

It is impossible to include a partial with cache into email to be sent using ActionMailer.

ActionView::Template::Error (undefined method `perform_caching' for #<ContactMailer:0x007f8dc14f5578>):
1: <% cache [object, admin?] do %>
...

So I have added a helper to the mailer:

helper_method :cache
def cache *args
  yield
end

But this seems a bit half-assed.

I18n.t inside partial

Let's assume that we have partial like below:

<% cache @post do %>
  <%= t(:post_created_at) %> <%= @post.created_at %>
<% end %>

Caching doesn't know about locales and it won't replace cache if locale is changed.

The following code works.

<% cache [I18n.locale, @post] do %>
  <%= t(:post_created_at) %> <%= @post.created_at %>
<% end %>

Will caching implicitly depend on I18n.locale in future versions?

Release to RubyGems?

When I used cache_digests on my last project I had to do what is now being done automatically after #48. Now that I came back after almost 6 months and I saw the notice on the README I thought that things would just work but it didn't. After some debugging I found out that that code has not been released yet :-P

Would anyone be able to push a new version to rubygems? I'm referencing the github project on my Gemfile but would be awesome to use a released version.

Thanks a lot in advance :-)

Expire partial template?

I have two templates as follow:

app/views/projects/show.html.erb

<% cache project do %>
All documents
<%= render project.documents %>
<% end %>

app/views/documents/_document.html.erb

<% cache document do %>
My document: <%= document.name %>
<%= render document.comments %>

<% end %>

When I change html in _document.html.erb, I refresh the page, but it does not update.
What should I do so that the view auto update when I change partial template?

Thanks.

Using cache_digests with cache("custom_name") not working

<% cache "menu" do %>
    bla bla...
<% end %>

I'm manually invalidating this cache by (it's working okay without cache_digests):

expire_fragment("menu")

Without cache_digests I'm getting this log:

Read fragment views/menu

After bundling cache_digests I'm getting this:

Read fragment views/menu/0fe212b51fb84adbcc47ef7e93bef477

Hash added after this fragment causes that I can't manually invalidate expire_fragment("menu").

Not detecting correct partial for model.association

I believe that cache_digests is not picking up the correct partial:

app/views/feed_statuses/_feed_status.html.erb

<% cache feed_status do %>
  <header>
    <%= render feed_status.user %>
    <%= timestamp(feed_status.created_at) %>
  </header>

  <section>
    <p><%= auto_link(feed_status.body) %></p>
  </section>
<% end %>

rake cache_digests:nested_dependencies TEMPLATE=feed_statuses/_feed_status

[
  "feed_statuses/feed_status.user"
]

Based on the README, which states that render(message.topics) => render("topics/topic"), I would expect this to understand the singular association as well. Is that not correct?

expected:

[
  "users/user"
]

'stack level too deep' with recursive partial

I have a partial that recursively renders a nested list of comments. When I try to run rake cache_digests:nested_dependencies on it, rake fails with stack level too deep.

Using ruby-1.9.3-p194, rails 3.2.13, and cache_digests 0.2.0:

<%# app/views/comments/_comment.html.erb
<%= comment.text %>
<% if comment.replies.count > 0 %>
  <% comment.replies.each do |reply| %>
    <%= render :partial => "comments/comment", :locals => { :comment => reply } %>
  <% end %>
<% end %>

When I try to analyze it:

$ rake cache_digests:nested_dependencies TEMPLATE=comments/_comment
rake aborted!
stack level too deep

Any thoughts? Is it possible that this is just a problem with the nested_dependencies rake task, and wouldn't cause issues in production? (I haven't deployed yet because I wanted to double-check the dependency graph first...)

Jbuilder support

I'm trying to use cache_digest gem with jbuilder (currently using Rails 3.x)
I can't seem to make it work like this.

cache @videos do 
  json.partial! "api/videos/video", collection: @videos, as: :video
end

It throws an error:

NoMethodError - undefined method `length' for nil:NilClass: actionpack (3.2.18) lib/action_view/helpers/cache_helper.rb:52:in`fragment_for' cache_digests (0.3.1) lib/cache_digests/fragment_helper.rb:22:in `fragment_for'

Calling cache([object]) and cache(object) Using the Same Key

It appears cache keys are identical for an ActiveRecord::Base and ActiveRecord::Relation if the ActiveRecord::Relation is the single ActiveRecord::Base object. For example:

Person.create(name: "Kevin")

@person = Person.find_by(name: "Kevin") # <Person name: "Kevin">
@people = Person.where(name: "Kevin") # <ActiveRecord::Relation [<Person name: "Kevin">]>

@person.to_json # { name: "Kevin" }
@people.to_json # [{ name: "Kevin" }]

This causes a bug with the following snippet:

<% # _json.html.erb %>
<% cache object do %>
<%= object.to_json %>
<% end %>

Results:

<% # random.html.erb %>
<%= render 'json', object: @people %> # [{ name: "Kevin" }]
<%= render 'json', object: @person %> # [{ name: "Kevin" }]

Note: the last two lines result in the same JSON although the second should not be nested inside an array.

The generated keys of item and items which size is 1 are the same

like this
the generated key of the item show is views/shows/28608-20130704070313/53b57e0d52d1d769538e3a7b94a81cae

the generated key of item array shows which only contain the item show above-mentioned is views/shows/28608-20130704070313/53b57e0d52d1d769538e3a7b94a81cae too

is this a bug?

<% cache @shows do %>
       ***
     <% @shows.each do |show| %>
            <% cache(show) do %>
                    ***
            <% end %>
     <% end %>
      ***
<% end%>

when the shows's size is 1, it's wrong.

belongs_to association not touching correctly

Let's say I have a model like:

class Person < ActiveRecord::Base
  # content...
end

and another:

class Bike < ActiveRecord::Base
  belongs_to :person, touch: true
end

If I change any attribute of bike, the person should be touched. That's ok.

The things is: if I change the Bike Person from Joao to Maria, only Maria is touched, while Joao are not.

Is that a bug, or I have to do something about it?

Thanks in advance.

Question: Using read_multi when appropriate

Do you think there is much benefit to adding tracking of the keys and using read_multi if there are a lot?

I know the goal of this gem is that in the end you only have a few keys since changes propagate up. However, I'm using this on a site that is kind of hard to do that which results in a lot of cache reads. I'm mostly using this gem for the key change when the template is updated feature.

I'd be happy to investigate if you think it would be worth it.

Changes to helpers don’t bust the cache

Skimming through the code it looks like if a template calls a helper; and the helper is changed; then the digest for the cache won’t change and the cache won’t be busted. If this is indeed the case it’s something to be aware of and I think it should be mentioned in the readme. I’m happy to make the change.

Missing rake tasks in Rails 4

This gem offers great rake tasks:

rake cache_digests:dependencies 
rake cache_digests:nested_dependencies

Although cache_digests was merged into Rails 4, the rake tasks weren't?

Is there any reason for this?

problem when using fragment caching without digests

Hi, I have the following situation:
My navigation is organized tree-based structure that is rendered recursively by partials.
Because of that complex recursive structure I stopped trying to achieve this with cache_digests.
So I tried to implement a global fragment cache for the whole navigation at once that doesn't use digests:

<% cache('navigation', :skip_digest => false) do %>
  <%= render :partial => "layouts/navigation_element", collection: NavigationElement.roots, :as => :navigation_element %>
<% end %>

That worked as excepted and the navigation gets cached. But I also get some errors in the log that refers to cache_digest:
[ERROR] Couldn't find template for digesting: navigation_elements/navigation_element.html

I think the render directive still tries to generate a digest for navigation_element although it isn't used.

So I tried to use the skip_digest option, that doesn't seem to have any effect in here.

This error message has also been referenced in this issue: #31
and the recommendation was to just ignore it. But I do not really feel right with this.

Is there any possibility to just turn off cache_digests for this part of my homepage?

Thanks

Request: allow explicit opt-out of digest

Because Memcache has no way of searching for a key by regex and cache_digests adds an MD5 hash to the end of all cache keys (with the notable exception of any keys that are arrays with the first element being "v#"), I humbly request an additional way to indicate an explicit opt-out of the addition of the fragment digest for a single cache call. This would allow something like this:

<%= cache ['v1', 'sidebar-navigation'] do %>
  <%= render "sidebar-item", :collection => expensive_queried_collection %>
<% end %>

My cached navigation only needs to be invalidated after I update one of the items in the collection but there's no way to find this using Memcache due to the MD5 hash. In this circumstance, having a key without an MD5 hash would allow easy lookup and expiration.

Implementation ideas:

<%# view %>
<%= cache 'sidebar-navigation', :skip_cache_digest => false do %>
# lib/cache_digests/fragment_helper.rb
def fragment_for(key, options = nil, &block)
  skip_digest = expicitly_versioned_cache_key? || (options && options.delete(:skip_cache_digest))
  # ...
end

I'll submit a PR if this idea seems acceptable.

Cache is not being invalidated

Inside a page, I cache its fragment like this:

  • cache 'testimonials' do
    = render "template_name"

When I change template_name content, the cache is not being invalidated (its content is not re-rendered).

Request: cache semi-static pages?

Maybe I'm too new at this, but is there any way this could be used to cache static pages generated with embedded ruby (html.erb)?

example: I have some marketing pages with embedded ruby in my InfoController.

An about us page, tutorial page, a downloads page, and these will only ever change between code updates.

I'm not sure how to implement this, or if cache digests are even the correct way to do it.

something like

# in InfoController#about
<% cache %>
    <h1>About</h1>
    <p>This is a Software as a Service web application</p>
    <%= link_to 'learn how to use the software', tutorial_path %>
<% end %>

Word 'rendered' in comment detected as dependency

Comments containing the word 'rendered' mistakenly get interpreted as a dependency on a template called 'eds/ed'.

# app/views/sample/sample.html.erb
<%# I get rendered in a cool way. %>
$ rake cache_digests:nested_dependencies TEMPLATE=sample/sample
[
  "eds/ed"
]

This is under Rails 3.2.9, ruby-1.9.3-p194, cache_digests 0.2.0

Does this work with haml?

I am having trouble getting this to work. I update the partial but the caching is still not refreshing.

Let me know if this is compatible with haml and i'll post some code snippets.

Should make it clear that this doesn't work with code reloading in development

It wasn't until I inspect the source of CacheDigests::TemplateDigestor that I realized the digests themselves are only compute once and cached in a MemoryStore.

It would be nice if cache_digests could detect if class caching is disabled in Rails, then disable this caching of digests, following the principle of least surprise.

Would it make sense to accept a proc as a way to specify explicit dependencies?

We're building an application that allows the users to create their own templates for sections of the app. This is similar to Shopfiy or Wordpress - users can create themes which have multiple templates.

However this makes it hard to deal with the explicit dependencies in cache_digests. The format <%# Template Dependency: todolists/todolist %> doesn't allow for a dynamically changing set of template dependencies.

I was wondering whether a proc would be a reasonable way to return a set of templates that the container template depends on?

<%# Template Dependency: { | h | h.return_dependent_templates } %>

It's taking me a while to wrap my head around the implications of this and whether this in fact the right approach or whether it just starts to break everything from the inside out. I wanted to just raise it and see your thoughts.

There's another example of a slightly different version of this problem in this stack overflow question.

dependency not correct when rendering partial from same view tree

With a tree structure as such:
views -> tracker -> config_items
This dependency:

<%= render 'some_view' %>

Gets calculated as 'tracker/some_view' insead of 'tracker/config_items/some_view'

Explicitly setting the path in the render call as such:

<%= render '/tracker/config_items/some_view' %>

Works correctly.

Register erb tracker for slim

DependencyTracker::ERBTracker seems to be properly working for slim too. Is it not registered for slim on purpose?

Are you supposed to register the ERBTracker for slim in an initializer?

template dependencies aren't being calculated at all?

I notice that my caches don't get busted up the hierarchy like I expect them to.

invocations of rake cache_digests:dependencies and rake cache_digests:nested_dependencies suggest that rails thinks there are no dependencies:

➔ rake cache_digests:nested_dependencies TEMPLATE=posts/show
[

]
➔ rake cache_digests:nested_dependencies TEMPLATE=posts/show
[

]

poking around in the console agrees with this:

app(dev)> finder = ApplicationController.new.lookup_context
app(dev)> d = ActionView::Digestor.new(name: "posts/show", finder: finder)
app(dev)> d.digest
  Cache digest for app/views/posts/show.html.haml: 42bf3496bacfcf84492d8c05d81305fe
=> "42bf3496bacfcf84492d8c05d81305fe"
app(dev)> d.dependencies
=> []

However, the posts show template has many dependencies. A couple examples, with names changed:

= render partial: "myspecialpartial"
= render partial: "discussions/thing", locals: {bar: @foo.bar, baz: nil}

rails 4.1.8, haml 4.0.5, config.assets.digest = true

Overwrite cache content with dynamic parts

I have a partial that contains a section of code in a cache project do block as normal.

Within the code of the partial I output a snippet of the project description - first 100 characters using truncate - which is fine when just listing projects.

However, if the user performs a search of projects and the search term is contained in the project description then when I ouput the description snippet as part of the partial I would like to replace the basic snippet with a snippet that relates to the search term (eg 10 words either side of the search term using excerpt).

I can do this replacement using javascript (setting the dynamic description as a data attribute on the div container and using it to overwrite the description text) after loading the cached html but I was wondering if it is possible to replace parts of the cached html using rails before outputting it out to the screen removing the need for it to be done using javascript (which could otherwise cause a flash of the basic description before overwriting it).

I thought about using two cache blocks in the partial (one either side of the description) but I've just hit another part of the partial that I would like to be dynamic as well and was wondering if it was possible to pass the output of cache project do into a replace function or something that replaces part of the html with the dynamic part somehow and then outputs the html.

There are still enough parts of my partial to warrant it being cached.

Custom template resolvers and digest caching.

I'm running into an issue that makes it hard to use Cache Digests in some cases. In the app I'm working on, users can upload custom templates. When these templates are rendered directly as views, Cache Digests works fine -- the template is resolved by a custom resolver, and the template handler injects a cache call that includes the template's digest (computed separately) in the cache key. This trick doesn't work if the custom template is rendered as a partial, as it is assumed that a template does not change at runtime.

I can get around this by disabling caching of digests -- then all templates are loaded and their digests computed. I could even get rid of my custom digest hack that predates Cache Digests. However, this would impact performance.

If Cache Digests included the view path in the cache keys, I think the issue would go away. We could ask each resolver in the path for a cache key and include them in the final cache key. That way, my custom resolver could just check if there have been any changes to the templates since last time and compute a cache key accordingly.

Is this something you would be interested in having in Cache Digests? It feels like it would touch too deeply into Rails, so perhaps it should just go there instead.

stack level too deep

Hello,

This morning I tried to use cache_digests on my rails4 app.
I tried with a simple code on my users#edit.html.haml view:

%div{:class=>"container-fluid", :id => 'profile'}
    .well
        .row-fluid
            #avatar= render :partial => 'users/profile/avatar'
            #personalities= render :partial => 'users/profile/personalities'
        .row-fluid
            #offers= render :partial => 'users/profile/offers'
            #contacts= render :partial => 'users/profile/contacts'
            #connections= render :partial => 'users/profile/connections'
        .row-fluid
            #images= render :partial => 'users/profile/images'

:javascript
    simpleFormField();
    simpleFormCheckbox();

- cache do
    toto

And surprise I got this message:

Cache digest for users/profile/avatar.html: 601b4fba0220b21478222b7ec53b4ec0
Cache digest for users/profile/personalities.html: c89e0f02eaeb2359fc9ef2d377bd8baf
Cache digest for users/profile/offers.html: 6a2f845587bc00b24f3c80ce5ca338bc
Cache digest for users/profile/contacts.html: cc807b021cc3b52206bae3f77eaea5a9
Cache digest for users/profile/omniauth.html: 710eaf3242bbc3901951774618605f43
Cache digest for users/profile/connections.html: 35aa840682ad2157cb52d0412d43b470
Cache digest for users/profile/images.html: 9b6a871b191588c98ebddfdd08c06a75
Cache digest for users/edit.html: 63cf22204875976adc0847c7cd2c312c
Rendered users/edit.html.haml within layouts/application (263.5ms)
Completed 500 Internal Server Error in 759ms

ActionView::Template::Error (stack level too deep):
/Users/uto/.rvm/gems/ruby-1.9.3-p327/bundler/gems/rails-5d54fd77b8e8/activesupport/lib/active_support/cache.rb:0

Rendered /Users/uto/.rvm/gems/ruby-1.9.3-p327/bundler/gems/rails-5d54fd77b8e8/actionpack/lib/action_dispatch/middleware/templates/rescues/_trace.erb (1.3ms)
Rendered /Users/uto/.rvm/gems/ruby-1.9.3-p327/bundler/gems/rails-5d54fd77b8e8/actionpack/lib/action_dispatch/middleware/templates/rescues/_request_and_response.erb (1.1ms)
Rendered /Users/uto/.rvm/gems/ruby-1.9.3-p327/bundler/gems/rails-5d54fd77b8e8/actionpack/lib/action_dispatch/middleware/templates/rescues/template_error.erb within rescues/layout (16.8ms)

My Gemfile:

source 'https://rubygems.org'

gem 'rails', :git => 'git://github.com/rails/rails.git'
gem "journey", :git => "git://github.com/rails/journey"
gem 'activerecord-deprecated_finders', :git => 'git://github.com/rails/activerecord-deprecated_finders.git'
gem 'turbolinks', "= 0.5.1"
gem 'haml-rails', :git => 'git://github.com/indirect/haml-rails.git'
gem 'sprockets-rails', :git => 'git://github.com/rails/sprockets-rails.git'

group :assets do
gem 'sass-rails', :git => 'git://github.com/rails/sass-rails.git'
gem 'coffee-rails', :git => 'git://github.com/rails/coffee-rails.git'
gem 'less-rails'
gem 'twitter-bootstrap-rails'
gem 'less-rails-fontawesome', :git => 'git://github.com/GabKlein/less-rails-fontawesome.git'
gem 'therubyracer'
gem 'uglifier'
end

gem 'jquery-rails'
gem 'jquery-cookie-rails'
gem 'jquery-turbolinks'

gem 'ohm'
gem 'ohm-contrib'
gem 'mysql2'
gem "mongoid", :git => 'git://github.com/mongoid/mongoid.git', :branch => "4.0.0-dev"
gem 'tire', :git => 'git://github.com/GabKlein/tire.git'
gem 'tire-contrib'

gem 'dalli'
gem 'cache_digests'

gem 'redis'
gem 'redis-store', :git => 'git://github.com/jodosha/redis-store.git'
gem 'redis-objects', :require => 'redis/objects'

gem 'authlogic'
gem 'omniauth-google-oauth2', :git => 'git://github.com/zquestz/omniauth-google-oauth2.git'
gem 'omniauth-facebook', :git => 'git://github.com/mkdynamic/omniauth-facebook.git'
gem 'fb_graph'

gem 'will_paginate', '~> 3.0'
gem 'uuidtools'
gem 'tlsmail'
gem 'geocoder'
gem 'rmagick'
gem 'carrierwave', :git => 'git://github.com/jnicklas/carrierwave.git'
gem 'activerecord-reputation-system', :git => 'git://github.com/GabKlein/activerecord-reputation-system.git'
gem 'unicorn'

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.