aye_commander 1.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,25 @@
1
+ describe AyeCommander::MissingRequiredArgumentError do
2
+ let(:error) { AyeCommander::MissingRequiredArgumentError }
3
+
4
+ it 'is an AyeCommander::Error child' do
5
+ expect(error.superclass).to be AyeCommander::Error
6
+ end
7
+
8
+ it 'should have a descriptive message of the error' do
9
+ errori = error.new [:taco]
10
+ expect(errori.message).to eq 'Missing required arguments: [:taco]'
11
+ end
12
+ end
13
+
14
+ describe AyeCommander::UnexpectedReceivedArgumentError do
15
+ let(:error) { AyeCommander::UnexpectedReceivedArgumentError }
16
+
17
+ it 'is an AyeCommander::Error child' do
18
+ expect(error.superclass).to be AyeCommander::Error
19
+ end
20
+
21
+ it 'should have a descriptive message of the error' do
22
+ errori = error.new [:taco]
23
+ expect(errori.message).to eq 'Received unexpected arguments: [:taco]'
24
+ end
25
+ end
@@ -0,0 +1,105 @@
1
+ describe AyeCommander::Hookable::ClassMethods do
2
+ include_context :command
3
+
4
+ %i(before around after aborted).each do |kind|
5
+ context ".#{kind}" do
6
+ it "adds the args to the #{kind} hooks array" do
7
+ command.send kind, :some, :method
8
+ expect(command.send("#{kind}_hooks")).to eq [:some, :method]
9
+ expect(command.instance_variable_get(:@hooks)).to_not be_empty
10
+ expect(command.instance_variable_get(:@hooks).default).to be_empty
11
+ end
12
+
13
+ it 'adds the received block as a block, after the args' do
14
+ command.send(kind, :some) { :hello }
15
+ expect(command.send("#{kind}_hooks").count).to eq 2
16
+ expect(command.send("#{kind}_hooks").last).to be_instance_of Proc
17
+ end
18
+
19
+ it 'adds the args at the end of the array' do
20
+ command.send kind, :first
21
+ command.send kind, :second, :third
22
+ expect(command.send("#{kind}_hooks")).to eq [:first, :second, :third]
23
+ end
24
+
25
+ it 'adds the args at the beginning of the array with the prepend option' do
26
+ command.send kind, :first
27
+ command.send kind, :second, :third, prepend: true
28
+ expect(command.send("#{kind}_hooks")).to eq [:second, :third, :first]
29
+ end
30
+ end
31
+
32
+ context ".#{kind}_hooks" do
33
+ it 'returns empty array with nothing set' do
34
+ expect(command.send("#{kind}_hooks")).to eq []
35
+ end
36
+
37
+ it 'returns the array of hooks' do
38
+ command.instance_variable_set :@hooks, kind => [:hello]
39
+ expect(command.send("#{kind}_hooks")).to eq [:hello]
40
+ end
41
+ end
42
+ end
43
+
44
+ %i(before after aborted).each do |kind|
45
+ context ".call_#{kind}_hooks" do
46
+ before :each do
47
+ body = -> { success? }
48
+ command.send :define_method, :by_symbol, &body
49
+ command.send :define_method, :by_method, &body
50
+ command.send kind, :by_symbol, instance.method(:by_method), body, &body
51
+ end
52
+
53
+ it 'makes all supported hooks callable' do
54
+ expect(command.send("call_#{kind}_hooks", instance)).to all(respond_to :call)
55
+ end
56
+
57
+ it 'calls all the prepared hooks' do
58
+ hooks = command.send "call_#{kind}_hooks", instance
59
+ allow(command).to receive(:prepare_hooks).and_return(hooks)
60
+ expect(hooks).to all(receive(:call))
61
+ command.send "call_#{kind}_hooks", instance
62
+ end
63
+
64
+ it 'runs all the prepared hooks in the instance context' do
65
+ expect(instance).to receive(:success?).exactly(4).times
66
+ command.send "call_#{kind}_hooks", instance
67
+ end
68
+ end
69
+ end
70
+
71
+ context '.call_around_hooks' do
72
+ before :each do
73
+ body = lambda do |step|
74
+ @order ||= []
75
+ number = order.count + 1
76
+ @order << number
77
+
78
+ success?
79
+ step.call
80
+ failure?
81
+
82
+ @order << number
83
+ end
84
+
85
+ command.send :define_method, :by_symbol, &body
86
+ command.send :define_method, :by_method, &body
87
+ command.around :by_symbol, instance.method(:by_method), body, &body
88
+ end
89
+
90
+ it 'compacts everything into one proc' do
91
+ expect(command.call_around_hooks(instance).count).to eq 1
92
+ end
93
+
94
+ it 'calls everything' do
95
+ expect(instance).to receive(:success?).exactly(4).times
96
+ expect(instance).to receive(:failure?).exactly(4).times
97
+ command.call_around_hooks(instance)
98
+ end
99
+
100
+ it 'should call the hooks in the correct order' do
101
+ command.call_around_hooks(instance)
102
+ expect(instance.order).to eq [1, 2, 3, 4, 4, 3, 2, 1]
103
+ end
104
+ end
105
+ end
@@ -0,0 +1,33 @@
1
+ describe AyeCommander::Initializable do
2
+ include_context :command
3
+
4
+ context '#initialize' do
5
+ it 'sets the instance variables with the received arguments' do
6
+ i = command.new(taco: :burrito, dogo: :hungry)
7
+ expect(i.taco).to eq :burrito
8
+ expect(i.dogo).to eq :hungry
9
+ end
10
+
11
+ it 'is able to handle the case when the variable start with @' do
12
+ i = command.new(:@taco => :burrito, :@dogo => :hungry)
13
+ expect(i.taco).to eq :burrito
14
+ expect(i.dogo).to eq :hungry
15
+ end
16
+
17
+ it 'is able to handle the case when no args are received' do
18
+ expect { command.new }.to_not raise_error
19
+ end
20
+
21
+ context 'when a command' do
22
+ it 'sets the status to :success if no other succeed has been set' do
23
+ command.succeeds_with :potato
24
+ expect(instance.status).to eq :success
25
+ end
26
+
27
+ it 'sets the status to the first suceed if success has been excluded' do
28
+ command.succeeds_with :potato, exclude_success: true
29
+ expect(instance.status).to eq :potato
30
+ end
31
+ end
32
+ end
33
+ end
@@ -0,0 +1,45 @@
1
+ describe AyeCommander::Inspectable do
2
+ include_context :command
3
+
4
+ before :each do
5
+ instance.instance_variable_set :@variable, :something
6
+ instance.instance_variable_set :@other, :potato
7
+ end
8
+
9
+ context '#inspect' do
10
+ it 'gives a string representation of the innards of the class' do
11
+ expect(instance.inspect).to match(/#<#<Class:\dx\w+> @status: success, @variable: something, @other: potato>/)
12
+ end
13
+ end
14
+
15
+ context '#to_hash' do
16
+ it 'gives a hash representation of the innards of the class' do
17
+ result = { :@status => :success, :@variable => :something, :@other => :potato }
18
+ expect(instance.to_hash).to eq result
19
+ end
20
+
21
+ it 'gives a hash representation of the innards of the class with the requested values' do
22
+ result = { :@variable => :something, :@other => :potato }
23
+ expect(instance.to_hash([:@variable, :other])).to eq result
24
+ end
25
+ end
26
+
27
+ context '#to_result_hash' do
28
+ it 'gives a hash of all values for the result if no return was specified' do
29
+ result = { :@status => :success, :@variable => :something, :@other => :potato }
30
+ expect(instance.to_result_hash).to eq result
31
+ end
32
+
33
+ it 'gives the necessary values for the result when a return was specified' do
34
+ command.returns :other
35
+ result = { :@status => :success, :@other => :potato }
36
+ expect(instance.to_result_hash).to eq result
37
+ end
38
+
39
+ it 'assigns nil to the values that were not created when a result was specified' do
40
+ command.returns :badger
41
+ result = { :@status => :success, :@badger => nil }
42
+ expect(instance.to_result_hash).to eq result
43
+ end
44
+ end
45
+ end
@@ -0,0 +1,130 @@
1
+ describe AyeCommander::Ivar::ClassMethods do
2
+ include_context :command
3
+
4
+ context '.define_missing_reader' do
5
+ it 'calls uses if its a command' do
6
+ expect(command).to receive(:uses).with(:taco)
7
+ command.define_missing_reader(:taco)
8
+ end
9
+
10
+ it 'defines the attr_reader if its a result' do
11
+ command.result_class.define_missing_reader(:taco)
12
+ expect(result).to respond_to :taco
13
+ expect(result).to_not respond_to :taco=
14
+ end
15
+ end
16
+
17
+ context '.to_ivar' do
18
+ it 'returns itself when the name is already in ivar form' do
19
+ expect(command.to_ivar(:@var)).to eq :@var
20
+ end
21
+
22
+ it 'returns the ivar form when name is not in ivar form' do
23
+ expect(command.to_ivar(:var)).to eq :@var
24
+ end
25
+
26
+ it 'is able to handle strings' do
27
+ expect(command.to_ivar('@var')).to eq :@var
28
+ expect(command.to_ivar('var')).to eq :@var
29
+ end
30
+ end
31
+
32
+ context '.to_nvar' do
33
+ it 'returns itself when name is already in nvar form' do
34
+ expect(command.to_nvar(:var)).to eq :var
35
+ end
36
+
37
+ it 'returns the nvar form when name is not in nvar form' do
38
+ expect(command.to_nvar(:@var)).to eq :var
39
+ end
40
+
41
+ it 'is able to handle strings' do
42
+ expect(command.to_nvar('@var')).to eq :var
43
+ expect(command.to_nvar('var')).to eq :var
44
+ end
45
+ end
46
+ end
47
+
48
+ describe AyeCommander::Ivar::Readable do
49
+ include_context :command
50
+
51
+ context '#method_missing' do
52
+ it 'raises if asked a method without an instance variable defined' do
53
+ expect { instance.taco }.to raise_error NoMethodError
54
+ end
55
+
56
+ it 'responds if asked the name of an instance variable' do
57
+ instance.instance_variable_set :@taco, :badger
58
+ expect(instance.taco).to eq :badger
59
+ end
60
+
61
+ it 'calls .define_missing_reader' do
62
+ expect(command).to receive(:define_missing_reader).with(:taco)
63
+ instance.instance_variable_set :@taco, :badger
64
+ instance.taco
65
+ end
66
+ end
67
+
68
+ context '#remove!' do
69
+ it 'removes an instance variable' do
70
+ instance.remove!(:status)
71
+ expect(instance.instance_variables).to be_empty
72
+ end
73
+ end
74
+
75
+ context '#to_ivar' do
76
+ it 'calls the .to_ivar' do
77
+ instance
78
+ expect(command).to receive(:to_ivar).with(:var)
79
+ instance.to_ivar(:var)
80
+ end
81
+ end
82
+
83
+ context '#to_nvar' do
84
+ it 'calls the .to_nvar' do
85
+ expect(command).to receive(:to_nvar).with(:var)
86
+ instance.to_nvar(:var)
87
+ end
88
+ end
89
+
90
+ context 'p#respond_to_missing?' do
91
+ it 'returns true if the variable name is defined' do
92
+ instance.instance_variable_set :@taco, :badger
93
+ expect(instance.send(:respond_to_missing?, :taco, [false])).to be true
94
+ end
95
+
96
+ it 'uses super if the variable name is not defined' do
97
+ expect(instance.send(:respond_to_missing?, :taco, [false])).to be false
98
+ end
99
+
100
+ it 'uses super if the variable name is not valid' do
101
+ expect(instance.send(:respond_to_missing?, :taco!, [false])).to be false
102
+ end
103
+ end
104
+ end
105
+
106
+ describe AyeCommander::Ivar::Writeable do
107
+ include_context :command
108
+
109
+ context '#method_missing' do
110
+ it 'responds to equality assignments' do
111
+ expect { instance.taco = 1 }.to_not raise_error
112
+ end
113
+
114
+ it 'defines the method so next time it doesnt go through method_missing' do
115
+ instance.taco = 1
116
+ expect(instance).to respond_to :taco
117
+ expect(instance).to respond_to :taco=
118
+ end
119
+ end
120
+
121
+ context 'p#respond_to_missing?' do
122
+ it 'returns true if variable name ends with =' do
123
+ expect(instance.send(:respond_to_missing?, :taco=, [false])).to be true
124
+ end
125
+
126
+ it 'uses super otherwise' do
127
+ expect(instance.send(:respond_to_missing?, :taco, [false])).to be false
128
+ end
129
+ end
130
+ end
@@ -0,0 +1,131 @@
1
+ describe AyeCommander::Limitable::ClassMethods do
2
+ include_context :command
3
+ let(:args) { %i(arg1 arg2) }
4
+
5
+ context '.uses' do
6
+ it 'should call save_variable' do
7
+ command.uses(*args)
8
+ expect(command.uses).to eq args
9
+ end
10
+
11
+ it 'should create accessors for the received values' do
12
+ command.uses(*args)
13
+ args.each do |arg|
14
+ expect(instance).to respond_to arg
15
+ expect(instance).to respond_to "#{arg}="
16
+ end
17
+ end
18
+ end
19
+
20
+ %i(receives requires returns).each do |limiter|
21
+ context ".#{limiter}" do
22
+ before :each do
23
+ command.public_send limiter, *args
24
+ end
25
+
26
+ it 'should call .uses' do
27
+ expect(command).to receive(:uses).with(*args).and_return(true)
28
+ command.public_send limiter, *args
29
+ end
30
+
31
+ it 'should save the values to a class instance variable' do
32
+ expect(command.limiters[limiter]).to eq args
33
+ end
34
+
35
+ it 'should add consecutive values without any problem' do
36
+ command.public_send limiter, :arg3
37
+ expect(command.limiters[limiter]).to eq %i(arg1 arg2 arg3)
38
+ end
39
+
40
+ it 'should not add repeated args' do
41
+ command.public_send limiter, :arg1, :arg4
42
+ expect(command.limiters[limiter]).to eq %i(arg1 arg2 arg4)
43
+ end
44
+ end
45
+ end
46
+
47
+ context '.validate_arguments' do
48
+ let(:args) { { hello: :world, how: :are, you: :! } }
49
+
50
+ it 'calls .validate_required_arguments if it has requires' do
51
+ expect(command).to receive(:validate_required_arguments).and_return(true)
52
+ command.requires :something
53
+ command.validate_arguments args
54
+ end
55
+
56
+ it 'does not call .validate_required_arguments if theres no requires' do
57
+ expect(command).to_not receive(:validate_required_arguments)
58
+ command.validate_arguments args
59
+ end
60
+
61
+ it 'does not call .validate_required_arguments with skip_validations: :requires option' do
62
+ command.requires :something
63
+ expect(command).to_not receive(:validate_required_arguments)
64
+ command.validate_arguments args, skip_validations: :requires
65
+ end
66
+
67
+ it 'calls .validate_received_arguments if it has receives' do
68
+ expect(command).to receive(:validate_received_arguments).and_return(true)
69
+ command.receives :something
70
+ command.validate_arguments args
71
+ end
72
+
73
+ it 'does not call .validate_received_argumnts if theres no receives' do
74
+ expect(command).to_not receive(:validate_received_arguments)
75
+ command.validate_arguments args
76
+ end
77
+
78
+ it 'does not call .validate_receiveed_arguments with skip_validations: :receives option' do
79
+ command.receives :something
80
+ expect(command).to_not receive(:validate_received_arguments)
81
+ command.validate_arguments args, skip_validations: :receives
82
+ end
83
+
84
+ it 'does not call either with skip_validations: true option' do
85
+ command.requires :something
86
+ command.receives :something_else
87
+ expect(command).to_not receive(:validate_received_arguments)
88
+ expect(command).to_not receive(:validate_required_arguments)
89
+
90
+ command.validate_arguments args, skip_validations: true
91
+ end
92
+ end
93
+
94
+ context '.validate_required_arguments' do
95
+ let(:args) { { hello: :world, how: :are, you: :! } }
96
+
97
+ it 'does nothing if the required arguments are contained in the received ones' do
98
+ command.requires :hello, :you
99
+ expect { command.validate_required_arguments args }.to_not raise_error
100
+ end
101
+
102
+ it 'does nothing if it receives extra arguments' do
103
+ command.requires :hello, :you
104
+ expect { command.validate_required_arguments(**args, extra: :arg) }.to_not raise_error
105
+ end
106
+
107
+ it 'raises an error when the required arguments are not fully contained in the received ones' do
108
+ command.requires :hello, :you, :doc
109
+ expect { command.validate_required_arguments args }.to raise_error AyeCommander::MissingRequiredArgumentError
110
+ end
111
+ end
112
+
113
+ context '.validate_received_arguments' do
114
+ let(:args) { { hello: :world, how: :are, you: :! } }
115
+
116
+ it 'does nothing if receives contains all the received arguments' do
117
+ command.receives :hello, :how, :you
118
+ expect { command.validate_received_arguments args }.to_not raise_error
119
+ end
120
+
121
+ it 'does nothing if some of the arguments are missing' do
122
+ command.receives :hello, :how, :you, :potato
123
+ expect { command.validate_received_arguments args }.to_not raise_error
124
+ end
125
+
126
+ it 'raises an error when it receives arguments not contained in the receives array' do
127
+ command.receives :hello, :how, :potato
128
+ expect { command.validate_received_arguments args }.to raise_error AyeCommander::UnexpectedReceivedArgumentError
129
+ end
130
+ end
131
+ end