kandros
kandros

Reputation: 101

Rails reference two levels deep nest in controller

I have a two level deep nesting:

routes.rb

  resources :projects do
    resources :offers do
      resources :reports
    end
  end

In offers controller I use:

before_action :set_project
before_action :set_offer, only: [:show, :edit, :update, :destroy]
.....  

def index
    @offers = @project.offers
end

.....

def set_project
  @project = Project.find(params[:project_id])
end

# Use callbacks to share common setup or constraints between actions.
def set_offer
  @offer = @project.offers.find(params[:id])
end

How can I reference repors in Reports_controller.rb like in offer's index?

Upvotes: 0

Views: 441

Answers (1)

Rob Wise
Rob Wise

Reputation: 5120

It's the same idea:

# reports_controller.rb

def index
  @reports = Reports.where(project: params[:project_id], 
                           offer: params[:offer_id])
end

def update
  @report = Reports.find_by(project: params[:project_id], 
                            offer: params[:offer_id],
                            id: params[:id])
  # rest of update code
end

You could put this logic into helper methods if you want like you did for the other ones.

I would also just mention that it's usually discouraged to nest much more than one level deep like this because, as you can see, it's getting kind of messy. One compromise that I use a lot is to use the shallow resources method.

Definitely check out this section of the Rails Routing guide for more info on this and how to implement shallow nesting. It basically lets you make it so that you only require the additional parameters for actions that actually need that information, but the other actions let you reference the resource by just its id without the need for the other parameters.

Upvotes: 1

Related Questions