4

在我的Rails 4的应用程序中,有四种模式:Rails 4嵌套浅层路由:如何在子控制器中获取父ID?

class User < ActiveRecord::Base 
    has_many :administrations 
    has_many :calendars, through: :administrations 
end 

class Calendar < ActiveRecord::Base 
    has_many :administrations 
    has_many :users, through: :administrations 
    has_many: :posts 
end 

class Administration < ActiveRecord::Base 
    belongs_to :user 
    belongs_to :calendar 
end 

class Post < ActiveRecord::Base 
    belongs_to :calendar 
end 

有了这个路由:

Rails.application.routes.draw do 

    root to: 'pages#home' 

    devise_for :users, :path => 'account' 

    resources :calendars do 
    resources :posts, shallow: true 
    end 

end 

哪个给出了这些路线:

Prefix Verb URI Pattern         Controller#Action 
        posts GET /posts(.:format)       posts#index 
         POST /posts(.:format)       posts#create 
       new_post GET /posts/new(.:format)      posts#new 
       edit_post GET /posts/:id/edit(.:format)     posts#edit 
        post GET /posts/:id(.:format)      posts#show 
         PATCH /posts/:id(.:format)      posts#update 
         PUT /posts/:id(.:format)      posts#update 
         DELETE /posts/:id(.:format)      posts#destroy 
        root GET /           pages#home 
     new_user_session GET /account/sign_in(.:format)     devise/sessions#new 
      user_session POST /account/sign_in(.:format)     devise/sessions#create 
    destroy_user_session DELETE /account/sign_out(.:format)     devise/sessions#destroy 
      user_password POST /account/password(.:format)     devise/passwords#create 
     new_user_password GET /account/password/new(.:format)    devise/passwords#new 
     edit_user_password GET /account/password/edit(.:format)   devise/passwords#edit 
         PATCH /account/password(.:format)     devise/passwords#update 
         PUT /account/password(.:format)     devise/passwords#update 
cancel_user_registration GET /account/cancel(.:format)     devise/registrations#cancel 
     user_registration POST /account(.:format)       devise/registrations#create 
    new_user_registration GET /account/sign_up(.:format)     devise/registrations#new 
    edit_user_registration GET /account/edit(.:format)      devise/registrations#edit 
         PATCH /account(.:format)       devise/registrations#update 
         PUT /account(.:format)       devise/registrations#update 
         DELETE /account(.:format)       devise/registrations#destroy 
     user_confirmation POST /account/confirmation(.:format)    devise/confirmations#create 
    new_user_confirmation GET /account/confirmation/new(.:format)   devise/confirmations#new 
         GET /account/confirmation(.:format)    devise/confirmations#show 
      user_unlock POST /account/unlock(.:format)     devise/unlocks#create 
     new_user_unlock GET /account/unlock/new(.:format)    devise/unlocks#new 
         GET /account/unlock(.:format)     devise/unlocks#show 
      calendar_posts GET /calendars/:calendar_id/posts(.:format)  posts#index 
         POST /calendars/:calendar_id/posts(.:format)  posts#create 
     new_calendar_post GET /calendars/:calendar_id/posts/new(.:format) posts#new 
         GET /posts/:id/edit(.:format)     posts#edit 
         GET /posts/:id(.:format)      posts#show 
         PATCH /posts/:id(.:format)      posts#update 
         PUT /posts/:id(.:format)      posts#update 
         DELETE /posts/:id(.:format)      posts#destroy 
       calendars GET /calendars(.:format)      calendars#index 
         POST /calendars(.:format)      calendars#create 
      new_calendar GET /calendars/new(.:format)     calendars#new 
      edit_calendar GET /calendars/:id/edit(.:format)    calendars#edit 
       calendar GET /calendars/:id(.:format)     calendars#show 
         PATCH /calendars/:id(.:format)     calendars#update 
         PUT /calendars/:id(.:format)     calendars#update 
         DELETE /calendars/:id(.:format)     calendars#destroy 

最后,这里是内容posts_controller.rb

class PostsController < ApplicationController 
    before_action :set_post, only: [:show, :edit, :update, :destroy] 

    # GET /posts 
    # GET /posts.json 
    def index 
    @posts = Post.all 
    end 

    # GET /posts/1 
    # GET /posts/1.json 
    def show 
    end 

    # GET /posts/new 
    def new 
    @post = Post.new 
    end 

    # GET /posts/1/edit 
    def edit 
    end 

    # POST /posts 
    # POST /posts.json 
    def create 
    @calendar = Calendar.find(params[:calendar_id]) 
    @post = @calendar.posts.create(post_params) 

    respond_to do |format| 
     if @post.save 
     format.html { redirect_to calendar_path(@calendar), notice: 'Post was successfully created.' } 
     format.json { render :show, status: :created, location: @post } 
     else 
     format.html { render :new } 
     format.json { render json: @post.errors, status: :unprocessable_entity } 
     end 
    end 
    end 

    # PATCH/PUT /posts/1 
    # PATCH/PUT /posts/1.json 
    def update 
    respond_to do |format| 
     if @post.update(post_params) 
     format.html { redirect_to calendar_path, notice: 'Post was successfully updated.' } 
     format.json { render :show, status: :ok, location: @post } 
     else 
     format.html { render :edit } 
     format.json { render json: @post.errors, status: :unprocessable_entity } 
     end 
    end 
    end 

    # DELETE /posts/1 
    # DELETE /posts/1.json 
    def destroy 
    @calendar = Calendar.find(params[:calendar_id]) 
    @post.destroy 
    respond_to do |format| 
     format.html { redirect_to calendar_path(@calendar), notice: 'Post was successfully destroyed.' } 
     format.json { head :no_content } 
    end 
    end 

    private 
    # Use callbacks to share common setup or constraints between actions. 
    def set_post 
     @post = Post.find(params[:id]) 
    end 

    # Never trust parameters from the scary internet, only allow the white list through. 
    def post_params 
     params.require(:post).permit(:date, :time, :subject, :format, :copy, :media) 
    end 
end 

我一直在遇到类似的错误。

问题#1:当我尝试从show.html.erb日历视图中删除一个帖子:

<h2><%= @calendar.name %> Calendar</h2> 

<h3>Posts</h3> 
<% if @calendar.posts.any? %> 
    <table> 
     <tr> 
      <th>Date</th> 
      <th>Time</th> 
      <th>Subject</th> 
      <th>Format</th> 
      <th>Copy</th> 
      <th>Media</th> 
     </tr> 
    <% @calendar.posts.each do |post| %> 
     <tr> 
     <td><%= post.date %></td> 
      <td><%= post.time %></td> 
      <td><%= post.subject %></td> 
      <td><%= post.format %></td> 
      <td><%= post.copy %></td> 
      <td><%= post.media %></td> 
     <td><%= link_to 'View', post %></td> 
     <td><%= link_to 'Update', edit_post_path(post) %></td> 
     <td><%= link_to 'Delete', post, method: :delete, data: { confirm: 'Are you sure?' } %></td> 
     </tr> 
    </table> 
    <% end %> 
... 

我得到:

ActiveRecord::RecordNotFound in PostsController#destroy 
Couldn't find Calendar with 'id'= 

问题2: :当我尝试更新edit.html.erb的帖子时后视图:

<h1>Editing Post</h1> 

<%= render 'form' %> 

<%= link_to 'Show', @post %> | 
<%= link_to 'Back', posts_path %> 

我得到:

ActiveRecord::RecordNotFound in PostsController#update 
Couldn't find Calendar with 'id'= 

问题#3:当我回去从show.html.erb后视图show.html.erb日历视图:

<div> 
    <p>Date</p> 
    <%= @post.date %> 
</div> 
<div> 
    <p>Time</p> 
    <%= @post.time %> 
</div> 
<div> 
    <p>Subject</p> 
    <%= @post.subject %> 
    </div> 
<div> 
    <p>Format</p> 
    <%= @post.format %> 
    </div> 
<div> 
    <p>Copy</p> 
    <%= @post.copy %> 
</div> 
<div> 
    <p>Media</p> 
    <%= @post.media %> 
</div> 

<%= link_to 'Edit', edit_post_path(@post) %> | 
<%= link_to 'Back', posts_path %> 

我得到:

ActiveRecord::RecordNotFound in PostsController#show 
Couldn't find Calendar with 'id'= 

如果我错误的解释是正确的,每一次,这个问题似乎是,我不能检索calendarpostid属于。

换句话说,我无法从子(后)控制器检索父(日历)ID。

我相信这是一个与我的嵌套浅层资源相关的问题,以及我的链接在视图中构建的方式。

我无法弄清楚如何使这些链接工作。

如果你能为我提供解决方案 - 最重要的是推理 - 对于上述三种情况之一,我绝对能够为其他两种解决方案提供解决方案。

有什么想法?

回答

3

我找到了解决我的三个问题的每一个问题。

问题#1:我代替:

format.html { redirect_to calendar_path(@calendar), notice: 'Post was successfully destroyed.' } 

有:

format.html { redirect_to calendar_path(@post.calendar_id), notice: 'Post was successfully destroyed.' } 

posts_controller.rb

问题#2:我代替:

<%= link_to 'Back', posts_path %> 

有:

<%= link_to 'Back', calendar_path(@post.calendar_id) %> 
edit.html.erb职位

查看。

问题#3:我代替:

<%= link_to 'Back', posts_path %> 

有:

calendar_path(@post.calendar_id) 
show.html.erb职位

查看