【问题标题】:Rails ActiveRecord Create or FindRails ActiveRecord 创建或查找
【发布时间】:2013-07-28 02:55:02
【问题描述】:

我正在开发 Rails 4 应用程序,在我的 api 发布方法中,我想根据用户尝试创建的内容来查找记录,如果它不存在,则创建它,如果它确实更新了它具有的参数。我写了一些代码来实际执行此操作,但执行起来需要一些时间。有没有其他方法可以用更少的代码或查询来做同样的事情。

@picture = current_picture.posts.where(post_id: params[:id]).first_or_initialize
@picture.update_attributes(active: true, badge: parameters[:badge], identifier: parameters[:identifier])
render json: @picture

【问题讨论】:

    标签: ruby-on-rails ruby activerecord ruby-on-rails-4


    【解决方案1】:

    你可以这样做,

    @picture = current_picture.posts.where(post_id: params[:id]).find_or_create.

    这将找到带有 params[:id] 的帖子,如果它没有找到该记录,那么它将在当前图片下使用该 id 创建记录帖子。

    【讨论】:

      【解决方案2】:

      Rails 4.0 release notes 表示find_by_ 尚未被弃用:

      find_by_... 和 find_by_... 的所有动态方法除了!是 已弃用。

      此外,根据Rails 4.0 documentationfind_or_create_by 方法仍然可用,但已被重写以符合以下语法:

      @picture = current_picture.posts.find_or_create_by(post_id: params[:id])
      

      更新:

      根据source code

      # rails/activerecord/lib/active_record/relation.rb
      def find_or_create_by(attributes, &block)
        find_by(attributes) || create(attributes, &block)
      end
      

      因此,在 Rails 4 中可以将多个属性作为参数传递给 find_or_create_by 是理所当然的。

      【讨论】:

      • 谢谢,但我认为该方法在 Rails 4 中已被贬低,我猜不是。所以我也在使用 'current_picture.posts.where(active: true, post_id: params[:id]).take!'其他地方,应该写不同的吗?
      • 我已经更新了我的答案。根据文档,您可以找到post_id 等于params[:id] 的用户的第一个帖子,或者使用设置为trueactive 属性创建新用户的帖子:current_picture.posts.create_with(active: true).find_or_create_by(post_id: params[:post_id])
      • 谢谢 如果帖子存在,它会将现有帖子设置为true吗?
      • 我更新了我的答案,引用了源代码,表明多个属性确实可以传递给 find_or_create_by。
      • 是的,但是如果找到记录,它会使用参数更新记录吗?
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2014-01-26
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多