基本上我在页面base
视图上有一个表格输出。标头(milestones
)通过传递Milestones
类并使用.each do
进行迭代来动态集成。然后,最初通过执行相同操作生成表行,将client
,trade
和units
拉入前三列。其余列应为日期(类entry
属性due
),这些日期是使用循环可访问的client
和trade
属性查找排序计算的,并且在为标题动态生成数组时创建的数组可访问的milestone
ID。这一切都正常工作,表生成正常..但日期输出为#<Entry:0x000000056faa90>
,依此类推。
现在我遇到过这个问题,基本上修复是添加一个类定义并告诉它返回我认为是该实例的属性。例如:
class Client < ActiveRecord::Base
validates :id, presence:true
validates :client, presence:true
def name
return self.client
end
end
这很有效,但仅限于我如何访问客户端。不幸的是,我以不同方式访问entry.due
。这是我的相关代码。
class BaseController < ApplicationController
def index
@trades = Trade.all
@milestones = Milestone.all
#@entries = Entry.all #Didn't seem relevant to how I am trying to access the information.
end
end
class Entry < ActiveRecord::Base
belongs_to :client
belongs_to :trade
belongs_to :milestone
validates :client, presence:true
validates :trade, presence:true
validates :milestone, presence:true
validates :due, presence:true
# Some of my trial and error; all to no avail.
def due
return self.due
end
def self.due
return self.due
end
def pickDue(c,t,m)
ret = self.select("date_format(due, '%m/%d/%Y')").where("client_id=? AND trade_id=? AND milestone_id=?", c, t, m).first
return ret
end
end
<table>
<thead>
<tr class="sort">
<th>Client</th>
<th>Trade</th>
<th>Units</th>
<%
ms = []
@milestones.each do |milestone|
ms.push(milestone)
%>
<th><%= milestone.name %></th>
<% end %>
</tr>
</thead>
<tbody>
<% @trades.order("entered").last(10).each do |trade| %>
<tr>
<td><%= trade.client.name %></td>
<td><%= trade.name %></td>
<td><%= trade.units %></td>
<% ms.each do |msr| %>
<td>
<%= Entry.select("date_format(due, '%m/%d/%Y')").where("client_id=? AND trade_id=? AND milestone_id=?", trade.client, trade, msr).first %>
<%#= Entry.pickDue(trade.client, trade, msr) %>
</td>
<% end %>
</tr>
<% end %>
</tbody>
</table>
通过这种方法,我可以无错误地加载页面,但我没有显示日期,而是显示#<Entry:0x000000056faa90>
之类的对象。
如果我将.due
添加到选择器的末尾:
<%= Entry.select("date_format(due, '%m/%d/%Y')").where("client_id=? AND trade_id=? AND milestone_id=?", trade.client, trade, msr).first.due %>
# undefined method `due' for nil:NilClass
如果我在其他任何地方添加.due
:
<%= Entry.due.select("date_format(due, '%m/%d/%Y')").where("client_id=? AND trade_id=? AND milestone_id=?", trade.client, trade, msr).first %>
<%= Entry.select("date_format(due, '%m/%d/%Y')").due.where("client_id=? AND trade_id=? AND milestone_id=?", trade.client, trade, msr).first %>
<%= Entry.select("date_format(due, '%m/%d/%Y')").where("client_id=? AND trade_id=? AND milestone_id=?", trade.client, trade, msr).due.first %>
# stack level too deep
我已经尝试了几十种不同的方法,这些方法通过几天的搜索而没有运气。除了输出对象而不是对象属性的当前情况之外,我认为下一个最接近的是当我收到错误时说它无法找到due
对象的ActiveRecord
方法,但我不记得怎么得到这个错误。
我真的很感激任何意见。
答案 0 :(得分:1)
如果我理解正确,我会在你的模型中删除试用和错误代码,然后在你看来你可以这样称呼:
Entry.where(client: trade.client, milestone: msr, trade: trade).pluck(:due)
这会在您的视图中进入里程碑循环,如下所示:
<% ms.each do |msr| %>
<td>
<%= Entry.where(client: trade.client, milestone: msr, trade: trade).pluck(:due).first %>
</td>
<% end %>
Pluck从您指定的列返回一组值(请参阅iTunes Link Maker,因此请注意.first
方法是Array#first
方法,而不是ActiveQuery#first
方法。您甚至可以创建一个同时传递所有里程碑的查询,而不是为每个里程碑运行查询,从而防止出现N + 1查询情况。
那将是:
<% Entry.where(client: trade.client, trade: trade, milestone: ms).pluck(:due).each do |entry_due_date| %>
<td>
<%= entry_due_date %>
</td>
<% end %>
最后,虽然我在视图中为您提供了SQL查询的代码,但在Rails中通常认为在您的视图中编写SQL查询是不好的做法,您应该将其作为Entry模型中的方法。