Skip to content

Instantly share code, notes, and snippets.

@dkolath
Created January 6, 2017 23:18
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save dkolath/c306b6e72f6109dda49e91c7323382af to your computer and use it in GitHub Desktop.
Save dkolath/c306b6e72f6109dda49e91c7323382af to your computer and use it in GitHub Desktop.
decorator pattern that defines the method the first time it delegates
class ModelDecorator
module Decorated
def self.extended(base)
base.send(:include, InstanceMethods)
end
def decorate(object)
@decorated_object ||= object
end
def decorated_object
@decorated_object
end
module InstanceMethods
def decorated
instance_variable_get "@#{self.class.decorated_object}".to_sym
end
end
end
extend Decorated
def method_missing(method_name, *args, &block)
if decorated.respond_to?(method_name)
self.class.class_eval %Q[
def #{method_name}(*args, &block)
decorated.send(:#{method_name}, *args, &block)
end
]
send(method_name, *args, &block)
else
raise NoMethodError, "Decorated object #{decorated} does not implement #{method_name}"
end
end
end
class DecoratedPerson < ModelDecorator
decorate :person
def initialize(person)
@person = person
end
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment