Object.save在规范数据验证中失败

时间:2011-10-23 16:14:03

标签: ruby-on-rails ruby-on-rails-3.1 rspec2

以下是客户控制器中创建的失败规范代码:

describe CustomersController do

  before(:each) do
    #the following recognizes that there is a before filter without execution of it.
    controller.should_receive(:require_signin)
    controller.should_receive(:require_employee)
  end

  render_views

    describe "'create' successful" do
      before(:each) do
        category = Factory(:category)
        sales = Factory(:user)      
        @customer = Factory.attributes_for(:customer, :category1_id => category.id, :sales_id => sales.id)
        session[:sales] =  true
        session[:user_id] = sales.id
        session[:user_name] = sales.name
        session[:page_step] = 1
        session['page1'] = customers_path
      end

      it "should create one customer record" do
        lambda do
          post 'create', @customer         
        end.should change(Customer, :count).by(1)
      end

      it "should redirect to customers path" do
        put 'create', @customer
        flash[:notice].should_not be_nil
        response.should redirect_to(customers_path)
      end
    end
 end

客户的销售ID和类别ID分别属于用户和类别表。

以下是规范失败错误:

  1) CustomersController GET customer page 'create' successful should create one customer record
     Failure/Error: lambda do
       count should have been changed by 1, but was changed by 0
     # ./spec/controllers/customers_controller_spec.rb:37:in `block (4 levels) in <top (required)>'

  2) CustomersController GET customer page 'create' successful should redirect to customers path
     Failure/Error: flash[:notice].should_not be_nil
       expected: not nil
            got: nil
     # ./spec/controllers/customers_controller_spec.rb:44:in `block (4 levels) in <top (required)>'

以下是在客户控制器中创建的应用代码:

  def create

    if session[:sales]
      @customer = Customer.new(params[:customer], :as => :roles_new_update)
      @customer.sales_id = session[:user_id]
      if @customer.save 
        @message = "New customer #{params[:name]} was created. Please check it out"
        @subject = "New customer #{params[:name]} was created BY {#session[:user_name]}"
        UserMailer.notify_tl_dh_ch_ceo(@message, @subject, session[:user_id])
        redirect_to session[('page' + session[:page_step].to_s).to_sym], :notice => 'Customer was created successfaully!'          
      else
        render 'new', :notice => 'Customer was not saved!'
      end
    end
  end

以下是factories.rb中的代码:

Factory.define :customer do |c|
  c.name                    "test customer"
  c.short_name              "test"   
  c.email                   "t@acom.com"
  c.phone                   "12345678"
  c.cell                    "1234567890"
  c.active                  1
  c.category1_id            2
  c.sales_id                1
  c.address                 "1276 S. Highland Ave, Lombard, IL 67034"
  c.contact                 "Jun C"

end

Factory.define :category do |c|
  c.name                   "category name"
  c.description            "test category"
  c.active                 true
end

Factory.define :user do |user|

  user.name                  "Test User"
  user.email                 "test@test.com"
  user.password              "password1"
  user.password_confirmation "password1"
  user.status                "active"
  user.user_type             "employee"

end

似乎错误是由@ customer.save返回false引起的,并且“if @ customer.save”的代码未执行。所以问题可能出在Factory生成的@customer上,这对我来说似乎很好。保存客户时,代码执行没有任何问题。

有什么建议吗?感谢。

2 个答案:

答案 0 :(得分:0)

我会将其分解为两个特定的测试。现在你不确定两件事:

  1. 客户被告知自救?
  2. 是否存在阻止客户保存的验证?
  3. 最快的方法是将@ customer.save更改为@ customer.save!并查看是否有任何异常(如果验证失败,它将会这样做)。

    我建议你把它分开。要测试#1,请在控制器规范中:

    it "should tell the customer to save itself when there is a session[:sales]" do
      session[:sales] = true
      customer_mock = double(:customer)
      customer_mock.should_receive(:sales_id=)
      customer_mock.should_receive(:save).and_return(:true)
      Customer.stub(:new => cutomer_mock)
      post 'create'
    end
    

    然后在您的customer_spec中,测试:

    it "should be valid with factory specs" do
      customer = Customer.new(Factory.attributes_for(:customer))
      customer.should be_valid
    end
    

答案 1 :(得分:0)

post :create, :customer => @customer

解决上述问题。