Sha256: 01b781bbdc4e989edcbf7e8e66225d7a2a8fbd0fb6f32a9e39786769ce63e40c

Contents?: true

Size: 1.81 KB

Versions: 1

Compression:

Stored size: 1.81 KB

Contents

module SuperSTI
  module Hook
    
    ######
    # has_extra_data(options = {})
    #
    # In it's most raw form, this method creates an associated Data class, 
    # which seamlessly adds attributes and methods to the main class
    #
    # If passed a block, extra attributes can be set on the data table, 
    # methods (e.g. has_many) can be called, and other methods can be defined.
    #
    # Options:
    #   table_name: The table name of the class
    #####
    def has_extra_data(options = {}, &block)

      table_name = options[:table_name] || "#{self.name.underscore.gsub("/", "_")}_data"
      klass = Class.new(ActiveRecord::Base) do
        set_table_name(table_name)
      end
      klass.class_eval &block if block_given?
      self.const_set "Data", klass
  
      # Add a reference to a data object that gets created when this is created
      has_one :data, :class_name => "#{self.name}::Data", :foreign_key => options[:foreign_key]
      before_create :get_data
      
      # A helper method which gets the existing data or builds a new object
      define_method :get_data do
        data || build_data
      end
      
      # Override respond_to? to check both this object and its data object.
      define_method "respond_to?" do |sym, include_private = false|
        super(sym, include_private) || get_data.respond_to?(sym, include_private)
      end
      
      # Override method_missing to check both this object and it's data object for any methods or magic functionality.
      # Firstly, try the original method_missing because there may well be 
      # some magic piping that will return a result and then try the data object.
      define_method :method_missing do |sym, *args|
        begin
          super(sym, args)
        rescue
          get_data.send(sym, *args)
        end
      end
    end
  end
end

Version data entries

1 entries across 1 versions & 1 rubygems

Version Path
super_sti-0.2.1 lib/super_sti/hook.rb