两种模型的一种方法。如何将模型名称作为变量传递给控制器?
One method for two models. How to pass name of model as variable to controller?
我在两个不同的控制器(Posts & Boards)中有两种方法。他们几乎是一样的。区别仅在于模型实例关联名称。要 DRY 这个,我想在模块中编写方法,但是如何在 Post 和 Board 之间共享它?
def init_post_comments
@user = current_user
a = @user.posts.pluck(:id) # not very nice...
b=params[:post_ids] ||= []
b = b.map(&:to_i)
follow = b - a
unfollow = a - b
follow.each do |id| # checkbox just checked
@post = Post.find_by_id(id)
if @post.users.empty?
@post.update_attribute(:new_follow, true)
end
@user.posts << @post
end
unfollow.each do |id| # if checkbox was unchecked
@post = Post.find_by_id(id)
remove_post_from_user(@post)# here we destroy association
end
if follow.size > 0
get_post_comments_data
end
redirect_to :back
end
UPDATE 好的,如果我将这些方法移到模型的关注点,我应该如何在此处处理关联?这里 @user.posts.pluck(:id)
和这里 @user.boards.pluck(:id)
我可以用什么来替换帖子和看板,这样它就可以与它们一起工作?
所以,我做到了!我不知道这样做是否正确,但我 DRY 这段代码。
两个控制器:
posts_controller.rb
def init_comments
if Post.comments_manipulator(current_user, params[:post_ids] ||= []) > 0
@posts = Post.new_post_to_follow
code = []
@posts.each do |post|
group = post.group
code = code_constructor('API.call')
end
Post.comments_init(get_request(code), @posts)
end
redirect_to :back
end
boards_controller.rb
def init_comments
if Board.comments_manipulator(current_user, params[:board_ids] ||= []) > 0
@boards = Board.new_board_to_follow
code = []
@boards.each do |board|# подготовка запроса
group = board.group
code = code_constructor('API.call')
end
Board.comments_init(get_request(code), @boards)
end
redirect_to :back
end
如您所见,它们完全相同。
在模型 board.rb
和 post.rb
- include CommentsInitializer
中
并且在models\concerns
module CommentsInitializer
extend ActiveSupport::Concern
module ClassMethods
def comments_manipulator(user, ids)
relationship = self.name.downcase + 's'
a = user.send(relationship).pluck(:id)
b = ids.map(&:to_i)
follow = b - a
unfollow = a - b
follow.each do |id| # start to follow newly checked obj
@obj = self.find_by_id(id)
if @obj.users.empty?
@obj.update_attribute(:new_follow, true)
end
user.send(relationship) << @obj
end
unfollow.each do |id| # remove from following
@obj = self.find_by_id(id)
remove_assoc_from_user(@obj, user)#destroy relation with current user
end
follow.size
end
def comments_init(comments, objs)
i = 0
objs.each do |obj| # updating comments data
if comments[i]['count'] == 0
obj.update(new_follow: false)
else
obj.update(new_follow: false, last_comment_id: comments[i]['items'][0]['id'])
end
i += 1
end
end
def remove_assoc_from_user(obj, user)
user = user.id
if user
obj.users.delete(user)
end
end
end
我的代码有效。如果您知道如何让它变得更好,请回答!
我在两个不同的控制器(Posts & Boards)中有两种方法。他们几乎是一样的。区别仅在于模型实例关联名称。要 DRY 这个,我想在模块中编写方法,但是如何在 Post 和 Board 之间共享它?
def init_post_comments
@user = current_user
a = @user.posts.pluck(:id) # not very nice...
b=params[:post_ids] ||= []
b = b.map(&:to_i)
follow = b - a
unfollow = a - b
follow.each do |id| # checkbox just checked
@post = Post.find_by_id(id)
if @post.users.empty?
@post.update_attribute(:new_follow, true)
end
@user.posts << @post
end
unfollow.each do |id| # if checkbox was unchecked
@post = Post.find_by_id(id)
remove_post_from_user(@post)# here we destroy association
end
if follow.size > 0
get_post_comments_data
end
redirect_to :back
end
UPDATE 好的,如果我将这些方法移到模型的关注点,我应该如何在此处处理关联?这里 @user.posts.pluck(:id)
和这里 @user.boards.pluck(:id)
我可以用什么来替换帖子和看板,这样它就可以与它们一起工作?
所以,我做到了!我不知道这样做是否正确,但我 DRY 这段代码。
两个控制器:
posts_controller.rb
def init_comments
if Post.comments_manipulator(current_user, params[:post_ids] ||= []) > 0
@posts = Post.new_post_to_follow
code = []
@posts.each do |post|
group = post.group
code = code_constructor('API.call')
end
Post.comments_init(get_request(code), @posts)
end
redirect_to :back
end
boards_controller.rb
def init_comments
if Board.comments_manipulator(current_user, params[:board_ids] ||= []) > 0
@boards = Board.new_board_to_follow
code = []
@boards.each do |board|# подготовка запроса
group = board.group
code = code_constructor('API.call')
end
Board.comments_init(get_request(code), @boards)
end
redirect_to :back
end
如您所见,它们完全相同。
在模型 board.rb
和 post.rb
- include CommentsInitializer
并且在models\concerns
module CommentsInitializer
extend ActiveSupport::Concern
module ClassMethods
def comments_manipulator(user, ids)
relationship = self.name.downcase + 's'
a = user.send(relationship).pluck(:id)
b = ids.map(&:to_i)
follow = b - a
unfollow = a - b
follow.each do |id| # start to follow newly checked obj
@obj = self.find_by_id(id)
if @obj.users.empty?
@obj.update_attribute(:new_follow, true)
end
user.send(relationship) << @obj
end
unfollow.each do |id| # remove from following
@obj = self.find_by_id(id)
remove_assoc_from_user(@obj, user)#destroy relation with current user
end
follow.size
end
def comments_init(comments, objs)
i = 0
objs.each do |obj| # updating comments data
if comments[i]['count'] == 0
obj.update(new_follow: false)
else
obj.update(new_follow: false, last_comment_id: comments[i]['items'][0]['id'])
end
i += 1
end
end
def remove_assoc_from_user(obj, user)
user = user.id
if user
obj.users.delete(user)
end
end
end
我的代码有效。如果您知道如何让它变得更好,请回答!