Issues with a spec test

I am having issues with the following spec test :

 74     before do
 75       allow_any_instance_of(Chef::Recipe).to receive(:include_recipe).and_call_original
 76       allow(File).to receive(:exist?).and_call_original
 77       allow(File).to receive(:exist?).with('/etc/.firstboot_done').and_return(false)
 78     end
 79
 80     cached(:chef_run) do
 81       ChefSpec::ServerRunner.new(platform: 'aws', version: 'xxx') do |node|
 82         node.normal[:xxx][:xxx] = 'xxx'
 83         node.normal[:xxx] = 'xxx'
 84         node.normal[:xxx] = 'xxx'
 85         node.normal[:opc_hostmetrics][:package] = 'opc-hostmetrics'
 86         node.normal[:xxx][:version] = xxx
 87         node.normal[:xxx][:release] = xxx
 88         node.normal[:packages] = {}
 89       end.converge(described_recipe)
 90     end
 91
 92     it 'installs opc-hostmetrics when no version is installed' do
 93       expect(chef_run).to install_package('opc-hostmetrics').with(version: '2.0-2')
 94       binding.pry
 95     end
 96   end```

Here’s what rspec is returning: expected "package[opc-hostmetrics]" with action :install to be in Chef run

I have referenced google, bing, and duckduckgo to with no luck on finding wtf that rspec error means?

Oh yeah…here’s the associated recipe:

  4   action :install
  5   only_if { ::File.exist?('/etc/.firstboot_done') }
  6 end```

It looks like it can’t find the package resource in the resource collection.
aka, you don’t ahve
package ‘opc-hostmetrics’ anywhere in the run

Ah right then you need to find aw ay to stub that file out.

Thanks for the reply…which file are you referring to that I need to stub out?

I am assuming you mean /etc/.firstboot_done

You might be better served not using ChefSpec for this and just use Test Kitchen and InSpec.

I have included the stub in my spec test on line 77 however allow(File).to receive(:exist?).with('/etc/.firstboot_done').and_return(false), I would imagine that’s the only stub required?

Yeah…I was thinking the same thing lol

To be honest.
I’m not super super sure. I personally wouldn’t be using ChefSpec here. As you’re basically testing the Chef-client which has plenty of tests for the package resource.

Instead, if you want to prove that guard works it’d throw up an instance.
And if you’re worried about multiple converges, use the “enforce_idempotency” in kitchen
https://github.com/sous-chefs/apache2/blob/master/kitchen.yml#L5-L10

Got a URL explaining what enforce_idempotency does in the first place (for grasshoppers such as myself)?

Not yet sorry :grimacing:
I’m working on all that documentation as we speak

No worries. Thank you for your help.

From memory, if a.resource fires in the second run, then it fails the kitchen test

Right. Also I realized there was an issue in my code as well:
allow(File).to receive(:exist?).with('/etc/.firstboot_done').and_return(false)
should actually be:
allow(File).to receive(:exist?).with('/etc/.firstboot_done').and_return(true)
Once the change was made, the spec test worked just fine.