0

タイムシート インデックスに user.name を表示するアプリに問題があります (現在のユーザーのタイムシートだけでなく、すべてのタイムシートを表示します)

ユーザーモデル:

# Table name: timesheets
#
#  id         :integer         not null, primary key
#  user_id    :integer
#  starting   :datetime
#  ending     :datetime
#  approved   :boolean
#  created_at :datetime        not null
#  updated_at :datetime        not null
#

class User < ActiveRecord::Base
  attr_accessible :name, :email, :password, :password_confirmation
  has_secure_password
  has_many :timesheets
  ....
end

タイムシート モデル (標準の user_id は外部キー)

# Table name: timesheets
#
#  id         :integer         not null, primary key
#  user_id    :integer
#  starting   :datetime 
#  ending     :datetime
#  approved   :boolean
#  created_at :datetime        not null
#  updated_at :datetime        not null
#

class Timesheet < ActiveRecord::Base
  attr_accessible :starting, :ending
  belongs_to :user

  validates :user_id, presence: true
  validates :starting, presence: true
  validates :ending, presence: true
  validate :end_after_start
...
end

私のタイムシートコントローラーからのインデックス定義:

def index
  @timesheets = Timesheet.paginate(page: params[:page], per_page: 10)
end

最後に、user_id が表示されている index.html.erb ファイルですが、代わりにユーザー名が必要です。これは管理者がタイムシートを承認するためのものであるため、サインインしたユーザーではなく、すべてのタイムシートを表示して必要なものを承認したい管理者であることを忘れないでください。

<ul class="timesheets">
<% @timesheets.each do |timesheet| %>
    <NOBR>
    <li>
          <%= timesheet.user_id %>
          <%= timesheet.starting.strftime("[ %^a %^b %e,  %Y - %l:%M %p ] - ") %><%= timesheet.ending.strftime("[ %^a %^b %e,  %Y - %l:%M %p ]") %> <%= (timesheet.ending - timesheet.starting)/3600 %> Hours
          <% if current_user.admin? %>
                |
              <% if timesheet.approved? %>
                 <%= link_to "Un-Approve", { action: :unapprove, id: timesheet.id }, method: :put %>
              <% else %>
                 <%= link_to "Approve", { action: :approve, id: timesheet.id }, method: :put %>
              <% end %> 
         <% end %>
        </li>
    </NOBR>
<% end %>
</ul>

<%= will_paginate %>

これは私の最初の質問なので、すべての正しいプロトコルに従っていることを願っています。

4

2 に答える 2

2

RAILS ANTIPATTERNS - Best Practice Ruby on Rails Refactoring」に従って

Ruby on Rails を使用すると、オブジェクトの関係間を簡単にナビゲートできるため、関連するオブジェクト内および関連するオブジェクト全体を簡単に深く掘り下げることができます。Rails の Demeter の法則に従って、オブジェクトの関係をナビゲートする際に「ドットを 1 つだけ使用する」ようにします。たとえば、@category.product.nameはデメテルの法則に違反しますが、@ category.product_nameは違反しません。

したがって、タイムシートのユーザー名を取得する最良の方法は、次を使用する必要があります

timesheet.user_name

それ以外の

timesheet.user.name

このためには、以下のようにタイムシート モデルに必要な属性を持つデリゲート メソッドを追加するだけです。

delegate :name, :email, to: :user, :prefix => true

だからあなたのモデルは

class Timesheet < ActiveRecord::Base
  attr_accessible :starting, :ending
  belongs_to :user

  validates :user_id, presence: true
  validates :starting, presence: true
  validates :ending, presence: true
  validate :end_after_start

  delegate :name, :email, to: :user, :prefix => true

  ...

end

次に、ビュー ファイルでユーザー名を取得します。

timesheet.user_name

このように、以下のようにユーザーのメールを取得することもできます

timesheet.user_email
于 2013-08-13T06:31:18.277 に答える
1

ユーザーモデルとの関連付けがある場合は、呼び出してユーザーモデルを取得できます

timesheet.user

この問題のこの場合

<ul class="timesheets">
<% @timesheets.each do |timesheet| %>
    <NOBR>
    <li>
          <%= timesheet.user.name %>
          <%= timesheet.starting.strftime("[ %^a %^b %e,  %Y - %l:%M %p ] - ") %><%= timesheet.ending.strftime("[ %^a %^b %e,  %Y - %l:%M %p ]") %> <%= (timesheet.ending - timesheet.starting)/3600 %> Hours
          <% if current_user.admin? %>
                |
              <% if timesheet.approved? %>
                 <%= link_to "Un-Approve", { action: :unapprove, id: timesheet.id }, method: :put %>
              <% else %>
                 <%= link_to "Approve", { action: :approve, id: timesheet.id }, method: :put %>
              <% end %> 
         <% end %>
        </li>
    </NOBR>
<% end %>
</ul>

<%= will_paginate %>
于 2013-08-13T03:57:06.373 に答える