I am setting up a test that should expect calls on two "subscriber" instances:
it "sends out sms to all the subscribers" do
#user.subscribers.create!
#user.subscribers.create!
Subscriber.any_instance.should_receive(:send_message).with(#message).times(2)
post :create, {:broadcast => valid_attributes}
end
The actual code is:
def create
#broadcast = Broadcast.new(params[:broadcast])
current_user.subscribers.each do |subscriber|
subscriber.send_message(#broadcast.message)
end
...
The error:
Failure/Error: post :create, {:broadcast => valid_attributes}
ArgumentError:
wrong number of arguments (1 for 0)
# ./app/controllers/broadcasts_controller.rb:41:in `block in create'
# ./app/controllers/broadcasts_controller.rb:40:in `create'
# ./spec/controllers/broadcasts_controller_spec.rb:73:in `block (4 levels) in <top (required)>'
For some reason, if I add the line: Subscriber.any_instance.should_receive(:send_message).with(#message).times(2), it fails with that error message. If I remove that line, the test runs smoothly (no wrong number of argument problem). What am I doing wrong?
The error you're getting is because the 'times' method is expected to be chained onto one of the other "receive count" expectations. You can use any one of the following:
should_receive(:send_message).with(#message).exactly(2).times
should_receive(:send_message).with(#message).at_most(2).times
You can also use one of the other alternatives that does not require the 'times' method:
should_receive(:send_message).with(#message).twice
should_receive(:send_message).with(#message).at_most(:twice)
More on that can be found in the rspec-mocks documentation
You may need to set the expectation BEFORE creating the subscribers:
it "sends out sms to all the subscribers" do
Subscriber.any_instance.should_receive(:send_message).with(#message).twice
#user.subscribers.create!
#user.subscribers.create!
post :create, {:broadcast => valid_attributes}
end
Related
Hello i have problem with testing JSONAPI with rspec and airborne.
GET model below
https://i.stack.imgur.com/Cyf75.png
Im testing it this way https://i.stack.imgur.com/Y9rHt.png
Rspec output:
Failures:
1) GET on /contacts should validate types
Failure/Error: expect_json('books.0', title: 'The Great Escape')
Airborne::PathError:
Expected NilClass
to be an object with property 0
# /home/robert/.rvm/gems/ruby-2.4.0/gems/airborne-0.2.5/lib/airborne/path_matcher.rb:21:in `rescue in block in get_by_path'
# /home/robert/.rvm/gems/ruby-2.4.0/gems/airborne-0.2.5/lib/airborne/path_matcher.rb:18:in `block in get_by_path'
# /home/robert/.rvm/gems/ruby-2.4.0/gems/airborne-0.2.5/lib/airborne/path_matcher.rb:9:in `each'
# /home/robert/.rvm/gems/ruby-2.4.0/gems/airborne-0.2.5/lib/airborne/path_matcher.rb:9:in `each_with_index'
# /home/robert/.rvm/gems/ruby-2.4.0/gems/airborne-0.2.5/lib/airborne/path_matcher.rb:9:in `get_by_path'
# /home/robert/.rvm/gems/ruby-2.4.0/gems/airborne-0.2.5/lib/airborne/request_expectations.rb:137:in `call_with_path'
# /home/robert/.rvm/gems/ruby-2.4.0/gems/airborne-0.2.5/lib/airborne/request_expectations.rb:18:in `expect_json'
# ./book_resource.rb:10:in `block (2 levels) in <top (required)>'
# ------------------
# --- Caused by: ---
# NoMethodError:
# undefined method `[]' for nil:NilClass
# /home/robert/.rvm/gems/ruby-2.4.0/gems/airborne-0.2.5/lib/airborne/path_matcher.rb:57:in `process_json'
Finished in 0.03121 seconds (files took 0.17681 seconds to load)
1 example, 1 failure
Your API response doesn't have the key books. Instead, it is returning the response as { "data": [ ... ] }.
So, in your tests, you need to specify expect_json('data.0', ...), instead of expect_json('books.0', ...).
Hope that should resolve this issue.
Already solve with:
describe Api::UsersController do
describe 'GET on /users' do
before do
FactoryGirl.create('user', name: 'Jack McClure')
FactoryGirl.create('user', name: 'Johny Reaper')
FactoryGirl.create('user', name: 'Niko Bellic')
end
it 'should return valid user' do
get :index, format: 'json'
expect_json('data.0.attributes', name: "Jack McClure")
expect_json('data.2.attributes', name: 'Niko Bellic')
end
end
i'm trying to run a controller test:
the controller code is
def aix_service_accounts
#no_dn_users= Hash.new
record = 0
#no_dn_users[record]= Hash.new
#no_dn_users[record]['aix_username'] ="abc"
end
The rspec code is
it "should show aix_service_accounts" do
get :aix_service_accounts
expect(assigns(:no_dn_users[0]['aix_username'])).to eq 'abc'
end
The result is
Failures:
1) AixController should show aix_service_accounts
Failure/Error: expect(assigns(:no_dn_users[0]['aix_username'])).to eq 'abc'
expected: "abc"
got: {"marked_for_same_origin_verification"=>true, "no_dn_users"=>{0=>{"aix_username"=>"abc"}}}
(compared using ==)
Diff:
## -1,2 +1,3 ##
-"abc"
+"marked_for_same_origin_verification" => true,
+"no_dn_users" => {0=>{"aix_username"=>"abc"}},
# ./spec/controllers/aix_controller_spec.rb:29:in `block (2 levels) in <top (required)>'
Could anyone help and explain the reason to me? Thanks!
Sure - you're trying to ask for a single key called :no_dn_users[0]['aix_username'] from the assigns. You need to change that to:
assigns(:no_dn_users)[0]['aix_username']
instead.
Ie, get out the first part by the key :no_dn_users, this will be the hash-inside-an-array that you're then referencing using indexing
1) RfidT is not valid without device_mac
Failure/Error: expect(obj2.errors[:device_mac]).to include ("not valid without device_mac!")
expected [] to include "not valid without device_mac!"
# ./spec/models/rfid_t_spec.rb:20:in `block (2 levels) in <top (required)>'
2) RfidT duplicate values of epc are not allowed
Failure/Error: expect(obj3.errors[:epc]).to include("duplicate values of epc are not allowed!")
expected [] to include "duplicate values of epc are not allowed!"
# ./spec/models/rfid_t_spec.rb:27:in `block (2 levels) in <top (required)>'
3) RfidT is not valid without first_seen
Failure/Error: expect(obj4.errors[:first_seen]).to include("cannot be Blank!")
expected ["can't be blank"] to include "cannot be Blank!"
# ./spec/models/rfid_t_spec.rb:33:in `block (2 levels) in <top (required)>'
4) RfidT is not valid without last_seen
Failure/Error: expect(obj5.errors[:last_seen]).to include("cannot be Blank!")
expected ["can't be blank"] to include "cannot be Blank!"
# ./spec/models/rfid_t_spec.rb:39:in `block (2 levels) in <top (required)>'
Finished in 0.16685 seconds (files took 6.45 seconds to load)
6 examples, 4 failures
But when i am using to_not in place of to in spec file then i am not getting any error .Please tell me what is meaning of this and what is the diffrence between to and to_not in ruby and rails.
my spec file generating no error is:
require 'rails_helper'
RSpec.describe RfidT, type: :model do
it "is valid without epc,device_mac,first_seen,last_seen,count" do
obj=RfidT.new(epc:"abc",device_mac:"pqrs",first_seen:10,last_seen:20,count:200)
expect(obj).to be_valid
end
it "is not valid without epc" do
obj1=RfidT.new(epc:nil)
obj1.valid?
#expect(obj1.errors[:epc]).to include("cannot be Blank!")
expect(obj1).to_not be_valid
end
it"is not valid without device_mac " do
obj2=RfidT.new(device_mac:nil)
obj2.valid?
expect(obj2.errors[:device_mac]).to_not include ("not valid without device_mac!")
end
it" duplicate values of epc are not allowed" do
RfidT.create(epc:"abc",device_mac:"pqrs",first_seen:10,last_seen:20,count:200)
obj3=RfidT.new(epc:"abc",device_mac:"pqrs",first_seen:10,last_seen:20,count:200)
obj3.valid?
expect(obj3.errors[:epc]).to_not include("duplicate values of epc are not allowed!")
end
it "is not valid without first_seen " do
obj4=RfidT.new(first_seen:nil)
obj4.valid?
expect(obj4.errors[:first_seen]).not_to include("cannot be Blank!")
end
it "is not valid without last_seen " do
obj5=RfidT.new(last_seen:nil)
obj5.valid?
expect(obj5.errors[:last_seen]).to_not include("cannot be Blank!")
end
end
to checks that the matcher (the thing that follows) matches, for example
expect(obj).to be_valid
Checks that obj.valid? is truthy. If it isn't the example will be mark as failed.
to_not is the opposite: it checks that the matcher doesn't match. In the above example it will mark the example as failed if obj.valid? is truthy.
Unless your code raises an exception, one of to or to_not will pass, because they are opposites of each other.
Your rspec output is telling you that your validations are not enforcing the constraints you want them to.
I am attempting to write a model test, like so:
require 'spec_helper'
describe Five9List do
before :each do
#five9_list = Five9List.new(name: 'test_list', size: '100')
end
describe "#new" do
it "takes two parameters and returns a Five9List object" do
#five9_list.should be_an_instance_of Five9List
end
end
describe "#name" do
it "returns the correct name" do
#five9_list.name.should eql "test_list"
end
end
describe "#size" do
it "returns the correct size" do
#five9_list.size.should eql 100
end
end
end
Currently, this succeeds and works fine. That's because my model is using attr_accessible, like so:
class Five9List < ActiveRecord::Base
attr_accessible :name, :size
end
If I want to get rid of attr_accessible and follow the rails 4 convention of using strong_params, how would I write that to where my rspec test would still succeed?
Adding this in my controller:
private
def five9_list_params
params.require(:five9_list).permit(:name, :size)
end
And removing attr_accessible does not work.
EDIT
Here is the error I receive from rspec .:
Failures:
1) Five9List#name returns the correct name
Failure/Error: #five9_list.name.should eql "test_list"
expected: "test_list"
got: nil
(compared using eql?)
# ./spec/models/five9_list_spec.rb:16:in `block (3 levels) in <top (required)>'
2) Five9List#size returns the correct size
Failure/Error: #five9_list.size.should eql 100
expected: 100
got: nil
(compared using eql?)
# ./spec/models/five9_list_spec.rb:22:in `block (3 levels) in <top (required)>'
Finished in 0.03303 seconds
4 examples, 2 failures, 1 pending
Failed examples:
rspec ./spec/models/five9_list_spec.rb:15 # Five9List#name returns the correct name
rspec ./spec/models/five9_list_spec.rb:21 # Five9List#size returns the correct size
Randomized with seed 20608
There's nothing wrong with your spec. I can only guess that you're not running Rails 4 or you've installed the ProtectedAttributes gem.
I'm getting these failures when running rspec spec/. The spec that is failing is was auto-generated with the scaffolding. I'm trying to understand RSpec but I don't know where to begin looking for the cause other than it feels like some method is missing?!? Yet, app appears to be working fine. Nothing about these failures appears in test.log. Is there another place I should be looking for hints to track this down?
$ rspec spec/
.....................F.F.
Failures:
1) clowns/edit.html.haml renders the edit clown form
Failure/Error: render
undefined method `to_sym' for nil:NilClass
# ./app/views/clowns/_form.html.haml:4:in `block in _app_views_clowns__form_html_haml__3590088286240866241_2176114460_3896491916910336970'
# ./app/views/clowns/_form.html.haml:1:in `_app_views_clowns__form_html_haml__3590088286240866241_2176114460_3896491916910336970'
# ./app/views/clowns/edit.html.haml:3:in `_app_views_clowns_edit_html_haml___574620942879655923_2176081980_599706797287605391'
# ./spec/views/clowns/edit.html.haml_spec.rb:13:in `block (2 levels) in <top (required)>'
2) clowns/new.html.haml renders new clown form
Failure/Error: render
undefined method `to_sym' for nil:NilClass
# ./app/views/clowns/_form.html.haml:4:in `block in _app_views_clowns__form_html_haml__3590088286240866241_2176114460_3896491916910336970'
# ./app/views/clowns/_form.html.haml:1:in `_app_views_clowns__form_html_haml__3590088286240866241_2176114460_3896491916910336970'
# ./app/views/clowns/new.html.haml:3:in `_app_views_clowns_new_html_haml__1085372210838170129_2159651900_599706797287605391'
# ./spec/views/clowns/new.html.haml_spec.rb:12:in `block (2 levels) in <top (required)>'
Finished in 1.03 seconds
27 examples, 2 failures, 2 pending
And here is the spec that apparently fails (edit.html.haml_spec.rb). It was auto-generated by rails g scaffold Clown name:string balloons:integer:
#spec/views/clowns/edit.html.haml_spec.rb
require 'spec_helper'
describe "clowns/edit.html.haml" do
before(:each) do
#clown = assign(:clown, stub_model(Clown,
:name => "MyString",
:balloons => 1
))
end
it "renders the edit clown form" do
render
# Run the generator again with the --webrat-matchers flag if you want to use webrat matchers
assert_select "form", :action => clown_path(#clown), :method => "post" do
assert_select "input#clown_name", :name => "clown[name]"
assert_select "input#clown_balloons", :name => "clown[balloons]"
end
end
end
Are you also using simple_form (or perhaps even formtastic)? I get the same error when I convert the scaffold forms from standards forms to simple_form forms (form_for(#user) => simple_form_for(#user)).
It still works, as you say, so I'm not sure it's worth worrying about. I think you'd be better off just letting Cucumber worry about it. Sarah Mei says view specs are a waste of time. :-)