【问题标题】:SQL query in Rails controllerRails 控制器中的 SQL 查询
【发布时间】:2015-12-25 17:20:07
【问题描述】:

我想删除 Followers 表中的一行:

def unfollow
    follower = Follower.where("user_id = user_id AND followed_by = current_user_id",{user_id: params[:user_id], current_user_id: current_user.id})

    follower.destroy    
end

但收到此错误:

 Started DELETE "/followers/unfollow" for 127.0.0.1 at 2015-12-25 17:36:15 +0100
Processing by FollowersController#unfollow as */*

  Parameters: {"user_id"=>"2"}

  User Load (0.4ms)  SELECT  "users".* FROM "users" WHERE "users"."id" = $1  ORDER BY "users"."id" ASC LIMIT 1  [["id", 1]]
Completed 500 Internal Server Error in 6ms (ActiveRecord: 0.4ms)

ArgumentError (wrong number of arguments (0 for 1)):
  app/controllers/followers_controller.rb:23:in `unfollow'

此操作由 AJAX 调用:

    unfollowUser(userId){
    console.log ("API.unfollowUser");   
    $.ajax({
      url: '/followers/unfollow',
      method: 'DELETE',
      data: { user_id: userId }
    }).done(unfollowUser => ServerActions.removedOneFollower(unfollowUser))
      .fail(error => console.log(error));
}

它应该取消关注我们之前关注的用户。

我检查了语法,似乎没问题。有人能解释一下如何解决这个错误吗?

【问题讨论】:

    标签: ruby-on-rails reactjs-flux


    【解决方案1】:

    使用 find_by

    Follower.find_by(user_id: params[:user_id]...)
    

    'where' 用于当您期望获得多行时

    【讨论】:

      【解决方案2】:

      您的查询返回ActiveRecord::Relation,这是您的销毁不起作用的原因。你可以销毁一个元素。

      试试这个:

      def unfollow
        follower = Follower.
          where(user_id: params[:user_id]).
          where(followed_by: current_user.id).
          take
      
        follower.destroy    
      end
      

      或者这个:

      def unfollow
        follower = Follower.find_by(
          user_id: params[:user_id],
          followed_by: current_user.id
        )
        follower.destroy
      end
      

      【讨论】:

      • 或将_all添加到销毁follower.destroy_allapi
      【解决方案3】:
      def unfollow
        follower = Follower.where("user_id = :user_id AND followed_by = :current_user_id", 
          user_id: params[:user_id], current_user_id: current_user.id).first
      
        follower.destroy    
      end
      

      应该这样做。

      Active Record 实际上足够聪明,知道应该在进行查询之前应用 first(而不是带回许多记录然后再取第一条记录,这将非常愚蠢且效率低下。)

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2011-02-18
        相关资源
        最近更新 更多