TDD your shell scripts using RSpec
MIT License
Run your shell script in a mocked environment to test its behaviour using RSpec.
Add this line to your application's Gemfile:
gem 'rspec-shell-expectations'
And then execute:
$ bundle
Or install it yourself as:
$ gem install rspec-shell-expectations
You can setup rspec-shell-expectations globally for your spec suite:
in spec_helper.rb
:
require 'rspec/shell/expectations'
RSpec.configure do |c|
c.include Rspec::Shell::Expectations
end
see specs in spec/
folder:
require 'rspec/shell/expectations'
describe 'my shell script' do
include Rspec::Shell::Expectations
let(:stubbed_env) { create_stubbed_env }
it 'runs the script' do
stdout, stderr, status = stubbed_env.execute(
'my-shell-script.sh',
{ 'SOME_OPTIONAL' => 'env vars' }
)
expect(status.exitstatus).to eq 0
end
end
let(:stubbed_env) { create_stubbed_env }
let!(:bundle) { stubbed_env.stub_command('bundle') }
let(:rake) { bundle.with_args('exec', 'rake') }
it 'is stubbed' do
stubbed_env.execute 'my-script.sh'
expect(rake.with_args('test')).to be_called
expect(bundle.with_args('install)).to be_called
end
let(:stubbed_env) { create_stubbed_env }
before do
stubbed_env.stub_command('rake').returns_exitstatus(5)
stubbed_env.stub_command('rake').with_args('spec').returns_exitstatus(3)
end
let(:stubbed_env) { create_stubbed_env }
let(:rake_stub) { stubbed_env.stub_command 'rake' }
before do
rake_stub.outputs('informative message', to: :stdout)
.outputs('error message', to: :stderr)
.outputs('log contents', to: 'logfile.log')
.outputs('converted result', to: ['prefix-', :arg2, '.txt'])
# last one creates 'prefix-foo.txt' when called as 'rake convert foo'
end
let(:stubbed_env) { create_stubbed_env }
let(:rake_stub) { stubbed_env.stub_command 'rake' }
it 'verifies called' do
stubbed_env.execute_script 'script.sh'
expect(rake_stub).to be_called
expect(rake_stub.with_args('spec')).to be_called
expect(rake_stub.with_args('features')).not_to be_called
end
let(:stubbed_env) { create_stubbed_env }
let(:cat_stub) { stubbed_env.stub_command 'cat' }
let(:mail_stub) { stubbed_env.stub_command 'mail' }
it 'verifies stdin' do
stubbed_env.execute_script 'script.sh'
expect(cat_stub.stdin).to eql 'hello'
expect(mail_stub.with_args('-s', 'hello').stdin).to eql 'world'
end
see the features and spec folder
Ruby 2+, no JRuby, due to issues with Open3.capture3
git checkout -b my-new-feature
)git commit -am 'Add some feature'
)git push origin my-new-feature
)