summaryrefslogtreecommitdiffstats
path: root/lib/puppet/util/cacher.rb
diff options
context:
space:
mode:
authorLuke Kanies <luke@madstop.com>2008-05-07 18:28:35 -0500
committerLuke Kanies <luke@madstop.com>2008-05-07 18:28:35 -0500
commit68d8d0ae0686939d94dae8ccc70e5582187335dc (patch)
treecee56d0235229b4682ae1f95e78351a7cb83c7d4 /lib/puppet/util/cacher.rb
parente936ef2426464b901638bf338c1c42590245b58f (diff)
downloadpuppet-68d8d0ae0686939d94dae8ccc70e5582187335dc.tar.gz
puppet-68d8d0ae0686939d94dae8ccc70e5582187335dc.tar.xz
puppet-68d8d0ae0686939d94dae8ccc70e5582187335dc.zip
Adding a module for handling caching information.
I keep having issues with integration tests keeping cached values around, and this module should hopefully give us a single place to invalidate all caches, thus making testing this much easier.
Diffstat (limited to 'lib/puppet/util/cacher.rb')
-rw-r--r--lib/puppet/util/cacher.rb67
1 files changed, 67 insertions, 0 deletions
diff --git a/lib/puppet/util/cacher.rb b/lib/puppet/util/cacher.rb
new file mode 100644
index 000000000..fbab9ab42
--- /dev/null
+++ b/lib/puppet/util/cacher.rb
@@ -0,0 +1,67 @@
+module Puppet::Util::Cacher
+ # Cause all cached values to be considered invalid.
+ def self.invalidate
+ @timestamp = Time.now
+ end
+
+ def self.valid?(timestamp)
+ unless defined?(@timestamp) and @timestamp
+ @timestamp = Time.now
+ return true
+ end
+ return timestamp >= @timestamp
+ end
+
+ def self.extended(other)
+ other.extend(InstanceMethods)
+ end
+
+ def self.included(other)
+ other.extend(ClassMethods)
+ other.send(:include, InstanceMethods)
+ end
+
+ module ClassMethods
+ private
+
+ def cached_attr(name, &block)
+ define_method(name) do
+ cache(name, &block)
+ end
+ end
+ end
+
+ module InstanceMethods
+ private
+
+ def cache(name, &block)
+ unless defined?(@cacher_caches) and @cacher_caches
+ @cacher_caches = Cache.new
+ end
+
+ @cacher_caches.value(name, &block)
+ end
+ end
+
+ class Cache
+ attr_reader :timestamp, :caches
+
+ def initialize
+ @timestamp = Time.now
+ @caches = {}
+ end
+
+ def value(name)
+ raise ArgumentError, "You must provide a block when using the cache" unless block_given?
+
+ @caches.clear unless Puppet::Util::Cacher.valid?(@timestamp)
+
+ # Use 'include?' here rather than testing for truth, so we
+ # can cache false values.
+ unless @caches.include?(name)
+ @caches[name] = yield
+ end
+ @caches[name]
+ end
+ end
+end