Skip to content

Loading…

Caching Bugs - Corrupted/overwritten keys. Values that throw errors when fetched #424

Open
andrewhubbs opened this Issue · 4 comments

2 participants

@andrewhubbs

I am running into a pretty strange bug with caching RABL views.

I have a setup that looks something like this:

Relevant Config

# rabl_config.rb
Rabl.configure do |config|
  config.cache_all_output = true
  config.cache_sources = Rails.env != "development"
  config.include_json_root = false
  config.view_paths = [Rails.root.join("app/views")]
end

# relevant portions of Gemfile
ruby "2.0.0"

gem "rails", "3.2.13rc1"
gem "oj"
gem "rabl", "0.8.0"

Views

# employees/limited_show.rabl
object @employee
cache ["limited", root_object]
attributes :id, :name

# employees/show.rabl
object @employee
cache ["full", root_object]
attributes :secret_stuff
node do |employee|
  partial "employees/limited_show", object: employee
end
#...

# employees/index.rabl
collection @employees
extends "employees/show"

# companies/show.rabl
object @company
attributes :name
node :employees do |company|
  partial "employees/index", object: company.employees.active
end
#...

Note: Except for the two employee show views, I use the default cache keys throughout.

Controllers

# companies_controller.rb
def show
  @company = Company.find(params[:id])
end

# employees_controller.rb
def show
  @employee = Employee.find(params[:id])
  render "employees/#{current_user.admin? ? "" : "limited_"}show"
end

When I hit the companies#show controller, I expect/get cache keys like the following:

"rabl/companies/1-20130320204732//json"
"rabl/full/employees/2-20130320165909//hash"
"rabl/limited/employees/2-20130320165909//hash"

I am also getting additional cache keys on companies#show that I'm not expecting that look like this:

"rabl/employees/1-20130320204732//hash"

Does the collection view generate additional cache values other than the ones normally created by the view it extends?

When I hit the employees#show controller, I expect/get cache keys like the following (depending on user permissions):

"rabl/full/employees/2-20130320165909//hash"
"rabl/limited/employees/2-20130320165909//hash"
"rabl/full/employees/2-20130320165909//json"
"rabl/limited/employees/2-20130320165909//json"

Everything basically works when I visit either of those routes independently. Weird things happen when I visit one route after the other.

For instance, after loading the companies#show I will have the 3 cache keys above, and as expected they have different values:

Rails.cache.fetch("rabl/full/employees/2-20130320165909//hash") == Rails.cache.fetch("rabl/limited/employees/2-20130320165909//hash")
> false

but, if I then visit the employees#show, those cached values are the same.

Rails.cache.fetch("rabl/full/employees/2-20130320165909//hash") == Rails.cache.fetch("rabl/limited/employees/2-20130320165909//hash")
> true

It is like calling the show template directly and creating the JSON cached version is corrupting the hash version (which should only be getting read and not written anyways).

Furthermore, I am also getting spurious exceptions like ArgumentError (undefined class/module Team): when I fetch some keys from the cache.

Basically, if I hit the companies#show everything is fine and loads correctly. I can make changes and my expiration code works great as well. If I then hit the employees#show it also works fine and returns the correct data. But, when I hit the companies#show again after the employees#show I get back incorrect data for employees that excludes changes and excludes all additional partials from the employees/show.rabl that are attached as nodes. Both calls are read only and will always happen even if there are no changes to any DB records/cache invalidations between them. I am at a loss here for what is happening.

Any thoughts on what might be going on?

@andrewhubbs

It feels like there are probably 2 or 3 different bugs here:

  • Writing objects to the cache that cannot be fetched without raising an error
  • Writing to the cache when the expected key lookup should be a hit
  • Collection views that extend item views writing to the cache with different keys than what is in the cache function
  • Also, #413 is still a bug independent of any of this issue. Just thought I would bring it back up. :+1:
@andrewhubbs

@nesquena, why are all of the bugs about caching with RABL being ignored (there are at least 3 issues open)? I think caching is pretty important to RABL and there are likely some very serious bugs in it.

I am happy to help out but some guidance on what RABL is doing here would be helpful.

@nesquena
Owner

Sorry, don't mean to ignore caching bugs, honestly I am a bit overstretched right now working on too many different things. RABL Caching was originally implemented by @databyte and other contributors so it is not the first thing I reach towards when I want to put a little time into RABL. Also, it's not a huge personal pain I'm feeling on my own rabl projects at the moment but I fully recognize it's importance. If anyone else can help submit patches for caching, I am more then happy to review and apply. If I missed any then please let me know.

@nesquena
Owner

Speaking of which, take a look at #417 and see if that would help address any of the issues?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Something went wrong with that request. Please try again.