2016-05-11 43 views
1

我有用户模型,有很多细节。如何link_to主对象在视图中看起来更干净?

在详细列表(索引)页面(./details)中有一个link_to备份主表或拥有详细信息的用户(./user/1)。

基本上,我想知道是否有办法使link_to方法的语法,使用ruby或rails约定来查看任何清理器,但我不知道。

<% @details.each do |detail| %> 
    <tr> 
    <td><%= detail.name %></td> 
    <td><%= link_to User.find_by_id(detail.foreign_key_id).name, \ 
      User.find_by_id(detail.foreign_key_id) %></td> 
    ... 

这工作得很好,但我似乎记得在某个时候看到一个更清晰的语法。

[编辑] 也在这种情况下,我有两种方式,用户可以关联到细节。

我在想的数据模型与项目类似,所以我将以这种方式提出问题。因此,用户可以是项目的所有者,和/或项目的赞助商

所以,User类将有以下....

class User < ActiveRecord::Base 
    has_many :owned_projects, class_name: "Project", foreign_key: :owner_id 
    has_many :sponsored_projects, class_name: "Project", foreign_key: :sponsor_id 
end 

那么该项目类将有此在它的定义

class Project < ActiveRecord::Base 
    belongs_to :owner, :foreign_key => :owner_id, :class_name => "User" 
    belongs_to :sponsor, :foreign_key => :sponsor_id, :class_name => "User" 
end 

工作表中同时具有owner_id字段和sponsor_id字段,所以用户类可以链接两次到项目表。

鉴于所有这一切,回到手头上的问题,我不知道如何使用更清晰的语法由@Michael Gaskill

描述如果是像她那样,它会是这样? %= link_to @project.sponsor.name, project.sponsor_id %></td>

Rails 魔法似乎没有弄清楚,或者我已经配置错了。

我已经测试过以下,这将工作,正如我前面提到的,但我试图确保没有更简洁的方法。

(目标是看到有关的详细信息页面,或项目在这个例子中,看看用户关联到它的两个类别,并有他们的名字可以点击链接到他们的显示 PAGE图谱)

<p> 
    <strong>Name:</strong> 
    <%= @project.name %> 
</p> 

<p> 
    <strong>Owner:</strong> 
    <%= link_to User.find_by_id(@project.owner_id).name, User.find_by_id(@project.owner_id) %> 
</p> 

<p> 
    <strong>Sponsor:</strong> 
    <%= link_to User.find_by_id(@project.sponsor_id).name, User.find_by_id(@project.sponsor_id) %> 
</p> 
+0

您是否得到了适合您的答案? –

回答

2

如果你的人际关系的设置是否正确,你应该能够做这样的事情:

%= link_to detail.user.name, detail.user %></td> 

如果您可以提供帮助,您希望避免在视图中执行任何ActiveRecord查询。如果您必须在视图中执行查询,请确保您没有复制它们。视图中的查询往往会导致N + 1问题,并且复制它们可能导致该问题变为2 *(N + 1),或更糟糕。

根据您的问题显示的新的关系,你应该能够代替你的视图代码使用此:

<p> 
    <strong>Name:</strong> 
    <%= @project.name %> 
</p> 

<p> 
    <strong>Owner:</strong> 
    <%= link_to @project.owner.name, @project.owner) %> 
</p> 

<p> 
    <strong>Sponsor:</strong> 
    <%= link_to @project.sponsor.name, @project.sponsor) %> 
</p> 

简单地说,Rails的魔法知道如何遍历关系检索名称来自每个赞助商和所有者模型对象。同样,link_to知道如何从发起人和所有者中自动检索路径信息(作为link_to的第二个参数给出)来为每个对象创建正确的链接。请注意,这适用于使用模型对象(例如“所有者”)而不是object_id(例如“owner_id”)。

link_to API documentation给出了关于如何将link_to与您的模型数据一起使用的更深入的指导。示例#2演示了此答案使用的确切技术;然而,我们选择直接从ActiveRecord模型(作为所有者或赞助商名称)提供链接文本,而不是像在示例中那样对其进行硬编码。

通过使用路由助手来定义要使用的路径,您还可以更明确地指出要链接到哪条路径。让我们展示了如何链接到编辑页面的项目业主和赞助商了类似的看法页:

<p> 
    <strong>Name:</strong> 
    <%= @project.name %> 
</p> 

<p> 
    <strong>Owner:</strong> 
    <%= link_to @project.owner.name, edit_owner_path(@project.owner) %> 
</p> 

<p> 
    <strong>Sponsor:</strong> 
    <%= link_to @project.sponsor.name, edit_owner_path(@project.sponsor) %> 
</p> 

你可以使用任何路由助手Rails所创建您导航到任何的你模型的行为。要找出哪条路线助手可为您的项目,你可以在命令行运行rake routes,并看到这样的结果:

 Prefix Verb URI Pattern     Controller#Action 
    projects GET /projects(.:format)   projects#index 
      POST /projects(.:format)   projects#create 
new_project GET /projects/new(.:format)  projects#new 
edit_project GET /projects/:id/edit(.:format) projects#edit 
    project GET /projects/:id(.:format)  projects#show 
      PATCH /projects/:id(.:format)  projects#update 
      PUT /projects/:id(.:format)  projects#update 
      DELETE /projects/:id(.:format)  projects#destroy 
     users GET /users(.:format)    users#index 
      POST /users(.:format)    users#create 
    new_user GET /users/new(.:format)   users#new 
    edit_user GET /users/:id/edit(.:format) users#edit 
     user GET /users/:id(.:format)   users#show 
      PATCH /users/:id(.:format)   users#update 
      PUT /users/:id(.:format)   users#update 
      DELETE /users/:id(.:format)   users#destroy 

这是一套标准的在你的config/routes.rb这些定义来定义路线:

resources :project 
resources :user 

在输出rake routes,你看到在左边的“前缀”列中显示的路线佣工。这些标识符将用于向显式页面链接提供link_to。这些被称为“前缀”,因为它们分别用于“路径”或“网址”以生成相对路径或绝对网址。考虑这些用途:

user_path(@project.owner)  # ==> "/user/9" 
user_url(@project.sponsor)  # ==> "http://example.com/user/23" 
new_user_path     # ==> "/user/new" 
new_user_url     # ==> "http://example.com/user/new" 

请注意,有些路由助手必须指定参数,有些则不需要。您可以从rake routes输出中读取此参数,因为参数是按替换参数(例如:id)的出现顺序提供的,不包括可选替换参数(例如(。:格式))。该标准设定为一个资源路线给你,你可以使用这些路线助手:

users_path      # ==> "/user" 
new_user_path     # ==> "/user/new" 
user_path(@user)    # ==> "/user/139" 
edit_user_path(@user)   # ==> "/user/139/edit" 

其他默认路由通常不直接在项目中使用,这样你就不会直接引用他们。

所以,你有一个模型对象的任何时候,你可以创建任何你想要使用的链路,或者使用隐式路径的方法:

<%= link_to @user.name, @user %> 

或路径助手的方法:

<%= link_to @user.name, user_path(@user) %> 

这两个应该产生用户#69, “斯科特Tenorman” 相同链接:

<a href="/user/69">Scott Tenorman</a> 

这就是魔法。这并不是什么神奇的东西,而是一系列聪明,精心制作的约定,它们协同工作,轻松实现简单的事情。一旦你知道他们是如何工作的。快乐连结!

+0

对不起,迟到回复你,谢谢你的回答。 但是,你的意思是User类应该用'has_many ...'而不是'belongs_to'来定义? Detail属于我的用户。 另外,我确实尝试使用这种方法,但它不适合我。我想我并没有分享我想要做的事情的复杂性,这可能会使这个简化的代码工作。用户类可以有两种不同的细节关系。我会尽力改进我的问题来解释这一点。 –

+0

好的。一定是睡眠不足导致的。我已经更新了我的回答,以更好地描述机制如何工作,并揭示了模型,Rails路线,路线助手以及'link_to'如何将它们结合在一起的一些魔术。 –

相关问题