Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How is ruby on rails has_many (and similar) implemented?

I am analysing the rails source code, because I wold like to understand the inner workings of the has_many and similar constructs.

So far, I was able to find where the method is implemented (link to github): it is in the module ActiveRecord::Associations

def has_many(name, options = {}, &extension)
  Builder::HasMany.build(self, name, options, &extension)
end

This one eventualy ends (link to github) in the class ActiveRecord::Associations::Builder::CollectionAssociation as

def self.build(model, name, options, &extension)
  new(model, name, options, &extension).build
end

There is where my ruby skills end and I could not track it further and find where is "new" implemented and what it does.

Can someone point me to the right direction and maybe comment along, what is going on under the hood?

like image 415
Tadej Mali Avatar asked Feb 25 '12 22:02

Tadej Mali


People also ask

What is Has_and_belongs_to_many?

Rails offers two different ways to declare a many-to-many relationship between models. The first way is to use has_and_belongs_to_many, which allows you to make the association directly: The second way to declare a many-to-many relationship is to use has_many :through.

What is has_ many?

A has_many association is similar to has_one , but indicates a one-to-many connection with another model. You'll often find this association on the "other side" of a belongs_to association. This association indicates that each instance of the model has zero or more instances of another model.


1 Answers

Basically, new is defined like this:

class Class
  def new(*args, &block)
    obj = allocate

    obj.initialize(*args, &block)
    # *actually* obj.send(:initialize, *args, &block) since initialize is private

    obj
  end
end

allocate is defined like this:

class Class
  def allocate
    # magic stuff for creating an empty object which cannot be expressed in Ruby:

    new_obj = Deep::Within::VM.__somehow_magically_allocate_memory__!

    new_obj.__class__ = self

    new_obj
  end
end
like image 72
Jörg W Mittag Avatar answered Oct 19 '22 11:10

Jörg W Mittag