What is the best way to handle a 4-sided relationship between two models?

I have two models: Company and User

In this situation:

  • A company can follow another company.
  • The user can follow the company.
  • A user can follow another user.

What is the best way to define relationships and what would the join model look like?

Also, are there any guidelines for dealing with such situations?

Update

Sorry, this has not been mentioned before. I know different types of relationships. My question is ' which is the best fit ?

+3


source to share


3 answers


Thanks to polymorphic associations, we can put all relationships in one table that looks like this:

create_table :follows do |t|
        t.references :followable, :polymorphic => true
        t.references :followed_by, :polymorphic => true
end

      

Then the models:



class User < ActiveRecord::Base
    has_many :following_objects, :class_name => 'Follow', :as => :followed_by
    has_many :followed_objects, :class_name => 'Follow', :as => :followable
end

class Company < ActiveRecord::Base
    has_many :following_objects, :class_name => 'Follow', :as => :followed_by
    has_many :followed_objects, :class_name => 'Follow', :as => :followable
end

class Follow < ActiveRecord::Base
    belongs_to :followable, :polymorphic => true
    belongs_to :followed_by, :polymorphic => true
end

      

Sorry for the ugly names.

+2


source


As for your question, I suggest you go through a couple of Railscasts videos:

And it is described very well on the RubyonRails website.



I would say, look at them in your case:

Hope this helps you.

+3


source


The basic idea would be to use two associative bindings :

  • User -> Friendship <- User
  • Company → Partnership <- Company

models /user.rb

has_many :friendships
has_many :friends, :through => :friendships
has_many :inverse_friendships, :class_name => "Friendship", :foreign_key => "friend_id"
has_many :inverse_friends, :through => :inverse_friendships, :source => :user

      

models / friendship.rb

belongs_to :user
belongs_to :friend, :class_name => "User"

      

models /company.rb

has_many :partnerships
has_many :partners, :through => :partnerships
has_many :inverse_partnerships, :class_name => "Partnership", :foreign_key => "partner_id"
has_many :inverse_partners, :through => :inverse_partnerships, :source => :company

      

models / partner.rb

belongs_to :company
belongs_to :partner, :class_name => "Company"

      


And one many-to-many association :

  • User -> CompanyUser <- Company

models / user.rb

has_and_belongs_to_many :companies

      

models / company.rb

has_and_belongs_to_many :users

      

So, for this implementation, you will need 5 tables (users, friends, companies, partners and companies) if you are using an RDBMS.

You can get a good example in this screencast:

http://railscasts.com/episodes/163-self-referential-association

+1


source







All Articles