Rails嵌套资源参数

时间:2015-04-10 22:50:32

标签: ruby-on-rails ruby

我对Ruby on Rails很新,在项目中使用4.1版。

我对嵌套资源在rails中的工作方式感到有点困惑。也许有人可以帮忙。

我正在建立一个任务系统作为一个学习项目。

我的网站拥有属于他们的任务。查看任务时,我可以这样做:

resources :websites do 
  resources :tasks
end

一个链接可以让我完成我的任务,只需要http://myapp.com/websites/2/tasks/3

这样的网址
<%= link_to 'Show', website_task_path(website,task) %>

我注意到的是,我可以将网址中的网站ID更改为任何内容 - http://myapp.com/websites/what-the-hell-is-going-on-here/tasks/1 - 与其他链接的工作方式相同。或者我也可以在网址中使用不同的网站ID访问该任务。

所以问题是,Rails是否应该默认对这条信息做任何事情?如果我想确保您使用参数中的正确父资源访问任务,是否由我决定?

2 个答案:

答案 0 :(得分:5)

您的任务ID在任务表中是唯一的。只要您想显示,编辑或删除任务,此信息就足够了。您可以通过您的关联轻松获得父母。但是嵌套资源允许您创建新任务。在这种情况下,没有ID集。您需要知道正确的父级才能在您的任务中设置它。

摘自可能的TasksController:

class TasksController < ApplicationController

  before_action :set_website, only: [:create]

  def create
    @website.tasks.create!(task_params)
  end

  private

  def set_website
    @website = Website.find(params[:website_id])
  end

  def task_params
    params.require(:task).permit(:title, :text)
  end

end

生成的嵌套路由:

# Routes without :task_id - Parent matters!

website_tasks
GET  /websites/:website_id/tasks(.:format) tasks#index
POST /websites/:website_id/tasks(.:format) tasks#create

new_website_task
GET  /websites/:website_id/tasks/new(.:format) tasks#new

# Routes with :task_id - Parent redundant.

edit_website_task
GET  /websites/:website_id/tasks/:id/edit(.:format) tasks#edit

website_task
GET    /websites/:website_id/tasks/:id(.:format) tasks#show
PATCH  /websites/:website_id/tasks/:id(.:format) tasks#update
PUT    /websites/:website_id/tasks/:id(.:format) tasks#update
DELETE /websites/:website_id/tasks/:id(.:format) tasks#destroy

您可以使用浅嵌套清除冗余website_id中的路由。详细解释了in the Rails docs

基本上它意味着:

resources :website do
  resources :tasks, only: [:index, :new, :create]
end
resources :tasks, only: [:show, :edit, :update, :destroy]

与写作相同:

resources :websites do
  resources :tasks, shallow: true
end

可能存在一些完整路径有价值的用例,例如: G。您希望将其提供给搜索引擎,或者您希望该网址更适合读者。

答案 1 :(得分:1)

  

所以问题是,Rails应该对这件作品做些什么   信息默认情况下?

如果您愿意,可以直接在ULR中对其进行硬编码来更改网站ID,但由于您的控制器负责根据请求动态生成URL,因此无法更新网站ID。

  

如果我想确保您正在访问该任务,请由我决定   在参数中使用正确的父资源?

是的,您可以通过确保以下内容确保使用正确的父级访问A任务:

  • 你的路线是像你一样的嵌套路线
  • 您的模型已定义关联,例如:网站:has_many :tasks和任务:belongs_to :website(例如)如果您想使用网站控制器创建任务,您可能还需要添加accepts_nested_attributes_for :tasks, reject_if: :all_blank, allow_destroy: true (我不知道你想做什么)
  • 当您在控制器中创建任务时,您正在使用父项例如:@website.tasks.new(task_params),以便使用website_id将任务保存在数据库中,这将允许您根据您的关联检索任务或任务

只要模型,视图和控制器知道网站和反之亦然的任务,您的路线就会生成并运行。