1

我查看了许多其他线程并花了过去几个小时查看它,但我仍然无法弄清楚。

我正在使用来自另一个视图页面的同一行代码

这是错误:

app/views/users/_user.html.erb其中第 4 行提出:

undefined method `microposts' for nil:NilClass

如果您熟悉的话,这是来自 Rubytutorial 演示应用程序。使用了此代码views\users\show.html.erb,我尝试查看它是否可以正常工作,views\users\ _user.html.erb但出现错误。

我重用的代码是:

<%= @user.microposts.count %>

这是调用部分的完整视图(_user.html.erb)

<li>
  <%= gravatar_for user, size: 52 %>
  <%= link_to user.name, user %>
<%- if @user %>
  <%= @user.microposts.count %>
<%- else %>
  THIS IS THE ERROR, THERE IS NO USER ON @user
<%- end %>
 <% if current_user.admin? && !current_user?(user) %>
    | <%= link_to "delete", user, method: :delete, confirm: "You sure?" %>
  <% end %>
</li>

这导致这是错误,\@user 上没有用户。这意味着根据 rorra 的评论,在部分情况下,\@user 不存在,那么我在哪里解决这个问题?

class UsersController < ApplicationController
  before_filter :signed_in_user,
                only: [:index, :edit, :update, :destroy, :following, :followers]
  before_filter :correct_user,   only: [:edit, :update]
  before_filter :admin_user,     only: :destroy


  def index

    @users = User.paginate(page: params[:page])
  end


  def show
    @user = User.find(params[:id])
    @microposts = @user.microposts.paginate(page: params[:page])
  end



  def new
    @user = User.new
  end

  def create
    @user = User.new(params[:user])
    if @user.save
      sign_in @user
      flash[:success] = "Welcome to Sample App!"
      redirect_to root_url
    else
      render 'new'
    end
  end

  def edit
  end

  def update
    if @user.update_attributes(params[:user])
      sign_in @user
      flash[:success] = "Profile updated"
      redirect_to @user
    else
      render 'edit'
    end
  end

  def destroy
    User.find(params[:id]).destroy
    flash[:success] = "User destroyed"
    redirect_to users_path
  end


  private

    def correct_user
      @user = User.find(params[:id])
      redirect_to root_path unless current_user?(@user)
    end

    def admin_user
      redirect_to root_path unless current_user.admin?
    end
end

这是views\users\index.html.erb

<% provide(:title, 'Users') %>
<h1>Users</h1>

<%= will_paginate %>

<ul class="users">
  <%= render @users %>

</ul>

<%= will_paginate %>

这是views\users\show.html.erb

<% provide(:title, @user.name) %>
<div class="row">
  <aside class="span4">
    <section>
      <h1>
        <%= gravatar_for @user %>
        <%= @user.name %>
      </h1>
    </section>
    <section>
      <%= render 'shared/stats' %>

    </section>
  <br>
  </aside>


  <div class="span10">
    <%= render 'follow_form' if signed_in? %>
    <% if @user.microposts.empty? %>
<h3>Microposts (<%= @user.microposts.count %>)</h3>
<% end %>
    <% if @user.microposts.any? %>
      <h3>Microposts (<%= @user.microposts.count %>)</h3>
      <ol class="microposts">
        <%= render @microposts %>
      </ol>

      <%= will_paginate @microposts %>
    <% end %>
  </div>
</div>
4

1 回答 1

0

使用以下代码更新您的部分 (\views\users\_user.html.erb):

<%- if @user %>
  <%= @user.microposts.count %>
<%- else %>
  THIS IS THE ERROR, THERE IS NO USER ON @user
<%- end %>

你会得到最后一句话:P

问题是部分的 @user 是一个 nil 对象,而不是一个 User 对象

如果您从show操作中调用部分,那么您不应该有一个 nil 对象,因为如果 @user 为 nil,它将在您的操作的第二行抛出异常(并且它不会到达部分)。

现在,让新开发人员感到困惑的是,在分部上,您通常传递一个对象,其名称是分部的名称,因此如果您的分部(如本例中)被命名为_user,并且您传递一个默认值对象到这个部分,那么您将能够通过使用变量user而不是实例变量@user来引用该对象

在您的视图中尝试此代码:

<%= user.microposts.count %>

为了完成这项工作,您通常会像这样发送对象

<%= render partial: '/views/users/user', object: @my_user %>

甚至

<%= render @user %> 

它将寻找视图 _user.html.erb

您通常使用这些部分来呈现集合,例如

<%= render partial: '/views/users/user', collection: @users %>

有关更多信息,请阅读Rails 指南中关于 partials


部分应如下所示:

    <li>
      <%= gravatar_for user, size: 52 %>
      <%= link_to user.name, user %>
      <%= user.microposts.count %>
      <% if current_user.admin? && !current_user?(user) %>
        | <%= link_to "delete", user, method: :delete, confirm: "You sure?" %>
      <% end %>
    </li>

从 index.html.erb 调用部分的方式

<%= render @users %>

完全没问题

您使用什么宝石进行分页?我认为问题在于paginate返回一个 ActiveRecord 关系,而不是每个用户的数组。

将您的控制器索引操作更新为:

@users = User.paginate(page: params[:page]).all
于 2013-03-04T08:07:08.903 回答