Module: CachedAttr::ClassMethods
- Defined in:
- lib/cached_attr.rb
Instance Method Summary collapse
-
#cached_attr(name, options = {}, &block) ⇒ Object
Defines an attribute on the including class.
Instance Method Details
#cached_attr(name, options = {}, &block) ⇒ Object
Defines an attribute on the including class.
33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 |
# File 'lib/cached_attr.rb', line 33 def cached_attr(name, = {}, &block) default_opts = { :writer => false, :method => false, :ttl => false } opts = default_opts.merge() class_eval do internal_retrieve_method = "__internal_retrieve_#{name}".to_sym define_method(internal_retrieve_method) do if block.nil? val = self.send(opts[:method]) else val = self.instance_exec(&block) end cached_attributes_store[name][:invoke_count] += 1 val end internal_init_method = "__internal_init_#{name}".to_sym define_method(internal_init_method) do |val = nil| unless cached_attributes_store.has_key?(name) cached_attributes_store[name] = {:call_count => 0, :invoke_count => 0} if val.nil? cached_attributes_store[name][:value] = self.send(internal_retrieve_method) cached_attributes_store[name][:expires] = Time.now + opts[:ttl] if opts[:ttl] else cached_attributes_store[name][:value] = val end end cached_attributes_store[name] end define_method("_#{name}_reset!".to_sym) do cached_attributes_store.delete(name) end define_method("_#{name}_expires".to_sym) do self.send(internal_init_method)[:expires] end define_method("_#{name}_call_count".to_sym) do self.send(internal_init_method)[:call_count] end define_method("_#{name}_invoke_count".to_sym) do self.send(internal_init_method)[:invoke_count] end define_method(name) do cache_val = self.send(internal_init_method) if opts[:ttl] && cache_val[:expires] && Time.now > cache_val[:expires] cache_val[:value] = self.send(internal_retrieve_method) cache_val[:expires] = Time.now + opts[:ttl] end cache_val[:call_count] = cached_attributes_store[name][:call_count] + 1 cache_val[:value] end if opts[:writer] define_method("#{name}=") do |val| self.send(internal_init_method, val) end end end end |