我在我的一个api视图上有性能问题,所以我运行了Bullet gem并发现了该视图的一些主要N+1问题。
api正在被使用,所以格式必须保持一致。
子弹N+1输出:
localhost:3000/api/v1/games/1/game_feed N+1查询检测到
CompletedQuest => [:comments]添加到您的finder::include =>[:comments] N+1查询方法调用栈
/app/views/api/v1/游戏/game_feed.json。jbuilder:3:inblock in _b3b681b668d1c2a5691a5b3f7c15bb8e' /app/views/api/v1/games/game_feed.json.jbuilder:1:in
_b3b681b668d1c2a5691a5b3f7c15bb8e'
但我不知道如何完成修复。以下是相关部分。
视图:
json.game_feed(@game_photos) do |f|
json.extract! f, :id, :user_id, :username, :image_url_original, :comments_count, :likes_count
json.comments f.comments do |comment|
json.(comment, :username, :comment)
end
json.likes f.likes do |like|
json.(like, :id, :user_id, :username)
end
end
控制器:
@game_photos = CompletedQuest.game_photos(@game.id)
模型:
def self.game_photos(game_id)
where("completed_quests.game_id = ?", game_id).order("completed_quests.id DESC").just_photos
end
scope :just_photos, -> { where.not( image_file_name: nil ) }
模型关系:
# CompletedQuests:
belongs_to :user
has_many :comments, dependent: :destroy
has_many :likes, dependent: :destroy
# Comments:
belongs_to :completed_quest, counter_cache: true
belongs_to :user
基本上对于提要中的每张照片,它会抓取每条评论&喜欢永远记录-显然这是不好的,我知道为什么,但我不知道如何解决它与我目前的结构。
任何帮助将是感激的-但有一件事是JSON的结构必须保持相同。
您可以在查询中包括相关的comments
,如下所示:
# app/models/completed_quest.rb
def self.game_photos(game_id)
includes(:comments).where("completed_quests.game_id = ?", game_id).order("completed_quests.id DESC").just_photos
end
这将包括结果中所有相关的注释,因此当您在视图中执行f.comments
时,将不会有每个f
实例的注释的数据库查询。