volute 0.1.0 → 0.1.1
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.
- data/CHANGELOG.txt +19 -1
- data/README.rdoc +333 -76
- data/Rakefile +4 -4
- data/TODO.txt +28 -14
- data/examples/diagnosis.rb +82 -0
- data/examples/equation.rb +1 -1
- data/examples/light.rb +27 -0
- data/examples/state_machine.rb +26 -24
- data/examples/state_machine_2.rb +64 -0
- data/examples/traffic.rb +115 -0
- data/lib/volute.rb +159 -32
- data/spec/apply_spec.rb +52 -0
- data/spec/filter_not_spec.rb +58 -0
- data/spec/{volute_guard_spec.rb → filter_spec.rb} +57 -29
- data/spec/filter_state_spec.rb +179 -0
- data/spec/filter_transitions_spec.rb +200 -0
- data/spec/over_spec.rb +36 -0
- data/spec/spec_helper.rb +6 -0
- data/spec/volute_spec.rb +0 -32
- data/spec/volutes_spec.rb +91 -0
- data/volute.gemspec +31 -11
- metadata +60 -20
@@ -0,0 +1,179 @@
|
|
1
|
+
|
2
|
+
require File.join(File.dirname(__FILE__), 'spec_helper.rb')
|
3
|
+
|
4
|
+
|
5
|
+
describe "a 'state' volute" do
|
6
|
+
|
7
|
+
describe do
|
8
|
+
|
9
|
+
before(:each) do
|
10
|
+
|
11
|
+
@item = Item.new
|
12
|
+
|
13
|
+
Volute.clear!
|
14
|
+
|
15
|
+
volute Item do
|
16
|
+
volute :weight => '1kg', :delivered => true do
|
17
|
+
object.comment = '1kg and delivered'
|
18
|
+
end
|
19
|
+
volute :not, :weight => '1kg' do
|
20
|
+
object.comment = 'not 1kg'
|
21
|
+
end
|
22
|
+
end
|
23
|
+
end
|
24
|
+
|
25
|
+
it 'should trigger for a given state' do
|
26
|
+
|
27
|
+
@item.weight = '1kg'
|
28
|
+
@item.delivered = true
|
29
|
+
|
30
|
+
@item.comment.should == '1kg and delivered'
|
31
|
+
end
|
32
|
+
|
33
|
+
it 'should trigger for a :not state' do
|
34
|
+
|
35
|
+
@item.delivered = true
|
36
|
+
|
37
|
+
@item.comment.should == 'not 1kg'
|
38
|
+
end
|
39
|
+
end
|
40
|
+
|
41
|
+
describe 'with multiple possible values' do
|
42
|
+
|
43
|
+
before(:each) do
|
44
|
+
|
45
|
+
@i0 = Item.new
|
46
|
+
@i1 = Item.new
|
47
|
+
@i2 = Item.new
|
48
|
+
|
49
|
+
Volute.clear!
|
50
|
+
|
51
|
+
volute Item do
|
52
|
+
volute :weight => [ '1kg', '2kg' ], :delivered => true do
|
53
|
+
object.comment = 'delivered an item of 1 or 2 kg'
|
54
|
+
end
|
55
|
+
end
|
56
|
+
end
|
57
|
+
|
58
|
+
it 'should trigger for this or that value' do
|
59
|
+
|
60
|
+
@i0.weight = '1kg'
|
61
|
+
@i0.delivered = true
|
62
|
+
@i1.weight = '2kg'
|
63
|
+
@i1.delivered = true
|
64
|
+
@i2.weight = '3kg'
|
65
|
+
@i2.delivered = true
|
66
|
+
|
67
|
+
@i0.comment.should == 'delivered an item of 1 or 2 kg'
|
68
|
+
@i1.comment.should == 'delivered an item of 1 or 2 kg'
|
69
|
+
@i2.comment.should == nil
|
70
|
+
end
|
71
|
+
|
72
|
+
it 'should trigger for a plain array value' do
|
73
|
+
|
74
|
+
@i0.weight = [ '1kg', '2kg' ]
|
75
|
+
@i0.delivered = true
|
76
|
+
|
77
|
+
@i0.comment.should == 'delivered an item of 1 or 2 kg'
|
78
|
+
end
|
79
|
+
end
|
80
|
+
|
81
|
+
describe 'with a :not_nil value' do
|
82
|
+
|
83
|
+
before(:each) do
|
84
|
+
|
85
|
+
@item = Item.new
|
86
|
+
|
87
|
+
Volute.clear!
|
88
|
+
|
89
|
+
volute Item do
|
90
|
+
volute :weight => '1kg', :delivered => :not_nil do
|
91
|
+
object.comment = 'item of 1kg entered delivery circuit'
|
92
|
+
end
|
93
|
+
end
|
94
|
+
end
|
95
|
+
|
96
|
+
it 'should not trigger when nil' do
|
97
|
+
|
98
|
+
@item.weight = '1kg'
|
99
|
+
|
100
|
+
@item.comment.should == nil
|
101
|
+
end
|
102
|
+
|
103
|
+
it 'should trigger else' do
|
104
|
+
|
105
|
+
@item.weight = '1kg'
|
106
|
+
@item.delivered = false
|
107
|
+
|
108
|
+
@item.comment.should == 'item of 1kg entered delivery circuit'
|
109
|
+
end
|
110
|
+
end
|
111
|
+
|
112
|
+
# Note : not mentioning an attribute has the same effect as using :any,
|
113
|
+
# but when editing in and out, it's easier to change some :any than the
|
114
|
+
# whole ":att => :x" thing
|
115
|
+
#
|
116
|
+
describe 'with an :any value' do
|
117
|
+
|
118
|
+
before(:each) do
|
119
|
+
|
120
|
+
@i0 = Item.new
|
121
|
+
@i1 = Item.new
|
122
|
+
@i2 = Item.new
|
123
|
+
|
124
|
+
Volute.clear!
|
125
|
+
|
126
|
+
volute Item do
|
127
|
+
volute :weight => '1kg', :delivered => :any do
|
128
|
+
object.comment = 'item of 1kg'
|
129
|
+
end
|
130
|
+
end
|
131
|
+
end
|
132
|
+
|
133
|
+
it 'should trigger appropriately' do
|
134
|
+
|
135
|
+
@i0.weight = '1kg'
|
136
|
+
@i1.weight = '1kg'
|
137
|
+
@i2.weight = '2kg'
|
138
|
+
|
139
|
+
#@i0.delivered = nil
|
140
|
+
@i1.delivered = true
|
141
|
+
@i2.delivered = false
|
142
|
+
|
143
|
+
@i0.comment.should == 'item of 1kg'
|
144
|
+
@i1.comment.should == 'item of 1kg'
|
145
|
+
@i2.comment.should == nil
|
146
|
+
end
|
147
|
+
|
148
|
+
it 'should trigger even if delivered is set' do
|
149
|
+
end
|
150
|
+
end
|
151
|
+
|
152
|
+
describe 'with :attribute => /regex/' do
|
153
|
+
|
154
|
+
before(:each) do
|
155
|
+
|
156
|
+
@p0 = Package.new
|
157
|
+
@p1 = Package.new
|
158
|
+
@p2 = Package.new
|
159
|
+
|
160
|
+
Volute.clear!
|
161
|
+
|
162
|
+
volute :location => /^Fort .+$/ do
|
163
|
+
object.comment = 'located in some fort'
|
164
|
+
end
|
165
|
+
end
|
166
|
+
|
167
|
+
it 'should match appropriately' do
|
168
|
+
|
169
|
+
@p0.location = 'Fort Alamo'
|
170
|
+
@p1.location = 'Fort Worth'
|
171
|
+
@p2.location = 'Fortalezza'
|
172
|
+
|
173
|
+
@p0.comment.should == 'located in some fort'
|
174
|
+
@p1.comment.should == 'located in some fort'
|
175
|
+
@p2.comment.should == nil
|
176
|
+
end
|
177
|
+
end
|
178
|
+
end
|
179
|
+
|
@@ -0,0 +1,200 @@
|
|
1
|
+
|
2
|
+
require File.join(File.dirname(__FILE__), 'spec_helper.rb')
|
3
|
+
|
4
|
+
|
5
|
+
describe 'transition volutes' do
|
6
|
+
|
7
|
+
describe 'from that value to this value' do
|
8
|
+
|
9
|
+
before(:each) do
|
10
|
+
|
11
|
+
Volute.clear!
|
12
|
+
|
13
|
+
@package = Package.new
|
14
|
+
@package.vset(:location, 'NRT')
|
15
|
+
|
16
|
+
volute :location do
|
17
|
+
volute :any => 'SFO' do
|
18
|
+
object.comment = 'reached SFO'
|
19
|
+
end
|
20
|
+
end
|
21
|
+
volute :location do
|
22
|
+
volute 'NRT' => 'SFO' do
|
23
|
+
object.comment = 'reached SFO from NRT'
|
24
|
+
end
|
25
|
+
end
|
26
|
+
volute 'NRT' => 'FCO' do
|
27
|
+
object.comment = 'reached FCO from NRT'
|
28
|
+
end
|
29
|
+
volute 'GVA' => :any do
|
30
|
+
object.comment = 'left GVA'
|
31
|
+
end
|
32
|
+
end
|
33
|
+
|
34
|
+
it 'should not trigger when not specified' do
|
35
|
+
|
36
|
+
@package.location = 'ZRH'
|
37
|
+
|
38
|
+
@package.comment.should == nil
|
39
|
+
end
|
40
|
+
|
41
|
+
it 'should trigger for an end state' do
|
42
|
+
|
43
|
+
@package.vset(:location, 'ZRH')
|
44
|
+
@package.location = 'SFO'
|
45
|
+
|
46
|
+
@package.comment.should == 'reached SFO'
|
47
|
+
end
|
48
|
+
|
49
|
+
it 'should trigger for an attribute, a start state and an end state' do
|
50
|
+
|
51
|
+
@package.location = 'SFO'
|
52
|
+
|
53
|
+
@package.comment.should == 'reached SFO from NRT'
|
54
|
+
end
|
55
|
+
|
56
|
+
it 'should trigger for a start state and an end state' do
|
57
|
+
|
58
|
+
@package.location = 'FCO'
|
59
|
+
|
60
|
+
@package.comment.should == 'reached FCO from NRT'
|
61
|
+
end
|
62
|
+
|
63
|
+
it 'should trigger for a start state' do
|
64
|
+
|
65
|
+
@package.vset(:location, 'GVA')
|
66
|
+
@package.location = 'CAL'
|
67
|
+
|
68
|
+
@package.comment.should == 'left GVA'
|
69
|
+
end
|
70
|
+
end
|
71
|
+
|
72
|
+
describe 'with this or that transition' do
|
73
|
+
|
74
|
+
before(:each) do
|
75
|
+
|
76
|
+
Volute.clear!
|
77
|
+
|
78
|
+
volute :location do
|
79
|
+
volute :any => 'SFO', 'SFO' => 'GVA' do
|
80
|
+
object.comment = 'reached SFO or GVA from SFO'
|
81
|
+
end
|
82
|
+
end
|
83
|
+
end
|
84
|
+
|
85
|
+
it 'should trigger appropriately' do
|
86
|
+
|
87
|
+
p0 = Package.new
|
88
|
+
p1 = Package.new
|
89
|
+
p2 = Package.new
|
90
|
+
|
91
|
+
p0.location = 'SFO'
|
92
|
+
p1.location = 'SFO'
|
93
|
+
p1.location = 'GVA'
|
94
|
+
p2.location = 'NRT'
|
95
|
+
|
96
|
+
p0.comment.should == 'reached SFO or GVA from SFO'
|
97
|
+
p1.comment.should == 'reached SFO or GVA from SFO'
|
98
|
+
p2.comment.should == nil
|
99
|
+
end
|
100
|
+
end
|
101
|
+
|
102
|
+
describe 'with multiple start or end values' do
|
103
|
+
|
104
|
+
before(:each) do
|
105
|
+
|
106
|
+
Volute.clear!
|
107
|
+
|
108
|
+
volute :location do
|
109
|
+
volute :any => [ 'ZRH', 'FRA' ] do
|
110
|
+
object.comment = 'reached ZRH or FRA'
|
111
|
+
end
|
112
|
+
volute [ 'NRT', 'SHA' ] => :any do
|
113
|
+
object.comment = 'left NRT or SHA'
|
114
|
+
end
|
115
|
+
end
|
116
|
+
end
|
117
|
+
|
118
|
+
it 'should trigger for this or that new (current) value' do
|
119
|
+
|
120
|
+
p0 = Package.new
|
121
|
+
p1 = Package.new
|
122
|
+
p2 = Package.new
|
123
|
+
|
124
|
+
p0.location = 'ZRH'
|
125
|
+
p1.location = 'FRA'
|
126
|
+
p2.location = 'NRT'
|
127
|
+
|
128
|
+
p0.comment.should == 'reached ZRH or FRA'
|
129
|
+
p1.comment.should == 'reached ZRH or FRA'
|
130
|
+
p2.comment.should == nil
|
131
|
+
end
|
132
|
+
|
133
|
+
it 'should trigger for this or that previous value' do
|
134
|
+
|
135
|
+
p0 = Package.new
|
136
|
+
p1 = Package.new
|
137
|
+
p2 = Package.new
|
138
|
+
|
139
|
+
p0.vset(:location, 'NRT')
|
140
|
+
p1.vset(:location, 'SHA')
|
141
|
+
p2.vset(:location, 'FRA')
|
142
|
+
|
143
|
+
p0.location = 'CDG'
|
144
|
+
p1.location = 'CDG'
|
145
|
+
p2.location = 'CDG'
|
146
|
+
|
147
|
+
p0.comment.should == 'left NRT or SHA'
|
148
|
+
p1.comment.should == 'left NRT or SHA'
|
149
|
+
p2.comment.should == nil
|
150
|
+
end
|
151
|
+
end
|
152
|
+
|
153
|
+
describe 'with /regex/' do
|
154
|
+
|
155
|
+
before(:each) do
|
156
|
+
|
157
|
+
Volute.clear!
|
158
|
+
|
159
|
+
@p0 = Package.new
|
160
|
+
@p1 = Package.new
|
161
|
+
@p2 = Package.new
|
162
|
+
|
163
|
+
volute :location do
|
164
|
+
volute :any => /^S..$/ do
|
165
|
+
object.comment = 'reached S..'
|
166
|
+
end
|
167
|
+
volute /^F..$/ => :any do
|
168
|
+
object.comment = 'left F..'
|
169
|
+
end
|
170
|
+
end
|
171
|
+
end
|
172
|
+
|
173
|
+
it 'should trigger appropriately for end values' do
|
174
|
+
|
175
|
+
@p0.location = 'SHA'
|
176
|
+
@p1.location = 'SFO'
|
177
|
+
@p2.location = 'FRA'
|
178
|
+
|
179
|
+
@p0.comment.should == 'reached S..'
|
180
|
+
@p1.comment.should == 'reached S..'
|
181
|
+
@p2.comment.should == nil
|
182
|
+
end
|
183
|
+
|
184
|
+
it 'should trigger appropriately for start values' do
|
185
|
+
|
186
|
+
@p0.location = 'FRA'
|
187
|
+
@p1.location = 'FDH'
|
188
|
+
@p2.location = 'ZRH'
|
189
|
+
|
190
|
+
@p0.location = 'VEE'
|
191
|
+
@p1.location = 'VIC'
|
192
|
+
@p2.location = 'GVA'
|
193
|
+
|
194
|
+
@p0.comment.should == 'left F..'
|
195
|
+
@p1.comment.should == 'left F..'
|
196
|
+
@p2.comment.should == nil
|
197
|
+
end
|
198
|
+
end
|
199
|
+
end
|
200
|
+
|
data/spec/over_spec.rb
ADDED
@@ -0,0 +1,36 @@
|
|
1
|
+
|
2
|
+
require File.join(File.dirname(__FILE__), 'spec_helper.rb')
|
3
|
+
|
4
|
+
|
5
|
+
describe 'a volute with an over' do
|
6
|
+
|
7
|
+
before(:each) do
|
8
|
+
|
9
|
+
Volute.clear!
|
10
|
+
|
11
|
+
@package = Package.new
|
12
|
+
|
13
|
+
volute Package do
|
14
|
+
volute do
|
15
|
+
over if object.delivered
|
16
|
+
end
|
17
|
+
volute :location do
|
18
|
+
(object.comment ||= []) << value
|
19
|
+
end
|
20
|
+
end
|
21
|
+
end
|
22
|
+
|
23
|
+
it 'should prevent evaluation of further volutes' do
|
24
|
+
|
25
|
+
@package.location = 'ZRH'
|
26
|
+
@package.location = 'CDG'
|
27
|
+
|
28
|
+
@package.comment.should == %w[ ZRH CDG ]
|
29
|
+
|
30
|
+
@package.delivered = true
|
31
|
+
@package.location = 'FCO'
|
32
|
+
|
33
|
+
@package.comment.should == %w[ ZRH CDG ]
|
34
|
+
end
|
35
|
+
end
|
36
|
+
|
data/spec/spec_helper.rb
CHANGED
@@ -7,16 +7,22 @@ class Invoice
|
|
7
7
|
include Volute
|
8
8
|
|
9
9
|
attr_accessor :paid
|
10
|
+
attr_accessor :customer_name
|
11
|
+
attr_accessor :customer_id
|
10
12
|
o_attr_accessor :comment
|
11
13
|
end
|
12
14
|
|
13
15
|
class Item
|
14
16
|
include Volute
|
15
17
|
|
18
|
+
attr_accessor :weight
|
16
19
|
attr_accessor :delivered
|
17
20
|
o_attr_accessor :comment
|
18
21
|
end
|
19
22
|
|
23
|
+
class HeavyItem < Item
|
24
|
+
end
|
25
|
+
|
20
26
|
class Package
|
21
27
|
include Volute
|
22
28
|
|
data/spec/volute_spec.rb
CHANGED
@@ -63,35 +63,3 @@ describe 'a class without a volute' do
|
|
63
63
|
end
|
64
64
|
end
|
65
65
|
|
66
|
-
describe 'a volute with an over' do
|
67
|
-
|
68
|
-
before(:each) do
|
69
|
-
|
70
|
-
Volute.clear!
|
71
|
-
|
72
|
-
@package = Package.new
|
73
|
-
|
74
|
-
volute Package do
|
75
|
-
volute do
|
76
|
-
over if object.delivered
|
77
|
-
end
|
78
|
-
volute :location do
|
79
|
-
(object.comment ||= []) << value
|
80
|
-
end
|
81
|
-
end
|
82
|
-
end
|
83
|
-
|
84
|
-
it 'should prevent evaluation of further volutes' do
|
85
|
-
|
86
|
-
@package.location = 'ZRH'
|
87
|
-
@package.location = 'CDG'
|
88
|
-
|
89
|
-
@package.comment.should == %w[ ZRH CDG ]
|
90
|
-
|
91
|
-
@package.delivered = true
|
92
|
-
@package.location = 'FCO'
|
93
|
-
|
94
|
-
@package.comment.should == %w[ ZRH CDG ]
|
95
|
-
end
|
96
|
-
end
|
97
|
-
|