Rspec – RuntimeError:nil的被调用id,错误地为4

我现在正在为ItemsController create操作进行Rspec测试,但是我遇到了错误。 (有ItemAuctionBidUser等型号)

create方法如下

  # POST /items # POST /items.json def create @item = Item.new(params[:item]) @item.user_id = current_user.id respond_to do |format| if @item.save format.html { redirect_to @item, notice: 'Item was successfully created.' } format.json { render json: @item, status: :created, location: @item } else format.html { render action: "new" } format.json { render json: @item.errors, status: :unprocessable_entity } end end @elapsed_seconds =(((params[:item][:days].to_i * 24)+params[:item][:hours].to_i)*60+params[:item][:minutes].to_i)*60 @auction = Auction.create(:item_id => @item.id, :highest_bid_id => 0, :exp_time => @item.created_at+ @elapsed_seconds.seconds, :suspend => 0, :user_id => @current_user.id, :extend_bit => 0 ) @item.update_attributes(:auction_id => @auction.id) @item_id = @item.id @auction_id = @auction.id @t1 = Thread.new{ @timer = Timers.new @bid_timer = @timer.after(@elapsed_seconds){ if Auction.find_by_id(@auction_id).suspend != 1 buy end } @timer.wait } end def buy if Auction.find_by_id(@auction_id).extend_bit == 1 extendtimer else if Auction.find_by_id(@auction_id).highest_bid_id != 0 Item.find_by_auction_id(@auction_id).update_attributes(:sold => 1, :sold_to => Bid.find_by_id(Auction.find_by_id(@auction_id).highest_bid_id).user_id ) MyMailer.auction_winner_email(Auction.find_by_id(@auction_id)).deliver else Item.find_by_auction_id(@auction_id).update_attributes(:sold => 0, :sold_to => 0 ) MyMailer.no_bids_email(Auction.find_by_id(@auction_id)).deliver end @t1.join end end def extendtimer Auction.find_by_id(@auction_id).update_attributes(:extend_bit => 0) @exp = Auction.find_by_id(@auction_id).exp_time + 2.minutes Auction.find_by_id(@auction_id).update_attributes(:exp_time => @exp) @min = Item.find_by_id(@item_id).minutes + 2 Item.find_by_id(@item_id).update_attributes(:minutes => @min) @timer2 = Timers.new @extend_timer = @timer2.after(120){ buy } @timer2.wait end 

我的Rspec如下。 此测试旨在首先使用对象(例如current_userauction ,“item” ). Then also stubs are declared. (such as Auction.stub(:find_by_id).and_return(auction)`)

 require 'spec_helper' describe ItemsController do let(:valid_session) { {} } describe "POST create" do it "" do #declare the objects and stubs current_user = User.new(id:'1') current_user.save auction = Auction.new(id:'1',highest_bid_id:'1', extend_bit:'1') auction.save Auction.stub(:find_by_id).and_return(auction) bid = Bid.new(auction_id:'1',amount:'150.0') bid.save Bid.stub(:find_by_id).and_return(bid) item = Item.new(id:'1',auction_id:'1',min_bid_price:'100.0') item.save Item.stub(:find_by_id).and_return(item) #POST create post :create, {:item => {'id' => '2','days'=>'1','hours'=>'1','minutes'=>'1'}} response.should redirect_to(@item) flash[:notice].should eql("Item was successfully created.") end end end 

不幸的是我跑了Rspec,我得到了如下错误。 我认为控制器中的@item无法通过@item = Item.new(params[:item])成功创建,因此可能会发生此错误。 但是我找不到如何解决。 我已经用了好几个小时了。 我想得到别人的帮助。

失败:

 1) ItemsController POST create Failure/Error: post :create, {:item => {'id' => '2','days'=>'1','hours'=>'1','minutes'=>'1'}} RuntimeError: Called id for nil, which would mistakenly be 4 -- if you really wanted the id of nil, use object_id # ./app/controllers/items_controller.rb:72:in `create' # ./spec/controllers/items_controller_spec.rb:19:in `block (3 levels) in ' Finished in 0.637 seconds 1 example, 1 failure Failed examples: rspec ./spec/controllers/items_controller_spec.rb:11 # ItemsController POST create Randomized with seed 33483 

由于没有人登录, current_user方法返回nil 。 在规范中设置局部变量current_user对此没有帮助。 相反,您可以定义ApplicationController#current_user= method:

 def current_user=(user) @current_user ||= user end 

并在您的规格中调用它:

 controller.current_user = current_user