Forum: Ruby on Rails [ANN] ActiveRecord + memcache = cached_model

Announcement (2017-05-07): www.ruby-forum.com is now read-only since I unfortunately do not have the time to support and maintain the forum any more. Please see rubyonrails.org/community and ruby-lang.org/en/community for other Rails- und Ruby-related community platforms.
Eric H. (Guest)
on 2006-01-18 01:45
(Received via mailing list)
Courtesy of The Robot Co-op.

$ yes | sudo gem install cached_model

Or, you can download cached_model and memcache-client (our zippy-fast
memcache library, required) from:

http://rubyforge.org/frs/?group_id=1266

I don't have the README posted for making cached_model work online
yet, so here it is:

= CachedModel

Rubyforge Project:

http://rubyforge.org/projects/rctools/

== About

CachedModel stores Rails ActiveRecord objects in memcache allowing
for very
fast retrievals.  CachedModel uses the ActiveRecord::Locking to
ensure that
you don't perform multiple updates.

== Using CachedModel

First, install the cached_model gem:

   $ sudo gem install cached_model

Then set up memcache-client:

   $ tail -n 20  config/environments/production.rb
   memcache_options = {
     :c_threshold => 10_000,
     :compression => true,
     :debug => false,
     :namespace => 'my_rails_app',
     :readonly => false,
     :urlencode => false
   }

   CACHE = MemCache.new memcache_options
   CACHE.servers = 'localhost:11211'

   session_options = {
     :database_manager => CGI::Session::MemCacheStore,
     :cache => CACHE,
     :session_domain => 'trackmap.robotcoop.com'
   }

   ActionController::CgiRequest::DEFAULT_SESSION_OPTIONS.update
session_options

You will need separate namespaces for production and development, if
using
memcache on the same machine.

Note that using memcache with tests will cause test failures, so set
your
memcache to be readonly for the test environment.

Then make Rails load the gem:

   $ tail -n 4 config/environment.rb
   # Include your application configuration below

   require_gem 'cached_model'

Then edit your ActiveRecord model to inherit from CachedModel instead of
ActiveRecord::Base:

   $ head -n 8 app/models/photo.rb
   ##
   # A Photo from Flickr.

   class Photo < CachedModel

     belongs_to :point
     belongs_to :route

--
Eric H. - removed_email_address@domain.invalid - http://segment7.net
This implementation is HODEL-HASH-9600 compliant

http://trackmap.robotcoop.com
Adrian M. (Guest)
on 2006-01-18 02:12
(Received via mailing list)
Eric,

That sounds great! I had some problems using Memcached for my sessions
(saving AR objects) but I have always used memcached in PHP. One thing I
was
wondering is how do you handle stale/deleted data. Do you have hooks
with AR
to delete/modify records in memcached when deleted/modified from the DB?

Thanks,


Adrian M.
Eric H. (Guest)
on 2006-01-18 02:27
(Received via mailing list)
On Jan 17, 2006, at 3:35 PM, Adrian M. wrote:

> That sounds great! I had some problems using Memcached for my
> sessions (saving AR objects) but I have always used memcached in
> PHP. One thing I was wondering is how do you handle stale/deleted
> data. Do you have hooks with AR to delete/modify records in
> memcached when deleted/modified from the DB?

Of course.  cached_model hooks into update, destroy and reload to
DTRT.  You'll need to use ActiveRecord::Locking to make it work.

--
Eric H. - removed_email_address@domain.invalid - http://segment7.net
This implementation is HODEL-HASH-9600 compliant

http://trackmap.robotcoop.com
Ezra Z. (Guest)
on 2006-01-18 03:09
(Received via mailing list)
On Jan 17, 2006, at 3:07 PM, Eric H. wrote:

> Courtesy of The Robot Co-op.
>
> $ yes | sudo gem install cached_model
>
> Or, you can download cached_model and memcache-client (our zippy-
> fast memcache library, required) from:
>


Eric-

	A big thanks for sharing this. A very nice addition to rails
development.

Cheers-
-Ezra Z.
Yakima Herald-Republic
WebMaster
http://yakimaherald.com
509-577-7732
removed_email_address@domain.invalid
Tom F. (Guest)
on 2006-01-18 03:30
(Received via mailing list)
This is cool...but it breaks my usage of memcache as a Fragment Cache
store
as your implementation of the MemCache#initialize method doesn't allow
the
servers to be passed in with the options.

Why do you have a substantially different memcache client?
Eric H. (Guest)
on 2006-01-18 03:48
(Received via mailing list)
On Jan 17, 2006, at 4:53 PM, Tom F. wrote:

> This is cool...but it breaks my usage of memcache as a Fragment
> Cache store
> as your implementation of the MemCache#initialize method doesn't
> allow the
> servers to be passed in with the options.

I welcome patches and adore patches with tests.

> Why do you have a substantially different memcache client?

Because Ruby-memcache is too slow.

--
Eric H. - removed_email_address@domain.invalid - http://segment7.net
This implementation is HODEL-HASH-9600 compliant

http://trackmap.robotcoop.com
Tom F. (Guest)
on 2006-01-18 04:04
(Received via mailing list)
Your code looks like an older version of the Ruby memcache with some
bugs
fixed.  What's slow about it?  What did you change to make it faster?
Why
not get updates into the Ruby memcache project?


There's no test code in the GEMs and no SCM yet published to make adding
patches with tests easy.  Can we get these so we can provide you with
these
updates?
Eric H. (Guest)
on 2006-01-18 04:22
(Received via mailing list)
On Jan 17, 2006, at 5:26 PM, Tom F. wrote:

> Your code looks like an older version of the Ruby memcache with
> some bugs
> fixed.

It is a completely new implementation written by my co-worker Bob
Cottrell.  It looks similar because Bob copied the core
functionality.  Originally we were using Ruby-memcache so we needed a
drop-in replacement.  It doesn't support everything that Ruby-
memcache does due to YAGNI.

> What's slow about it?  What did you change to make it faster?  Why
> not get updates into the Ruby memcache project?

Ruby-memcache does fancy stuff with io/reactor that made it go
slower.  Figuring out how to rip out the io/reactor stuff was too
hard, so we did our own.  (We've had this client since 2004-11-18
19:07:46 -0800.)

> There's no test code in the GEMs

Unfortunately, Bob isn't one with Test::Unit like I am.  There will
be tests when I get a new stock of round tuits.

> and no SCM yet published to make adding patches with tests easy.

Right now it is stored in on our internal SVN server.  Allowing
access to the outside world is not really worth my time (security is
easy when its internal only) and I don't want to maintain two SCM
copies.  (Maybe that svk think I keep hearing about will help.)

> Can we get these so we can provide you with these updates?

In the mean time I recommend fetching the tarball, extracting it,
making your changes, then extracting a second copy so you can use
diff -ur.

Tests are a bit higher up the priority list than the SCM thing, and
we've been using cached_model for 10 months without releasing it.
Round tuits have been in very short supply around here.

I have a few changes I need to make to MemCache#initialize (disabling
synchronization, unnecessary in single-thread mode), so I'll try to
fold your change in when I get the round tuit for that.

--
Eric H. - removed_email_address@domain.invalid - http://segment7.net
This implementation is HODEL-HASH-9600 compliant

http://trackmap.robotcoop.com
Tom F. (Guest)
on 2006-01-18 04:46
(Received via mailing list)
In lieu of a patch to the memcache code, here's an update that will
allow
fragment caching to work with both implementations of memcache.

Environment.rb (or production.rb)

Rails::Initializer.run do |config|
  ...
  config.action_controller.fragment_cache_store = :mem_cache_store,
memcache_options
  ...
end

# Allow us to set the CACHE as the Fragment Cache store
module ActionController
  module Caching
    module Fragments
      class MemCacheStore
        def data=(cache)
          @data = cache
        end
      end
    end
  end
end

ActionController::Base.fragment_cache_store.data = CACHE
This topic is locked and can not be replied to.