Module: PropertySets::ActiveRecordExtension::ClassMethods

Defined in:
lib/property_sets/active_record_extension.rb

Instance Method Summary collapse

Instance Method Details

#property_set(association, options = {}, &block) ⇒ Object



9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
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
# File 'lib/property_sets/active_record_extension.rb', line 9

def property_set(association, options = {}, &block)
  unless include?(PropertySets::ActiveRecordExtension::InstanceMethods)
    self.send(:prepend, PropertySets::ActiveRecordExtension::InstanceMethods)
    cattr_accessor :property_set_index
    self.property_set_index = Set.new
  end

  raise "Invalid association name, letters only" unless association.to_s =~ /[a-z]+/
  self.property_set_index << association

  property_class = PropertySets.ensure_property_set_class(
    association,
    options.delete(:owner_class_name) || self.name
  )
  property_class.instance_eval(&block)

  hash_opts = {:class_name => property_class.name, :autosave => true, :dependent => :destroy}.merge(options)

  silence_warnings do
    has_many association, hash_opts do
      include PropertySets::ActiveRecordExtension::AssociationExtensions

      property_class.keys.each do |key|
        raise "Invalid property key #{key}" if self.respond_to?(key)

        # Reports the coerced truth value of the property
        define_method "#{key}?" do
          type  = property_class.type(key)
          value = lookup_value(type, key)
          ![ "false", "0", "", "off", "n" ].member?(value.to_s.downcase)
        end

        # Returns the value of the property
        define_method "#{key}" do
          type = property_class.type(key)
          lookup_value(type, key)
        end

        # Assigns a new value to the property
        define_method "#{key}=" do |value|
          instance = lookup(key)
          instance.value = PropertySets::Casting.write(property_class.type(key), value)
          instance.value
        end

        define_method "#{key}_record" do
          lookup(key)
        end
      end

      define_method :property_serialized? do |key|
        property_class.type(key) == :serialized
      end
    end
  end
end