无法找到ID =(ActiveRecord :: RecordNotFound)的用户

时间:2013-03-28 22:45:46

标签: ruby-on-rails

使用我的rails应用程序,我可以成功创建一个对象(称为work;将它们视为博客帖子)作为current_user。用户has_many工作。我可以通过使用postgresql浏览器检查数据库来验证是否已成功创建对象。该表还包含创建工作的正确user_id,因此我知道我的创建函数在我的控制器中工作。

然而,问题是当我尝试查看工作时,我收到以下错误:

WorksController中的ActiveRecord :: RecordNotFound#show

找不到ID = 23的用户

app / controllers / works_controller.rb:43:在“show”

奇怪的是,我仍然可以查看几周前创作的作品。该错误仅出现在我最近创建的作品中。

这是Works控制器:

class WorksController < ApplicationController
   #before_filter :current_user,   only: [:edit, :update]

  def index
    @works = Work.all

respond_to do |format|
  format.html # index.html.erb
  format.xml  { render :xml => @works }
end
end
def create
    @work = current_user.works.create(params[:work])
    redirect_to current_user
  end

def edit
    @work = current_user.works.find(params[:id])
end

def new
  @work = current_user.works.new
end

def destroy
  @work = current_user.works.find(params[:id]).destroy
  flash[:success] = "Work deleted"
  redirect_to current_user
end

 def update
    @work = current_user.works.find(params[:id])
    if @work.update_attributes(params[:work])
      flash[:success] = "updated"
      redirect_to @work
    else
      render 'edit'
    end
  end


  def show
    @user = User.find(params[:id])
    @work = @user.works.find(params[:id])
    @activities = PublicActivity::Activity.order("created_at DESC").where(trackable_type: "Work", trackable_id: @work).all

    respond_to do |format|
      format.html # show.html.erb
      format.xml  { render :xml => @work }
    end
  end
end

我假设错误在Works控制器中。我需要在控制器中编辑什么才能修复“显示”错误?

编辑:如果我使用上面的当前代码,我只能查看其他人的作品(查看我自己的投掷错误)。但是,如果我将current_user添加到查询中(例如@ works = current_user.works),那么我只能看到自己的作品。查看其他人的作品会引发错误。我如何解决这个问题,以便我可以查看自己的作品和他人创作的作品?

编辑2:

@work = Work.find(params [:id])如果从控制器中移除@user并且在show.html视图文件中删除“@user”引用,则有效。但是,我需要控制器中的“@user”引用,因为我想显示创建工作的用户的名称。我该怎么做呢?

编辑3:

固定!再次感谢所有贡献答案的人!以下是我采取的措施:

  1. 我从控制器中删除了@user引用(“show”操作)。正如Fred在下面提到的那样,不需要@user引用,因为我使用了:id两次来引用两个独立的对象。

  2. 将“@work”变量编辑为@work = Work.find(params[:id])。这将根据id查找正确的工作项,无论用户是谁创建的。

  3. 当我需要在工作页面上显示用户数据时,只需在show.html.erb视图页面上使用<%= @work.user.name %>即可。 '@ user = User.find(params [:id])'不需要,因为我已经使用'belongs_to:user'在作品模型上定义了外键关系。

  4. 再次感谢所有帮助! -j

4 个答案:

答案 0 :(得分:4)

在你的节目动作中,一起摆脱@user,只需使用:

@work = Work.find(params[:id])

这将允许任何人查看任何工作。

您的其他行动也是如此。说:

@work = current_user.works.find(params[:id])

您正在搜索所有current_user的作品,以查找id == params[:id]

的作品

答案 1 :(得分:1)

我怀疑您在查找用户时使用的是work_id而不是user_id,因此它有时可以正常运行,但ID错误。

你是在工作的控制者。 params [:id]就是工作。

所以这个:

@user = User.find(params[:id])
@work = @user.works.find(params[:id])

应该是这样的:

@user = User.find(current_user)
@work = @user.works.find(params[:id])

如果你只想要所有的作品使用

@works = Work.all

因为你可以使用相同的params [:id]作为te id来查找用户和工作。如果它们是相同的ID,那只是巧合。

答案 2 :(得分:1)

我发现使用current_user.works.find_by(id:params [:id])可以在找不到任何内容时返回nil。

我认为这有点好,因为你现在可以在你的查找中使用current_user更安全一点,因为你不必依赖你的视图来显示它不应该显示的数据,因为它永远不会得到它。 / p>

答案 3 :(得分:0)

看起来您正在删除用户,并留下对works

的悬空引用

通过

查询作品

@work = @user.works.find(params[:id])

您正在寻找属于@user(冗余)

的@ user的所有作品

如果您改为使用@work = @user.works,则不会触及那些悬空作品,因为@ user.works将返回空响应。

这实际上不是最好的解决方案,您需要在删除用户时更好地处理依赖项的破坏。

编辑:对不起,我使用current_user我应该使用@user,上面的评论有同样的错误。