mhgbrown / cached_resource

Caching for ActiveResource
MIT License
80 stars 28 forks source link

instantiate object from nested json #33

Closed Daniel-ltw closed 6 years ago

Daniel-ltw commented 8 years ago

This is a problem when re-creating an object that is actually a nested json from the cache.

If the class does not exist, dalli would throw an error stating that it does not understand the constant.

For example

[{
  a: 1
  b: [{
        c: 5
        d: 6
        e: 7
      },
      {
        c: 4
        d: 5
        e: 6
      }] 
},
{
  a: 2
  b: [{
        c: 5
        d: 6
        e: 7
      },
      {
        c: 4
        d: 5
        e: 6
      }] 
}]

When gem tries to re-instantiate the a::b object, it would throw an error if that class does not exist.

Probably use hashie or ostruct could solve the problem @ https://github.com/mhgbrown/cached_resource/blob/master/lib/cached_resource/caching.rb#L90.

benoror commented 6 years ago

Having the same issue with a nested object... I am getting the following error:

NameError: uninitialized constant Helix::Diagnostic::Metadata
from /Users/benoror/.rvm/gems/ruby-2.4.1/gems/activesupport-4.2.8/lib/active_support/inflector/methods.rb:263:in `const_get

because Metadata class does not exist, it's just a nested JSON inside Helix::Diagnostic class:

{
  "id": "1",
  "name": "foobar",
  "metadata": {
    "name": "i'm not a class afaik =("
  }
}

inspecting the cached resource I get metadata as a separate Helix::Diagnostic::Metadata class:

[3] pry(main)> Helix::Diagnostic.find(1)
[cached_resource] READ helix/diagnostic/1
=> #<Helix::Diagnostic:0x007fd4416289d8
 @attributes=
  {"id"=>1,
   "name"=>"foobar",
   "metadata"=>
    #<Helix::Diagnostic::Metadata:0x007fd441628dc0
     @attributes=
      {"name"=>"i'm not a class afaik =("},
     @persisted=true,
     @prefix_options={}>},
 @persisted=true,
 @prefix_options={}>

Similar to the issue described here: https://github.com/redis-store/redis-store/issues/281

@Daniel-ltw did you find a workaround?

Daniel-ltw commented 6 years ago

One way was to create the empty class/object in the project. That would allow cached_resource to know how to instantiate the object.

Another way is to finish up https://github.com/mhgbrown/cached_resource/pull/22 and get that merged.

Also, there is the other way of thinking about things, why do we need to nest the object? Is there a better way to solve this with a different software design/architecture?

@benoror hope you get the solution that you need. At the time of my work on that specific project, the first option kind of works. If you have any other issues, feel free to drop another comment and I hope that I could help.

benoror commented 6 years ago

@Daniel-ltw you're awesome, that did the trick!

There you go, have a beer 🍺 !

Another way is to finish up #22 and get that merged.

Pinging the OP asap

Also, there is the other way of thinking about things, why do we need to nest the object? Is there a better way to solve this with a different software design/architecture?

In our case is a cached resource coming from a remote ActiveResource server, out of our control, so unfortunately no 😢


Have another one 🍺 !