Home > Software design >  How can I link a parent object to its children using Ruby on Rails
How can I link a parent object to its children using Ruby on Rails

Time:11-11

I am very new to Ruby on Rails and try to make something simple, I have a list of parent objects on the landing page. I want the labels in that list to become links or link button that would take me to a list of children that correspond to the parent

Here is the routes.rb

  root 'parent_objects#index'
  resources :parent_objectsdo
     resources :child_objects, only: [:create, :destroy] 
  end

Models

class ParentObject < ApplicationRecord
   belongs_to :someobject
   has_many :child_object
end

class ChildObject < ApplicationRecord
    belongs_to :parent_object
end

Here is the landing page/index page where the parent_objects are displayed just fine. There I try to display the link where the parent object would take to the list of all child objects

<h1>Parent Objects</h1>

<table>
  <thead>
    <tr>
      <th>Parent object name</th>
      <th>Parent object description</th>
      <th colspan="3"></th>
    </tr>
  </thead>

  <tbody>
    <% @parent_objects.each do |parent_object| %>
      <tr>
        <td><%= link_to parent_object.parent_object_name, parent_object_path(parent_object) %>/td>
        <td><%= parent_object.description %></td>
        <td><%= link_to 'Show', parent_object%></td>
        <td><%= link_to 'Edit', edit_parent_object_path(todo_list) %></td>
        <td><%= link_to 'Destroy', parent_object, method: :delete, data: { confirm: 'Are you sure?' } %></td>
      </tr>
    <% end %>
  </tbody>
</table>
<%= will_paginate @todo_lists %>
<br>

<%= link_to 'New Todo List', new_todo_list_path %>

Here is the controller for the child object

class ChildObjectController < ApplicationController
  before_action :set_child_object, only: %i[ show edit update destroy ]

  def index
    @child_object = ChildObject.where(parent_object_id: params[:id])
  end

  def show
  end

  private
    # Use callbacks to share common setup or constraints between actions.
    def set_child_object
       @child_object = ChildObject.where(parent_object_id: params[:id])
    end

    # Only allow a list of trusted parameters through.
    def child_object_params
      params.require(:child_object).permit(:name, :description)
    end
end

When I try to click the link/link button for the parent object, for some reason the show action is invoked where get the error for the undefined method name for the @child_object

I know that I somehow need invoke the index page for the child object

Please let me know what I am doing wrong

Thank you very much in advance

CodePudding user response:

resources :parent_objects do
  resources :child_objects, only: [:index] 
end

Make sure the controller is properly pluralized:

class ChildObjectsController < ApplicationController
  # GET /parent_objects/1/child_objects
  def index
    @parent_object = ParentObject.find(params[:parent_object_id])
    @child_objects = @parent_object.child_objects 
  end
end

Note that you want to use .find to find the parent record so that the correct 404 - Not Found response is returned if the id is invalid instead of having your code blow up later with a nil error.

To link to a nested route you can use the named path helper:

link_to 'Child objects', parent_object_child_objects_path(parent_object)

Or use the polymorphic route helpers to lookup the helper method:

link_to 'Child objects', [parent_object, :child_objects]
  • Related