199 lines
		
	
	
		
			5.2 KiB
		
	
	
	
		
			Ruby
		
	
	
	
	
	
			
		
		
	
	
			199 lines
		
	
	
		
			5.2 KiB
		
	
	
	
		
			Ruby
		
	
	
	
	
	
| require 'spec_helper'
 | |
| 
 | |
| module Producer::Core
 | |
|   describe Condition do
 | |
|     subject(:condition) { described_class.new }
 | |
| 
 | |
|     %w[
 | |
|       `
 | |
|       sh
 | |
|       file_contains
 | |
|       file_eq
 | |
|       file_match
 | |
|       dir?
 | |
|       env?
 | |
|       executable?
 | |
|       file?
 | |
|     ].each do |test|
 | |
|       it "has `#{test}' test defined" do
 | |
|         expect(condition).to respond_to test.to_sym
 | |
|       end
 | |
|     end
 | |
| 
 | |
|     describe '.define_test' do
 | |
|       let(:some_test) { Test }
 | |
| 
 | |
|       before { described_class.define_test(:some_test, some_test) }
 | |
| 
 | |
|       it 'defines a new test keyword' do
 | |
|         expect(condition).to respond_to :some_test
 | |
|       end
 | |
| 
 | |
|       it 'defines the negated test' do
 | |
|         expect(condition).to respond_to :no_some_test
 | |
|       end
 | |
| 
 | |
|       context 'when a test keyword is called' do
 | |
|         it 'registers the test' do
 | |
|           expect { condition.some_test }.to change { condition.tests.count }.by 1
 | |
|         end
 | |
| 
 | |
|         it 'registers the test with assigned env' do
 | |
|           env = double 'env'
 | |
|           condition.instance_eval { @env = env }
 | |
|           condition.some_test
 | |
|           expect(condition.tests.last.env).to be env
 | |
|         end
 | |
| 
 | |
|         it 'registers the test with given arguments' do
 | |
|           condition.some_test :foo, :bar
 | |
|           expect(condition.tests.last.arguments).to eq %i[foo bar]
 | |
|         end
 | |
| 
 | |
|         context 'when given test is callable' do
 | |
|           let(:some_test) { proc { } }
 | |
| 
 | |
|           before { condition.some_test }
 | |
| 
 | |
|           it 'registers a condition test' do
 | |
|             expect(condition.tests.last).to be_a Tests::ConditionTest
 | |
|           end
 | |
| 
 | |
|           it 'registers the test with given block' do
 | |
|             expect(condition.tests.last.condition_block).to be some_test
 | |
|           end
 | |
| 
 | |
|           it 'registers the test with given arguments' do
 | |
|             condition.some_test :foo, :bar
 | |
|             expect(condition.tests.last.condition_args).to eq %i[foo bar]
 | |
|           end
 | |
|         end
 | |
|       end
 | |
| 
 | |
|       context 'when a negated test keyword is called' do
 | |
|         it 'registers a negated test' do
 | |
|           condition.no_some_test
 | |
|           expect(condition.tests.last).to be_negated
 | |
|         end
 | |
|       end
 | |
|     end
 | |
| 
 | |
|     describe '.evaluate' do
 | |
|       let(:env)           { double 'env' }
 | |
|       let(:code)          { proc { some_test; :some_return_value } }
 | |
|       let(:some_test)     { Class.new(Test) }
 | |
|       let(:arguments)     { [] }
 | |
|       subject(:condition) { described_class.evaluate(env, *arguments, &code) }
 | |
| 
 | |
|       before { described_class.define_test(:some_test, some_test) }
 | |
| 
 | |
|       it 'returns an evaluated condition' do
 | |
|         expect(condition).to be_a described_class
 | |
|       end
 | |
| 
 | |
|       it 'evaluates the condition tests' do
 | |
|         expect(condition.tests.first).to be_a Test
 | |
|       end
 | |
| 
 | |
|       it 'evaluates the condition return value' do
 | |
|         expect(condition.return_value).to eq :some_return_value
 | |
|       end
 | |
| 
 | |
|       context 'when arguments are given' do
 | |
|         let(:code)      { proc { |a, b| throw a } }
 | |
|         let(:arguments) { %i[foo bar] }
 | |
| 
 | |
|         it 'passes arguments as block parameters' do
 | |
|           expect { condition }
 | |
|             .to throw_symbol :foo
 | |
|         end
 | |
|       end
 | |
|     end
 | |
| 
 | |
|     describe '#initialize' do
 | |
|       it 'assigns no tests' do
 | |
|         expect(condition.tests).to be_empty
 | |
|       end
 | |
| 
 | |
|       it 'assigns the return value as nil' do
 | |
|         expect(condition.return_value).to be nil
 | |
|       end
 | |
|     end
 | |
| 
 | |
|     describe '#met?' do
 | |
|       let(:test_ok)       { instance_spy Test, pass?: true }
 | |
|       let(:test_ko)       { instance_spy Test, pass?: false }
 | |
|       subject(:condition) { described_class.new(tests) }
 | |
| 
 | |
|       context 'when all tests are successful' do
 | |
|         let(:tests) { [test_ok, test_ok] }
 | |
| 
 | |
|         it 'returns true' do
 | |
|           expect(condition.met?).to be true
 | |
|         end
 | |
|       end
 | |
| 
 | |
|       context 'when one test is unsuccessful' do
 | |
|         let(:tests) { [test_ok, test_ko] }
 | |
| 
 | |
|         it 'returns false' do
 | |
|           expect(condition.met?).to be false
 | |
|         end
 | |
|       end
 | |
| 
 | |
|       context 'when there are no test' do
 | |
|         let(:tests)         { [] }
 | |
|         subject(:condition) { described_class.new([], return_value) }
 | |
| 
 | |
|         context 'and return value is truthy' do
 | |
|           let(:return_value) { :some_truthy_value }
 | |
| 
 | |
|           it 'returns true' do
 | |
|             expect(condition.met?).to be true
 | |
|           end
 | |
|         end
 | |
| 
 | |
|         context 'and return value is falsy' do
 | |
|           let(:return_value) { nil }
 | |
| 
 | |
|           it 'returns false' do
 | |
|             expect(condition.met?).to be false
 | |
|           end
 | |
|         end
 | |
|       end
 | |
|     end
 | |
| 
 | |
|     describe '#!' do
 | |
|       [true, false].each do |b|
 | |
|         context "when #met? return #{b}" do
 | |
|           before { allow(condition).to receive(:met?) { b } }
 | |
| 
 | |
|           it 'returns the negated #met?' do
 | |
|             expect(condition.!).to be !condition.met?
 | |
|           end
 | |
|         end
 | |
|       end
 | |
|     end
 | |
| 
 | |
|     describe '#get' do
 | |
|       let(:env) { Env.new }
 | |
| 
 | |
|       it 'delegates to env registry' do
 | |
|         expect(env).to receive(:get).with :some_key
 | |
|         described_class.evaluate(env, []) { get :some_key }
 | |
|       end
 | |
|     end
 | |
| 
 | |
|     describe '#target' do
 | |
|       let(:env) { Env.new }
 | |
| 
 | |
|       before { env.target = :some_target }
 | |
| 
 | |
|       it 'returns current env target' do
 | |
|         condition = described_class.evaluate(env, []) { target == :some_target }
 | |
|         expect(condition).to be_met
 | |
|       end
 | |
|     end
 | |
|   end
 | |
| end
 |