In my Rails 4 application, I have the following models:
User has_many :administrations has_many :calendars, through: :administrations has_many :comments has_many :calendar_comments, through: :calendars, :source => :comments Calendar has_many :administrations has_many :users, through: :administrations has_many :posts has_many :comments, through: posts has_many :ads Administration belongs_to :user belongs_to :calendar Post belongs_to :calendar has_many :comments, as: :commentable Ad belongs_to :calendar has_many :comments, as: :commentable Comment belongs_to :commentable, polymorphic: true belongs_to :user
I need to access comments , which belong_to a ad from calendar ad belongs_to .
This is what I am trying to do in my Calendars#Index action:
@posts_comments = @user.calendar_comments.where(commentable_type: "Post").order("created_at DESC").limit(5) @ads_comments = @user.calendar_comments.where(commentable_type: "Ad").order("created_at DESC").limit(5)
My first assumption was to add has_many :comments, through: ads to the calendar model:
Calendar has_many :administrations has_many :users, through: :administrations has_many :posts has_many :comments, through: posts has_many : ads has_many :comments, through: ads
But this undoes the effect of has_many :comments, through: posts , and then I can no longer access the comments , which belong_to a post from the calendar post belongs_to .
Is there a way to make BOTH has_many :comments, through: posts and has_many :comments, through: ads work?
-----
UPDATE : according to this article and what is stack overflow question , the answer may be to use source: and source_type:
I donβt know how to use them.
-----
UPDATE 2 : will it make sense to use the following code?
class Calendar < ActiveRecord::Base has_many :administrations, dependent: :destroy has_many :users, through: :administrations has_many :posts, dependent: :destroy has_many :commented_posts, through: :comments, source: :commentable, source_type: 'Post' has_many :ads, dependent: :destroy has_many :commented_ads, through: :comments, source: :commentable, source_type: 'Ad'
-----
UPDATE 3 : when you try to execute the above code, the following error message appears:
Could not find the source association(s) :comments in model Calendar. Try 'has_many :calendar_comments, :through => :calendars, :source => <name>'. Is it one of administrations, users, posts, commented_posts, ads, commented_ads, invites, or pokes?
I tried the following:
class Calendar < ActiveRecord::Base has_many :administrations, dependent: :destroy has_many :users, through: :administrations has_many :posts, dependent: :destroy has_many :calendar_comments, :through => :calendars, :source => :post has_many :ads, dependent: :destroy has_many :calendar_comments, :through => :calendars, :source => :ad
-----
UPDATE 4 : A new failed attempt with the following code:
class Calendar < ActiveRecord::Base has_many :administrations, dependent: :destroy has_many :users, through: :administrations has_many :posts, dependent: :destroy has_many :calendar_comments, :through => :commentable, :source => :post has_many :ads, dependent: :destroy has_many :calendar_comments, :through => :commentable, :source => :ad
Still not working, same error message as above.
-----
UPDATE 5 : based on MrYoshiji's answer, I now have
class Calendar < ActiveRecord::Base has_many :administrations, dependent: :destroy has_many :users, through: :administrations has_many :posts, dependent: :destroy has_many :posts_comments, through: :posts, source_type: 'Post' has_many :ads, dependent: :destroy has_many :ads_comments, through: :ads, source_type: 'Ad'
Now has_many :calendar_comments, through: :calendars, :source => :comments in the User model no longer works.
I tried:
has_many :comments has_many :calendar_post_comments, through: :calendars, :source => :post_comments has_many :calendar_ad_comments, through: :calendars, :source => :ad_comments
Still not working.
-----
UPDATE 6 . I am still sticking to this problem since I cannot find a way to get the following code:
@posts_comments = @user.calendar_comments.where(commentable_type: "Post").order("created_at DESC").limit(5) @ads_comments = @user.calendar_comments.where(commentable_type: "Ad").order("created_at DESC").limit(5)
I tried a lot of different things, and the best I could come up with was:
class Calendar < ActiveRecord::Base has_many :administrations, dependent: :destroy has_many :users, through: :administrations has_many :posts, dependent: :destroy has_many :post_comments, through: :posts, source_type: 'Post' has_many :ads, dependent: :destroy has_many :ad_comments, through: :ads, source_type: 'Ad' end class User < ActiveRecord::Base has_many :administrations, dependent: :destroy has_many :calendars, through: :administrations has_many :comments has_many :calendar_post_comments, through: :calendars, :source => :post_comments has_many :calendar_ad_comments, through: :calendars, :source => :ad_comments end
Then I update my calendar controller as follows:
def index @user = current_user @calendars = @user.calendars.all @posts_comments = @user.calendar_post_comments .order("created_at DESC") .limit(5) @ads_comments = @user.calendar_ad.comments .order("created_at DESC") .limit(5) end
But this returns the following error:
NoMethodError at /calendars undefined method `chain' for nil:NilClass @posts_comments = @user.calendar_post_comments.order("created_at DESC").limit(5)
What is wrong here?