I have a Users model with has_many :comments
Each comment records the current_user to the commenter column.
How can I call #commenter.username in my view and show the commenter's username?
Currently in comments_controller using: #commenter = User.find("2") will pull the correct information. I would like to use something along the lines of: #commenter = User.find_by_id(:commenter)
From the comments, it sounds like you have this Comment model:
class Comment < ActiveRecord::Base
belongs_to :user
end
The comment model represents comments on a user's page, where the user model is defined as:
class User < ActiveRecord::Base
has_many :comments
end
There is also a commenter column on the comments table to store the user who posted the comment (on the other user's page).
First, I would recommend using commenter_id for this column rather than commenter, since this is the convention for storing ids of any kind.
Assuming that you have a commenter_id column on the comments table, you would then define a second relationship as follows:
class Comment < ActiveRecord::Base
belongs_to :user
belongs_to :commenter, class_name: "User", foreign_key: :commenter_id
end
The commenter relationship defines the user who wrote the comment, rather than the user whose page the comment is on.
For the other side of this relationship, update your User model:
class User < ActiveRecord::Base
has_many :comments
has_many :page_comments, class_name: "Comment", foreign_key: :commenter_id
end
Here, page_comments defines the comments this user has posted on other users' pages.
Then if you have a #comment, you can get the commenter's name with simply:
#comment.commenter.name
As long as you setup your column names and models correctly, dealing with getting information like this should be very simple.
Related
Hi I have a comment object, and I use polymorphic association, so it can belongs to many other objects. But I also want them to belong to users.
Now I can, call comment.comment_owner and I get the object that was commented by this comment.
As for the user I have a user_id field in the comment object, I pass the user id through the form. But when I try to get owner user by comment.user I get an error. Right now I`m getting user by User.find(comment.user_id). But this looks bad.
Is there a way to pass the user id. So I can get User owning a comment by comment.user
My associations:
class Comment < ActiveRecord::Base
belongs_to :comment_owner, polymorphic: true
end
class User < ActiveRecord::Base
has_many :comments, as: :comment_owner
end
class Posts < ActiveRecord::Base
has_many :comments, as: :comment_owner
end
Why not just
class Comment < ApplicationRecord
belongs_to :user
end
First of all, in my opinion comment_owner is not a good name for what you're designing here. Comment owner would suggest an ownership relation (rather a person or someone). I'd rather call it commentable as these object are being commented on.
If this relation is meant to be a polymorphic then you should have commentable_type and commentable_id (or comment_owner_type and comment_owner_id if you really prefer the original) as polymorphic => true expects to have those two fields (named as: relation_name_type and relation_name_id).
If you then have a Comment object you get the user commented by calling comment.commentable (or comment.comment_owner in case you decide to keep your naming).
[EDIT]
As you said, you want to have two parents. If I get this right you just want to have two relations - this means that if you just modify your code to:
class Comment < ActiveRecord::Base
belongs_to :commentable, polymorphic: true
belongs_to :author, class_name: 'User'
end
class User < ActiveRecord::Base
has_many :comments, as: :commentable
has_many :notes, class_name: 'Comment'
end
class Post < ActiveRecord::Base
has_many :comments, as: :commentable
end
You will have your polymorphic relation as well as the ownership.
I have two models Board and Pictures and I want a user to be able to comment on either the Board as a whole or the individual Pictures.
My polymorphic Comment model:
class Comment < ActiveRecord::Base
belongs_to :commentable, polymorphic: true
end
and then I have a simple has_many in each of the other models:
class Board < ActiveRecord::Base
has_many :comments, as: :commentable, dependent: :destroy
has_many :pictures
class Pictures < ActiveRecord::Base
has_many :comments, as: :commentable, dependent: :destroy
belongs_to :board
What I really want to be able to do is add a new scope called something like all_comments which combines the comments from the Board model with the related comments from the Pictures model. I can do this with a method, but I end up with an array and not a scoped relation.
My method:
def all_comments
comments = self.comments
return comments + self.pictures.map {|x| x.comments}.flatten
end
How can I return a scoped relationship that can chain the results?
first of all Pictures should be singular.
secondly, you can just call a finder on Comment to get all the comments you want
Comment.where("type = 'board' AND id IN(?) OR type = 'picture' AND id IN(?)", self.id, self.pictures.map(&:id))
or something like that.
phoet's answer intrigued me (I +1'd), so here's my refactor / expansion on what he suggested:
You'd look in the Comment model to pull out the relevant comments. To do this, you need to firstly know the board & the pictures associated with it. Phoet uses the self.pictures object for this:
#app/models/comment.rb
Class Board < ActiveRecord::Base
def all_comments
ids = self.id + self.pictures.map(&:id)
Comment.find(ids)
end
end
This will find the ids in the comment model, returning the data as a collection. If you wanted a true representation of the comments (hierarchical), you'd have to use some sort of ancestry / inheritance structure I think
I am trying to set up my models and controllers for a user event setup. It's a many-to-many setup for users to sign up for events. I already have the join table ('users_events') created.
So far I have:
Models:
class User < ActiveRecord::Base
has_and_belongs_to_many :events, join_table: 'users_events'
end
class Event < ActiveRecord::Base
has_and_belongs_to_many :users, join_table: 'users_events'
end
I want to be able to be able to query for all events a user is signed up for. Where should this query go? In users_controller or events_controller? What would the search/find code look like?
First of all users_events goes against rails convention. Rails infers table names by alphabetical order so the table should be named: events_users
Then you can do things like:
current_user.events
Or
event = Event.create!(name: "foo")
current_user.events << event
And the other way around..this way you also don't need to mention the join table in your model.
I was able to figure it out. As I elaborated in my reply to Nikolai, I also have a one-to-many relationship in that an event belongs_to (was created by) a user, so user.events was giving me the events the user had created, not what they were attending. Here is how I solved it.
class User < ActiveRecord::Base
has_many :events
has_and_belongs_to_many :attending_events, class_name: 'Event'
end
class Event < ActiveRecord::Base
belongs_to :user
has_and_belongs_to_many :attendees, class_name: 'User'
end
I have created a user using device authentication. I also have created article view, controller and model where model has fields such as title, body and article_id. Now I want to implement comments (with the condition that only logged in user can comment on an article). I have created an is_admin as a special user that has power create new articles through application.
The User table has all fields that are default generated by device. The Article table has fields like article_id, title, and body. There is still no association between user and article table. The Comment table will have (according to my understanding) comment_id, and comment_body.
Expected Associations:
class Comment < ActiveRecord::Base
belongs_to :article
belongs_to :user
I want to make sure that only logged in users can comment on articles, and that is_admin user can create new articles.
How can I create association between user, article and comment tables? Do I need to create association for user and comment table?
It is recommended to go through the rails guide and small blog to understand association as #dpassage suggested in comment. Looks you already have work around, so let me consolidate.
As you described, you will have three model:
First: User
class User
has_many :articles # not dependent => :destroy, may you not want to destroy article on deletion of user
has_many :comments, :dependent => :destroy
end
Second: Article
class Article
has_many :comments, :dependent => :destroy
belongs_to :user
end
Third: Comment
class Comment
belongs_to :user
belongs_to :article
end
class Comment < ActiveRecord::Base
belongs_to :post
belongs_to :user
end
So with the above association can I fetch both user and post details from a given comment object?.
like
#comment.post.post_title and
#comment.user.user_name.
Also please note that I have used comment as a nested resource of post.
resources :posts do
resources :comments
end
Yes you can, and you don't need to specify the foreign key or class name to do so. Saying belongs_to :user means rails will look for a user_id integer field in the comments table, and expect an ActiveRecord class named User to exist.
Add as many as you like, they don't interfere with each other.