I would like to test my controller after I added strong_parameters gem, how to do that? I tried:

Controller

class EventsController < ApplicationController
  def update
    @event = Event.find(params[:id])
    respond_to do |format|
      if @event.update_attributes(event_params)
        format.html { redirect_to(@event, :notice => 'Saved!') }
      else
        format.html { render :action => "new" }
      end
    end
  end

  private
  def event_params
    params.require(:event).permit!
  end
end

Specs

describe EventsController do
  describe "PUT update" do
    describe "with forbidden params" do
      let(:event) { Event.create! title: "old_title", location: "old_location", starts_at: Date.today }

      it "does not update the forbidden params" do
        put :update,
          id: event.to_param,
          event: { 'title' => 'new_title', 'location' => 'NY' }

        assigns(:event).title.should eq('new_title') # explicitly permitted
        assigns(:event).location.should eq("old_location")  # implicitly forbidden

        response.should redirect_to event
      end
    end
  end
end

Errors

1) EventsController PUT update with forbidden params does not update the forbidden params
   Failure/Error: assigns(:event).title.should eq('new_title') # explicitly permitted
   NoMethodError:
     undefined method `title' for nil:NilClass
   # ./spec/controllers/events_controller_spec.rb:13:in
有帮助吗?

解决方案

I see a few things going on here.

The fact that it says undefined method on line 13 is because the @event variable is not being assigned, so assigns(:event) is returning nil. You should check out why that is happening, maybe you have some authentication that is preventing you from updating the record? Maybe you can check out the testing logs to see what is actually going on.
It could be because you are using let() which is lazy and the record is not actually available yet when you try to search for it, but I'm not completely sure. You could try using let!() and see if that helps.

With regards to the actual usage of strong parameters, if you only want title to be assignable you need to do something like the following:

params.require(:event).permit(:title)

If you use permit!, the event parameters hash and every subhash is whitelisted.

许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top