0

如何为 ruby​​_block 编写 ChefSpec 单元测试?如果在配方中声明了局部变量怎么办?将如何处理?

这是食谱的代码:

package 'autofs' do
  action :install
end

src = '/etc/ssh/sshd_config'

unless ::File.readlines(src).grep(/^PasswordAuthentication yes/).any?
  Chef::Log.warn "Need to add/change PasswordAuthentication to yes in sshd config."
  ruby_block 'change_sshd_config' do
    block do
      srcfile = Chef::Util::FileEdit.new(src)
      srcfile.search_file_replace(/^PasswordAuthentication no/, "PasswordAuthentication yes")
      srcfile.insert_line_if_no_match(/^PasswordAuthentication/, "PasswordAuthentication yes")
      srcfile.write_file
    end
  end
end

unless ::File.readlines(src).grep('/^Banner /etc/issue.ssh/').any?
  Chef::Log.warn "Need to change Banner setting in sshd config."
  ruby_block 'change_sshd_banner_config' do
    block do
      srcfile = Chef::Util::FileEdit.new(src)
      srcfile.search_file_replace(/^#Banner none/, "Banner /etc/issue.ssh")
      srcfile.insert_line_if_no_match(/^Banner/, "Banner /etc/issue.ssh")
      srcfile.write_file
    end
  end
end

由于我是 ChefSpec 的新手,因此我能够为基本资源编写代码。我编写了单元测试如下:

require 'chefspec'

describe 'package::install' do

  let(:chef_run) { ChefSpec::SoloRunner.new(platform: 'ubuntu', version: '16.04').converge(described_recipe) }

  it 'install a package autofs' do
    expect(chef_run).to install_package('autofs')
  end

  it 'creates a ruby_block with an change_sshd_config' do
    expect(chef_run).to run_ruby_block('change_sshd_config')
  end

  it 'creates a ruby_block with an change_sshd_banner_config' do
    expect(chef_run).to run_ruby_block('change_sshd_banner_config')
  end

end

上述实现是否正确?我无法弄清楚如何为红宝石块等复杂资源编写它。以及如何注意配方中声明的局部变量。提前致谢..

4

2 回答 2

1
 let(:conf) { double('conf') }
    before do
      allow(File).to receive(:readlines).with('/etc/ssh/sshd_config').and_return(["something"])
      allow(File).to receive(:readlines).with('/etc/ssh/sshd_config').and_return(["something"])
end

 it 'creates a ruby_block with an change_sshd_config' do
    expect(chef_run).to run_ruby_block('change_sshd_config')
    expect(Chef::Util::FileEdit).to receive(:new).with('/etc/ssh/sshd_config').and_return(conf)
    confile = Chef::Util::FileEdit.new('/etc/ssh/sshd_config')
  end

对其他红宝石块也做同样的事情!大多数情况下它会起作用。

或者

您可以使用 inspec 进行测试以测试系统的状态。似乎您可能想要测试系统的状态,以了解在 Chef 应用配置后配置 sshd 的方式。您可以使用类似以下代码段的 inspec 来完成此操作:

describe file('/etc/ssh/sshd_config') do
  its('content') { should match /whatever/ }
end

我希望这有帮助!

于 2017-05-23T18:12:38.280 回答
0

单元测试应该测试特定的输入产生预期的输出。通过期望 Chef 拥有run_ruby_block,您实质上是在说“ Chef是否按照我期望的方式工作”——而不是“我的ruby_block资源是否按照我期望的方式工作”。

您应该使用 ChefSpec 来验证 的副作用ruby_block是否符合您的预期。也就是说,文件被修改。RenderFileMatchers上的 ChefSpec 文档可能是您正在寻找的。

于 2017-05-11T14:28:19.493 回答