def belongs_to(association_name, metadata={})
      # foo_id
      id_getter = "#{association_name}_id".to_sym
      add_attribute(id_getter, :integer, metadata)
      add_association association_name, :belongs_to, metadata
      association_class_name = metadata.try(:fetch, :class_name, [name.split('::')[0..-2].join('::'), association_name.to_s.classify].reject(&:blank?).join('::'))

      define_method(id_getter) do
        ivar = "@#{id_getter}"
        if instance_variable_defined?(ivar)
          instance_variable_get(ivar)
        else
          if obj = send(association_name)
            instance_variable_set(ivar, obj.id)
          else
            instance_variable_set(ivar, nil)
          end
        end
      end

      # foo_id=
      define_method("#{id_getter}=") do |arg|
        instance_variable_set("@#{id_getter}", arg.to_i)
      end

      # foo
      define_method(association_name) do
        if instance_variable_defined?("@#{association_name}")
          instance_variable_get("@#{association_name}")
        elsif id = instance_variable_get("@#{association_name}_id")
          association_class = association_class_name.constantize

          if self.class.autoload_associations? && association_class.respond_to?(:find)
            instance_variable_set("@#{association_name}", association_class.find(id))
          end
        else
          instance_variable_set("@#{association_name}", nil)
        end
      end

      # foo=
      define_method("#{association_name}=") do |arg|
        association_class = association_class_name.constantize

        if instance_variable_defined?("@#{association_name}_id")
          remove_instance_variable("@#{association_name}_id")
        end
        instance_variable_set("@#{association_name}", association_class.cast(arg))
      end
    end
def belongs_to(association_name, metadata={})
      # foo_id
      id_getter = "#{association_name}_id".to_sym
      add_attribute(id_getter, :integer, metadata)
      add_association association_name, :belongs_to, metadata
      association_class_name = metadata.try(:fetch, :class_name, [name.split('::')[0..-2].join('::'), association_name.to_s.classify].reject(&:blank?).join('::'))

      define_method(id_getter) do
        ivar = "@#{id_getter}"
        if instance_variable_defined?(ivar)
          instance_variable_get(ivar)
        else
          if obj = send(association_name)
            instance_variable_set(ivar, obj.id)
          else
            instance_variable_set(ivar, nil)
          end
        end
      end

      # foo_id=
      define_method("#{id_getter}=") do |arg|
        instance_variable_set("@#{id_getter}", arg.to_i)
      end

      # foo
      define_method(association_name) do
        if instance_variable_defined?("@#{association_name}")
          instance_variable_get("@#{association_name}")
        elsif id = instance_variable_get("@#{association_name}_id")
          association_class = association_class_name.constantize

          if self.class.autoload_associations? && association_class.respond_to?(:find)
            instance_variable_set("@#{association_name}", association_class.find(id))
          end
        else
          instance_variable_set("@#{association_name}", nil)
        end
      end

      # foo=
      define_method("#{association_name}=") do |arg|
        association_class = association_class_name.constantize

        if instance_variable_defined?("@#{association_name}_id")
          remove_instance_variable("@#{association_name}_id")
        end
        instance_variable_set("@#{association_name}", association_class.cast(arg))
      end
    end
Association macros

 Defines an association that is a reference to another Attribution class.

 @param [Symbol] association_name The name of the association
 @param [Hash] metadata Extra information about the association.
 @option metadata [String] :class_name Class of the association,
   defaults to a class name based on the association name