Ruby-on-rails Rails 3:如何创建新的嵌套资源?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/3784183/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-02 23:15:29  来源:igfitidea点击:

Rails 3: How to create a new nested resource?

ruby-on-railsruby-on-rails-3

提问by Andrew

The Getting Started Rails Guidekind of glosses over this part since it doesn't implement the "new" action of the Comments controller. In my application, I have a book model that has many chapters:

入门指南Rails的那种粉饰过这一部分,因为它没有实现评论控制器的“新”行动。在我的应用程序中,我有一个包含许多章节的书籍模型:

class Book < ActiveRecord::Base
  has_many :chapters
end

class Chapter < ActiveRecord::Base
  belongs_to :book
end

In my routes file:

在我的路线文件中:

resources :books do
  resources :chapters
end

Now I want to implement the "new" action of the Chapters controller:

现在我想实现 Chapters 控制器的“新”操作:

class ChaptersController < ApplicationController
  respond_to :html, :xml, :json

  # /books/1/chapters/new
  def new
    @chapter = # this is where I'm stuck
    respond_with(@chapter)
  end

What is the right way to do this? Also, What should the view script (form) look like?

这样做的正确方法是什么?另外,视图脚本(表单)应该是什么样的?

回答by dombesz

First you have to find the respective book in your chapters controller to build a chapter for him. You can do your actions like this:

首先你必须在你的章节控制器中找到相应的书来为他建立一个章节。您可以执行以下操作:

class ChaptersController < ApplicationController
  respond_to :html, :xml, :json

  # /books/1/chapters/new
  def new
    @book = Book.find(params[:book_id])
    @chapter = @book.chapters.build
    respond_with(@chapter)
  end

  def create
    @book = Book.find(params[:book_id])
    @chapter = @book.chapters.build(params[:chapter])
    if @chapter.save
    ...
    end
  end
end

In your form, new.html.erb

在您的表单中,new.html.erb

form_for(@chapter, :url=>book_chapters_path(@book)) do
   .....rest is the same...

or you can try a shorthand

或者你可以试试速记

form_for([@book,@chapter]) do
    ...same...

Hope this helps.

希望这可以帮助。

回答by Andrew Vit

Try @chapter = @book.build_chapter. When you call @book.chapter, it's nil. You can't do nil.new.

试试@chapter = @book.build_chapter。当你打电话时@book.chapter,它是零。你不能做nil.new

EDIT: I just realized that book most likely has_many chapters... the above is for has_one. You should use @chapter = @book.chapters.build. The chapters "empty array" is actually a special object that responds to buildfor adding new associations.

编辑:我刚刚意识到这本书很可能有很多章……以上是针对 has_one 的。你应该使用@chapter = @book.chapters.build. 章节“空数组”实际上是一个特殊的对象,用于响应build添加新关联。

回答by xxjjnn

Perhaps unrelated, but from this question's title you might arrive here looking for how to do something slightly different.

也许无关,但从这个问题的标题你可能会来到这里寻找如何做一些稍微不同的事情。

Lets say you want to do Book.new(name: 'FooBar', author: 'SO')and you want to split some metadata into a separate model, called readable_configwhich is polymorphic and stores nameand authorfor multiple models.

假设您想要做Book.new(name: 'FooBar', author: 'SO')并且您想要将一些元数据拆分为一个单独的模型,称为readable_config多态和存储name以及author用于多个模型。

How do you accept Book.new(name: 'FooBar', author: 'SO')to build the Bookmodel and also the readable_configmodel (which I would, perhaps mistakenly, call a 'nested resource')

您如何接受Book.new(name: 'FooBar', author: 'SO')构建Book模型以及readable_config模型(我可能会错误地将其称为“嵌套资源”)

This can be done as so:

这可以这样做:

class Book < ActiveRecord::Base
  has_one :readable_config, dependent: :destroy, autosave: true, validate: true
  delegate: :name, :name=, :author, :author=, :to => :readable_config

  def readable_config
    super ? super : build_readable_config
  end
end