enum_state_machine 0.0.1 → 0.0.2

Sign up to get free protection for your applications and to get access to all the features.
Files changed (72) hide show
  1. checksums.yaml +4 -4
  2. data/.gitignore +12 -0
  3. data/.ruby-gemset +1 -0
  4. data/.ruby-version +1 -0
  5. metadata +83 -130
  6. data/.rvmrc +0 -1
  7. data/enum_state_machine.gemspec +0 -25
  8. data/lib/enum_state_machine.rb +0 -9
  9. data/lib/enum_state_machine/assertions.rb +0 -36
  10. data/lib/enum_state_machine/branch.rb +0 -225
  11. data/lib/enum_state_machine/callback.rb +0 -232
  12. data/lib/enum_state_machine/core.rb +0 -12
  13. data/lib/enum_state_machine/core_ext.rb +0 -2
  14. data/lib/enum_state_machine/core_ext/class/state_machine.rb +0 -5
  15. data/lib/enum_state_machine/error.rb +0 -13
  16. data/lib/enum_state_machine/eval_helpers.rb +0 -87
  17. data/lib/enum_state_machine/event.rb +0 -257
  18. data/lib/enum_state_machine/event_collection.rb +0 -141
  19. data/lib/enum_state_machine/extensions.rb +0 -149
  20. data/lib/enum_state_machine/graph.rb +0 -92
  21. data/lib/enum_state_machine/helper_module.rb +0 -17
  22. data/lib/enum_state_machine/initializers.rb +0 -4
  23. data/lib/enum_state_machine/initializers/rails.rb +0 -22
  24. data/lib/enum_state_machine/integrations.rb +0 -97
  25. data/lib/enum_state_machine/integrations/active_model.rb +0 -585
  26. data/lib/enum_state_machine/integrations/active_model/locale.rb +0 -11
  27. data/lib/enum_state_machine/integrations/active_model/observer.rb +0 -33
  28. data/lib/enum_state_machine/integrations/active_model/observer_update.rb +0 -42
  29. data/lib/enum_state_machine/integrations/active_model/versions.rb +0 -31
  30. data/lib/enum_state_machine/integrations/active_record.rb +0 -548
  31. data/lib/enum_state_machine/integrations/active_record/locale.rb +0 -20
  32. data/lib/enum_state_machine/integrations/active_record/versions.rb +0 -123
  33. data/lib/enum_state_machine/integrations/base.rb +0 -100
  34. data/lib/enum_state_machine/machine.rb +0 -2292
  35. data/lib/enum_state_machine/machine_collection.rb +0 -86
  36. data/lib/enum_state_machine/macro_methods.rb +0 -518
  37. data/lib/enum_state_machine/matcher.rb +0 -123
  38. data/lib/enum_state_machine/matcher_helpers.rb +0 -54
  39. data/lib/enum_state_machine/node_collection.rb +0 -222
  40. data/lib/enum_state_machine/path.rb +0 -120
  41. data/lib/enum_state_machine/path_collection.rb +0 -90
  42. data/lib/enum_state_machine/state.rb +0 -297
  43. data/lib/enum_state_machine/state_collection.rb +0 -112
  44. data/lib/enum_state_machine/state_context.rb +0 -138
  45. data/lib/enum_state_machine/state_enum.rb +0 -23
  46. data/lib/enum_state_machine/transition.rb +0 -470
  47. data/lib/enum_state_machine/transition_collection.rb +0 -245
  48. data/lib/enum_state_machine/version.rb +0 -3
  49. data/lib/enum_state_machine/yard.rb +0 -8
  50. data/lib/enum_state_machine/yard/handlers.rb +0 -12
  51. data/lib/enum_state_machine/yard/handlers/base.rb +0 -32
  52. data/lib/enum_state_machine/yard/handlers/event.rb +0 -25
  53. data/lib/enum_state_machine/yard/handlers/machine.rb +0 -344
  54. data/lib/enum_state_machine/yard/handlers/state.rb +0 -25
  55. data/lib/enum_state_machine/yard/handlers/transition.rb +0 -47
  56. data/lib/enum_state_machine/yard/templates.rb +0 -3
  57. data/lib/enum_state_machine/yard/templates/default/class/html/setup.rb +0 -30
  58. data/lib/enum_state_machine/yard/templates/default/class/html/state_machines.erb +0 -12
  59. data/lib/tasks/enum_state_machine.rake +0 -1
  60. data/lib/tasks/enum_state_machine.rb +0 -24
  61. data/lib/yard-enum_state_machine.rb +0 -2
  62. data/test/functional/state_machine_test.rb +0 -1066
  63. data/test/unit/integrations/active_model_test.rb +0 -1245
  64. data/test/unit/integrations/active_record_test.rb +0 -2551
  65. data/test/unit/integrations/base_test.rb +0 -104
  66. data/test/unit/integrations_test.rb +0 -71
  67. data/test/unit/invalid_event_test.rb +0 -20
  68. data/test/unit/invalid_parallel_transition_test.rb +0 -18
  69. data/test/unit/invalid_transition_test.rb +0 -115
  70. data/test/unit/machine_collection_test.rb +0 -603
  71. data/test/unit/machine_test.rb +0 -3395
  72. data/test/unit/state_machine_test.rb +0 -31
@@ -1,25 +0,0 @@
1
- module EnumStateMachine
2
- module YARD
3
- module Handlers
4
- # Handles and processes #state
5
- class State < Base
6
- handles method_call(:state)
7
-
8
- def process
9
- if owner.is_a?(EnumStateMachine::Machine)
10
- handler = self
11
- statement = self.statement
12
- names = extract_node_names(statement.parameters(false))
13
-
14
- names.each do |name|
15
- owner.state(name) do
16
- # Parse the block
17
- handler.parse_block(statement.last.last, :owner => self)
18
- end
19
- end
20
- end
21
- end
22
- end
23
- end
24
- end
25
- end
@@ -1,47 +0,0 @@
1
- module EnumStateMachine
2
- module YARD
3
- module Handlers
4
- # Handles and processes #transition
5
- class Transition < Base
6
- handles method_call(:transition)
7
-
8
- def process
9
- if [EnumStateMachine::Machine, EnumStateMachine::Event, EnumStateMachine::State].include?(owner.class)
10
- options = {}
11
-
12
- # Extract requirements
13
- ast = statement.parameters.first
14
- ast.children.each do |assoc|
15
- # Skip conditionals
16
- next if %w(if unless).include?(assoc[0].jump(:ident).source)
17
-
18
- options[extract_requirement(assoc[0])] = extract_requirement(assoc[1])
19
- end
20
-
21
- owner.transition(options)
22
- end
23
- end
24
-
25
- private
26
- # Extracts the statement requirement from the given node
27
- def extract_requirement(ast)
28
- case ast.type
29
- when :symbol_literal, :string_literal, :array
30
- extract_node_names(ast, false)
31
- when :binary
32
- AllMatcher.instance - extract_node_names(ast.children.last)
33
- when :var_ref, :vcall
34
- case ast.source
35
- when 'nil'
36
- nil
37
- when 'same'
38
- LoopbackMatcher.instance
39
- else
40
- AllMatcher.instance
41
- end
42
- end
43
- end
44
- end
45
- end
46
- end
47
- end
@@ -1,3 +0,0 @@
1
- require 'yard'
2
-
3
- YARD::Templates::Engine.register_template_path File.expand_path(File.join(File.dirname(__FILE__), 'templates'))
@@ -1,30 +0,0 @@
1
- require 'tempfile'
2
-
3
- # Define where state machine descriptions will be rendered
4
- def init
5
- super
6
- sections.place(:state_machine_details).before(:children)
7
- end
8
-
9
- # Renders state machine details in the main content of the class's documentation
10
- def state_machine_details
11
- erb(:state_machines) if state_machines
12
- end
13
-
14
- # Gets a list of state machines prased for this class
15
- def state_machines
16
- @state_machines ||= begin
17
- if state_machines = object['state_machines']
18
- state_machines.each do |name, machine|
19
- serializer.serialize(state_machine_image_path(machine), machine[:image]) if machine[:image]
20
- end
21
- end
22
- end
23
- end
24
-
25
- # Generates the image path for the given machine's visualization
26
- def state_machine_image_path(machine)
27
- base_path = File.dirname(serializer.serialized_path(object))
28
- image_name = "#{object.name}_#{machine[:name]}"
29
- "#{File.join(base_path, image_name)}.png"
30
- end
@@ -1,12 +0,0 @@
1
- <h2>State Machines</h2>
2
-
3
- This class contains <%= state_machines.count %> state machine(s).
4
-
5
- <% state_machines.each do |name, machine| %>
6
- <h3><%= h(machine[:name]) %></h3>
7
- <p><%= h(machine[:description]) %></p>
8
-
9
- <% if machine[:image] %>
10
- <img alt="State machine diagram for <%= h(machine[:name]) %>" src="<%= url_for(state_machine_image_path(machine)) %>" />
11
- <% end %>
12
- <% end %>
@@ -1 +0,0 @@
1
- require File.join("#{File.dirname(__FILE__)}/enum_state_machine")
@@ -1,24 +0,0 @@
1
- namespace :enum_state_machine do
2
- desc 'Draws state machines using GraphViz (options: CLASS=User,Vehicle; FILE=user.rb,vehicle.rb [not required in Rails]; FONT=Arial; FORMAT=png; ORIENTATION=portrait; HUMAN_NAMES=true'
3
- task :draw do
4
- # Build drawing options
5
- options = {}
6
- options[:file] = ENV['FILE'] if ENV['FILE']
7
- options[:path] = ENV['TARGET'] if ENV['TARGET']
8
- options[:format] = ENV['FORMAT'] if ENV['FORMAT']
9
- options[:font] = ENV['FONT'] if ENV['FONT']
10
- options[:orientation] = ENV['ORIENTATION'] if ENV['ORIENTATION']
11
- options[:human_names] = ENV['HUMAN_NAMES'] == 'true' if ENV['HUMAN_NAMES']
12
-
13
- if defined?(Rails)
14
- puts "Files are automatically loaded in Rails; ignoring FILE option" if options.delete(:file)
15
- Rake::Task['environment'].invoke
16
- else
17
- # Load the library
18
- $:.unshift(File.dirname(__FILE__) + '/..')
19
- require 'enum_state_machine'
20
- end
21
-
22
- EnumStateMachine::Machine.draw(ENV['CLASS'], options)
23
- end
24
- end
@@ -1,2 +0,0 @@
1
- require 'enum_state_machine/core'
2
- require 'enum_state_machine/yard'
@@ -1,1066 +0,0 @@
1
- require File.expand_path(File.dirname(__FILE__) + '/../test_helper')
2
-
3
- class AutoShop
4
- attr_accessor :num_customers
5
-
6
- def initialize
7
- @num_customers = 0
8
- super
9
- end
10
-
11
- state_machine :initial => :available do
12
- after_transition :available => any, :do => :increment_customers
13
- after_transition :busy => any, :do => :decrement_customers
14
-
15
- event :tow_vehicle do
16
- transition :available => :busy
17
- end
18
-
19
- event :fix_vehicle do
20
- transition :busy => :available
21
- end
22
- end
23
-
24
- # Increments the number of customers in service
25
- def increment_customers
26
- self.num_customers += 1
27
- end
28
-
29
- # Decrements the number of customers in service
30
- def decrement_customers
31
- self.num_customers -= 1
32
- end
33
- end
34
-
35
- class ModelBase
36
- def save
37
- @saved = true
38
- self
39
- end
40
- end
41
-
42
- class Vehicle < ModelBase
43
- attr_accessor :auto_shop, :seatbelt_on, :insurance_premium, :force_idle, :callbacks, :saved, :time_elapsed, :last_transition_args
44
-
45
- def initialize(attributes = {})
46
- attributes = {
47
- :auto_shop => AutoShop.new,
48
- :seatbelt_on => false,
49
- :insurance_premium => 50,
50
- :force_idle => false,
51
- :callbacks => [],
52
- :saved => false
53
- }.merge(attributes)
54
-
55
- attributes.each {|attr, value| send("#{attr}=", value)}
56
- super()
57
- end
58
-
59
- # Defines the state machine for the state of the vehicled
60
- state_machine :initial => lambda {|vehicle| vehicle.force_idle ? :idling : :parked}, :action => :save do
61
- before_transition {|vehicle, transition| vehicle.last_transition_args = transition.args}
62
- before_transition :parked => any, :do => :put_on_seatbelt
63
- before_transition any => :stalled, :do => :increase_insurance_premium
64
- after_transition any => :parked, :do => lambda {|vehicle| vehicle.seatbelt_on = false}
65
- after_transition :on => :crash, :do => :tow
66
- after_transition :on => :repair, :do => :fix
67
-
68
- # Callback tracking for initial state callbacks
69
- after_transition any => :parked, :do => lambda {|vehicle| vehicle.callbacks << 'before_enter_parked'}
70
- before_transition any => :idling, :do => lambda {|vehicle| vehicle.callbacks << 'before_enter_idling'}
71
-
72
- around_transition do |vehicle, transition, block|
73
- time = Time.now
74
- block.call
75
- vehicle.time_elapsed = Time.now - time
76
- end
77
-
78
- event all do
79
- transition :locked => :parked
80
- end
81
-
82
- event :park do
83
- transition [:idling, :first_gear] => :parked
84
- end
85
-
86
- event :ignite do
87
- transition :stalled => :stalled
88
- transition :parked => :idling
89
- end
90
-
91
- event :idle do
92
- transition :first_gear => :idling
93
- end
94
-
95
- event :shift_up do
96
- transition :idling => :first_gear, :first_gear => :second_gear, :second_gear => :third_gear
97
- end
98
-
99
- event :shift_down do
100
- transition :third_gear => :second_gear
101
- transition :second_gear => :first_gear
102
- end
103
-
104
- event :crash do
105
- transition [:first_gear, :second_gear, :third_gear] => :stalled, :if => lambda {|vehicle| vehicle.auto_shop.available?}
106
- end
107
-
108
- event :repair do
109
- transition :stalled => :parked, :if => :auto_shop_busy?
110
- end
111
- end
112
-
113
- state_machine :insurance_state, :initial => :inactive, :namespace => 'insurance' do
114
- event :buy do
115
- transition :inactive => :active
116
- end
117
-
118
- event :cancel do
119
- transition :active => :inactive
120
- end
121
- end
122
-
123
- def save
124
- super
125
- end
126
-
127
- def new_record?
128
- @saved == false
129
- end
130
-
131
- def park
132
- super
133
- end
134
-
135
- # Tows the vehicle to the auto shop
136
- def tow
137
- auto_shop.tow_vehicle
138
- end
139
-
140
- # Fixes the vehicle; it will no longer be in the auto shop
141
- def fix
142
- auto_shop.fix_vehicle
143
- end
144
-
145
- def decibels
146
- 0.0
147
- end
148
-
149
- private
150
- # Safety first! Puts on our seatbelt
151
- def put_on_seatbelt
152
- self.seatbelt_on = true
153
- end
154
-
155
- # We crashed! Increase the insurance premium on the vehicle
156
- def increase_insurance_premium
157
- self.insurance_premium += 100
158
- end
159
-
160
- # Is the auto shop currently servicing another customer?
161
- def auto_shop_busy?
162
- auto_shop.busy?
163
- end
164
- end
165
-
166
- class Car < Vehicle
167
- state_machine do
168
- event :reverse do
169
- transition [:parked, :idling, :first_gear] => :backing_up
170
- end
171
-
172
- event :park do
173
- transition :backing_up => :parked
174
- end
175
-
176
- event :idle do
177
- transition :backing_up => :idling
178
- end
179
-
180
- event :shift_up do
181
- transition :backing_up => :first_gear
182
- end
183
- end
184
- end
185
-
186
- class Motorcycle < Vehicle
187
- state_machine :initial => :idling do
188
- state :first_gear do
189
- def decibels
190
- 1.0
191
- end
192
- end
193
- end
194
- end
195
-
196
- class TrafficLight
197
- state_machine :initial => :stop do
198
- event :cycle do
199
- transition :stop => :proceed, :proceed => :caution, :caution => :stop
200
- end
201
-
202
- state :stop do
203
- def color(transform)
204
- value = 'red'
205
-
206
- if block_given?
207
- yield value
208
- else
209
- value.send(transform)
210
- end
211
-
212
- value
213
- end
214
- end
215
-
216
- state all - :proceed do
217
- def capture_violations?
218
- true
219
- end
220
- end
221
-
222
- state :proceed do
223
- def color(transform)
224
- 'green'
225
- end
226
-
227
- def capture_violations?
228
- false
229
- end
230
- end
231
-
232
- state :caution do
233
- def color(transform)
234
- 'yellow'
235
- end
236
- end
237
- end
238
-
239
- def color(transform = :to_s)
240
- super
241
- end
242
- end
243
-
244
- class VehicleTest < Test::Unit::TestCase
245
- def setup
246
- @vehicle = Vehicle.new
247
- end
248
-
249
- def test_should_not_allow_access_to_subclass_events
250
- assert !@vehicle.respond_to?(:reverse)
251
- end
252
-
253
- def test_should_have_human_state_names
254
- assert_equal 'parked', Vehicle.human_state_name(:parked)
255
- end
256
-
257
- def test_should_have_human_state_event_names
258
- assert_equal 'park', Vehicle.human_state_event_name(:park)
259
- end
260
- end
261
-
262
- class VehicleUnsavedTest < Test::Unit::TestCase
263
- def setup
264
- @vehicle = Vehicle.new
265
- end
266
-
267
- def test_should_be_in_parked_state
268
- assert_equal 'parked', @vehicle.state
269
- end
270
-
271
- def test_should_raise_exception_if_checking_invalid_state
272
- assert_raise(IndexError) { @vehicle.state?(:invalid) }
273
- end
274
-
275
- def test_should_raise_exception_if_getting_name_of_invalid_state
276
- @vehicle.state = 'invalid'
277
- assert_raise(ArgumentError) { @vehicle.state_name }
278
- end
279
-
280
- def test_should_be_parked
281
- assert @vehicle.parked?
282
- assert @vehicle.state?(:parked)
283
- assert_equal :parked, @vehicle.state_name
284
- assert_equal 'parked', @vehicle.human_state_name
285
- end
286
-
287
- def test_should_not_be_idling
288
- assert !@vehicle.idling?
289
- end
290
-
291
- def test_should_not_be_first_gear
292
- assert !@vehicle.first_gear?
293
- end
294
-
295
- def test_should_not_be_second_gear
296
- assert !@vehicle.second_gear?
297
- end
298
-
299
- def test_should_not_be_stalled
300
- assert !@vehicle.stalled?
301
- end
302
-
303
- def test_should_not_be_able_to_park
304
- assert !@vehicle.can_park?
305
- end
306
-
307
- def test_should_not_have_a_transition_for_park
308
- assert_nil @vehicle.park_transition
309
- end
310
-
311
- def test_should_not_allow_park
312
- assert !@vehicle.park
313
- end
314
-
315
- def test_should_be_able_to_ignite
316
- assert @vehicle.can_ignite?
317
- end
318
-
319
- def test_should_have_a_transition_for_ignite
320
- transition = @vehicle.ignite_transition
321
- assert_not_nil transition
322
- assert_equal 'parked', transition.from
323
- assert_equal 'idling', transition.to
324
- assert_equal :ignite, transition.event
325
- assert_equal :state, transition.attribute
326
- assert_equal @vehicle, transition.object
327
- end
328
-
329
- def test_should_have_a_list_of_possible_events
330
- assert_equal [:ignite], @vehicle.state_events
331
- end
332
-
333
- def test_should_have_a_list_of_possible_transitions
334
- assert_equal [{:object => @vehicle, :attribute => :state, :event => :ignite, :from => 'parked', :to => 'idling'}], @vehicle.state_transitions.map {|transition| transition.attributes}
335
- end
336
-
337
- def test_should_have_a_list_of_possible_paths
338
- assert_equal [[
339
- EnumStateMachine::Transition.new(@vehicle, Vehicle.state_machine, :ignite, :parked, :idling),
340
- EnumStateMachine::Transition.new(@vehicle, Vehicle.state_machine, :shift_up, :idling, :first_gear)
341
- ]], @vehicle.state_paths(:to => :first_gear)
342
- end
343
-
344
- def test_should_allow_generic_event_to_fire
345
- assert @vehicle.fire_state_event(:ignite)
346
- assert_equal 'idling', @vehicle.state
347
- end
348
-
349
- def test_should_pass_arguments_through_to_generic_event_runner
350
- @vehicle.fire_state_event(:ignite, 1, 2, 3)
351
- assert_equal [1, 2, 3], @vehicle.last_transition_args
352
- end
353
-
354
- def test_should_allow_skipping_action_through_generic_event_runner
355
- @vehicle.fire_state_event(:ignite, false)
356
- assert_equal false, @vehicle.saved
357
- end
358
-
359
- def test_should_raise_error_with_invalid_event_through_generic_event_runer
360
- assert_raise(IndexError) { @vehicle.fire_state_event(:invalid) }
361
- end
362
-
363
- def test_should_allow_ignite
364
- assert @vehicle.ignite
365
- assert_equal 'idling', @vehicle.state
366
- end
367
-
368
- def test_should_allow_ignite_with_skipped_action
369
- assert @vehicle.ignite(false)
370
- assert @vehicle.new_record?
371
- end
372
-
373
- def test_should_allow_ignite_bang
374
- assert @vehicle.ignite!
375
- end
376
-
377
- def test_should_allow_ignite_bang_with_skipped_action
378
- assert @vehicle.ignite!(false)
379
- assert @vehicle.new_record?
380
- end
381
-
382
- def test_should_be_saved_after_successful_event
383
- @vehicle.ignite
384
- assert !@vehicle.new_record?
385
- end
386
-
387
- def test_should_not_allow_idle
388
- assert !@vehicle.idle
389
- end
390
-
391
- def test_should_not_allow_shift_up
392
- assert !@vehicle.shift_up
393
- end
394
-
395
- def test_should_not_allow_shift_down
396
- assert !@vehicle.shift_down
397
- end
398
-
399
- def test_should_not_allow_crash
400
- assert !@vehicle.crash
401
- end
402
-
403
- def test_should_not_allow_repair
404
- assert !@vehicle.repair
405
- end
406
-
407
- def test_should_be_insurance_inactive
408
- assert @vehicle.insurance_inactive?
409
- end
410
-
411
- def test_should_be_able_to_buy
412
- assert @vehicle.can_buy_insurance?
413
- end
414
-
415
- def test_should_allow_buying_insurance
416
- assert @vehicle.buy_insurance
417
- end
418
-
419
- def test_should_allow_buying_insurance_bang
420
- assert @vehicle.buy_insurance!
421
- end
422
-
423
- def test_should_allow_ignite_buying_insurance_with_skipped_action
424
- assert @vehicle.buy_insurance!(false)
425
- assert @vehicle.new_record?
426
- end
427
-
428
- def test_should_not_be_insurance_active
429
- assert !@vehicle.insurance_active?
430
- end
431
-
432
- def test_should_not_be_able_to_cancel
433
- assert !@vehicle.can_cancel_insurance?
434
- end
435
-
436
- def test_should_not_allow_cancelling_insurance
437
- assert !@vehicle.cancel_insurance
438
- end
439
- end
440
-
441
- class VehicleParkedTest < Test::Unit::TestCase
442
- def setup
443
- @vehicle = Vehicle.new
444
- end
445
-
446
- def test_should_be_in_parked_state
447
- assert_equal 'parked', @vehicle.state
448
- end
449
-
450
- def test_should_not_have_the_seatbelt_on
451
- assert !@vehicle.seatbelt_on
452
- end
453
-
454
- def test_should_not_allow_park
455
- assert !@vehicle.park
456
- end
457
-
458
- def test_should_allow_ignite
459
- assert @vehicle.ignite
460
- assert_equal 'idling', @vehicle.state
461
- end
462
-
463
- def test_should_not_allow_idle
464
- assert !@vehicle.idle
465
- end
466
-
467
- def test_should_not_allow_shift_up
468
- assert !@vehicle.shift_up
469
- end
470
-
471
- def test_should_not_allow_shift_down
472
- assert !@vehicle.shift_down
473
- end
474
-
475
- def test_should_not_allow_crash
476
- assert !@vehicle.crash
477
- end
478
-
479
- def test_should_not_allow_repair
480
- assert !@vehicle.repair
481
- end
482
-
483
- def test_should_raise_exception_if_repair_not_allowed!
484
- exception = assert_raise(EnumStateMachine::InvalidTransition) {@vehicle.repair!}
485
- assert_equal @vehicle, exception.object
486
- assert_equal Vehicle.state_machine(:state), exception.machine
487
- assert_equal :repair, exception.event
488
- assert_equal 'parked', exception.from
489
- end
490
- end
491
-
492
- class VehicleIdlingTest < Test::Unit::TestCase
493
- def setup
494
- @vehicle = Vehicle.new
495
- @vehicle.ignite
496
- end
497
-
498
- def test_should_be_in_idling_state
499
- assert_equal 'idling', @vehicle.state
500
- end
501
-
502
- def test_should_be_idling
503
- assert @vehicle.idling?
504
- end
505
-
506
- def test_should_have_seatbelt_on
507
- assert @vehicle.seatbelt_on
508
- end
509
-
510
- def test_should_track_time_elapsed
511
- assert_not_nil @vehicle.time_elapsed
512
- end
513
-
514
- def test_should_allow_park
515
- assert @vehicle.park
516
- end
517
-
518
- def test_should_call_park_with_bang_action
519
- class << @vehicle
520
- def park
521
- super && 1
522
- end
523
- end
524
-
525
- assert_equal 1, @vehicle.park!
526
- end
527
-
528
- def test_should_not_allow_idle
529
- assert !@vehicle.idle
530
- end
531
-
532
- def test_should_allow_shift_up
533
- assert @vehicle.shift_up
534
- end
535
-
536
- def test_should_not_allow_shift_down
537
- assert !@vehicle.shift_down
538
- end
539
-
540
- def test_should_not_allow_crash
541
- assert !@vehicle.crash
542
- end
543
-
544
- def test_should_not_allow_repair
545
- assert !@vehicle.repair
546
- end
547
- end
548
-
549
- class VehicleFirstGearTest < Test::Unit::TestCase
550
- def setup
551
- @vehicle = Vehicle.new
552
- @vehicle.ignite
553
- @vehicle.shift_up
554
- end
555
-
556
- def test_should_be_in_first_gear_state
557
- assert_equal 'first_gear', @vehicle.state
558
- end
559
-
560
- def test_should_be_first_gear
561
- assert @vehicle.first_gear?
562
- end
563
-
564
- def test_should_allow_park
565
- assert @vehicle.park
566
- end
567
-
568
- def test_should_allow_idle
569
- assert @vehicle.idle
570
- end
571
-
572
- def test_should_allow_shift_up
573
- assert @vehicle.shift_up
574
- end
575
-
576
- def test_should_not_allow_shift_down
577
- assert !@vehicle.shift_down
578
- end
579
-
580
- def test_should_allow_crash
581
- assert @vehicle.crash
582
- end
583
-
584
- def test_should_not_allow_repair
585
- assert !@vehicle.repair
586
- end
587
- end
588
-
589
- class VehicleSecondGearTest < Test::Unit::TestCase
590
- def setup
591
- @vehicle = Vehicle.new
592
- @vehicle.ignite
593
- 2.times {@vehicle.shift_up}
594
- end
595
-
596
- def test_should_be_in_second_gear_state
597
- assert_equal 'second_gear', @vehicle.state
598
- end
599
-
600
- def test_should_be_second_gear
601
- assert @vehicle.second_gear?
602
- end
603
-
604
- def test_should_not_allow_park
605
- assert !@vehicle.park
606
- end
607
-
608
- def test_should_not_allow_idle
609
- assert !@vehicle.idle
610
- end
611
-
612
- def test_should_allow_shift_up
613
- assert @vehicle.shift_up
614
- end
615
-
616
- def test_should_allow_shift_down
617
- assert @vehicle.shift_down
618
- end
619
-
620
- def test_should_allow_crash
621
- assert @vehicle.crash
622
- end
623
-
624
- def test_should_not_allow_repair
625
- assert !@vehicle.repair
626
- end
627
- end
628
-
629
- class VehicleThirdGearTest < Test::Unit::TestCase
630
- def setup
631
- @vehicle = Vehicle.new
632
- @vehicle.ignite
633
- 3.times {@vehicle.shift_up}
634
- end
635
-
636
- def test_should_be_in_third_gear_state
637
- assert_equal 'third_gear', @vehicle.state
638
- end
639
-
640
- def test_should_be_third_gear
641
- assert @vehicle.third_gear?
642
- end
643
-
644
- def test_should_not_allow_park
645
- assert !@vehicle.park
646
- end
647
-
648
- def test_should_not_allow_idle
649
- assert !@vehicle.idle
650
- end
651
-
652
- def test_should_not_allow_shift_up
653
- assert !@vehicle.shift_up
654
- end
655
-
656
- def test_should_allow_shift_down
657
- assert @vehicle.shift_down
658
- end
659
-
660
- def test_should_allow_crash
661
- assert @vehicle.crash
662
- end
663
-
664
- def test_should_not_allow_repair
665
- assert !@vehicle.repair
666
- end
667
- end
668
-
669
- class VehicleStalledTest < Test::Unit::TestCase
670
- def setup
671
- @vehicle = Vehicle.new
672
- @vehicle.ignite
673
- @vehicle.shift_up
674
- @vehicle.crash
675
- end
676
-
677
- def test_should_be_in_stalled_state
678
- assert_equal 'stalled', @vehicle.state
679
- end
680
-
681
- def test_should_be_stalled
682
- assert @vehicle.stalled?
683
- end
684
-
685
- def test_should_be_towed
686
- assert @vehicle.auto_shop.busy?
687
- assert_equal 1, @vehicle.auto_shop.num_customers
688
- end
689
-
690
- def test_should_have_an_increased_insurance_premium
691
- assert_equal 150, @vehicle.insurance_premium
692
- end
693
-
694
- def test_should_not_allow_park
695
- assert !@vehicle.park
696
- end
697
-
698
- def test_should_allow_ignite
699
- assert @vehicle.ignite
700
- end
701
-
702
- def test_should_not_change_state_when_ignited
703
- assert_equal 'stalled', @vehicle.state
704
- end
705
-
706
- def test_should_not_allow_idle
707
- assert !@vehicle.idle
708
- end
709
-
710
- def test_should_now_allow_shift_up
711
- assert !@vehicle.shift_up
712
- end
713
-
714
- def test_should_not_allow_shift_down
715
- assert !@vehicle.shift_down
716
- end
717
-
718
- def test_should_not_allow_crash
719
- assert !@vehicle.crash
720
- end
721
-
722
- def test_should_allow_repair_if_auto_shop_is_busy
723
- assert @vehicle.repair
724
- end
725
-
726
- def test_should_not_allow_repair_if_auto_shop_is_available
727
- @vehicle.auto_shop.fix_vehicle
728
- assert !@vehicle.repair
729
- end
730
- end
731
-
732
- class VehicleRepairedTest < Test::Unit::TestCase
733
- def setup
734
- @vehicle = Vehicle.new
735
- @vehicle.ignite
736
- @vehicle.shift_up
737
- @vehicle.crash
738
- @vehicle.repair
739
- end
740
-
741
- def test_should_be_in_parked_state
742
- assert_equal 'parked', @vehicle.state
743
- end
744
-
745
- def test_should_not_have_a_busy_auto_shop
746
- assert @vehicle.auto_shop.available?
747
- end
748
- end
749
-
750
- class VehicleLockedTest < Test::Unit::TestCase
751
- def setup
752
- @vehicle = Vehicle.new
753
- @vehicle.state = 'locked'
754
- end
755
-
756
- def test_should_be_parked_after_park
757
- @vehicle.park
758
- assert @vehicle.parked?
759
- end
760
-
761
- def test_should_be_parked_after_ignite
762
- @vehicle.ignite
763
- assert @vehicle.parked?
764
- end
765
-
766
- def test_should_be_parked_after_shift_up
767
- @vehicle.shift_up
768
- assert @vehicle.parked?
769
- end
770
-
771
- def test_should_be_parked_after_shift_down
772
- @vehicle.shift_down
773
- assert @vehicle.parked?
774
- end
775
- end
776
-
777
- class VehicleWithParallelEventsTest < Test::Unit::TestCase
778
- def setup
779
- @vehicle = Vehicle.new
780
- end
781
-
782
- def test_should_fail_if_any_event_cannot_transition
783
- assert !@vehicle.fire_events(:ignite, :cancel_insurance)
784
- end
785
-
786
- def test_should_be_successful_if_all_events_transition
787
- assert @vehicle.fire_events(:ignite, :buy_insurance)
788
- end
789
-
790
- def test_should_not_save_if_skipping_action
791
- assert @vehicle.fire_events(:ignite, :buy_insurance, false)
792
- assert !@vehicle.saved
793
- end
794
-
795
- def test_should_raise_exception_if_any_event_cannot_transition_on_bang
796
- exception = assert_raise(EnumStateMachine::InvalidParallelTransition) { @vehicle.fire_events!(:ignite, :cancel_insurance) }
797
- assert_equal @vehicle, exception.object
798
- assert_equal [:ignite, :cancel_insurance], exception.events
799
- end
800
-
801
- def test_should_not_raise_exception_if_all_events_transition_on_bang
802
- assert @vehicle.fire_events!(:ignite, :buy_insurance)
803
- end
804
-
805
- def test_should_not_save_if_skipping_action_on_bang
806
- assert @vehicle.fire_events!(:ignite, :buy_insurance, false)
807
- assert !@vehicle.saved
808
- end
809
- end
810
-
811
- class VehicleWithEventAttributesTest < Test::Unit::TestCase
812
- def setup
813
- @vehicle = Vehicle.new
814
- @vehicle.state_event = 'ignite'
815
- end
816
-
817
- def test_should_fail_if_event_is_invalid
818
- @vehicle.state_event = 'invalid'
819
- assert !@vehicle.save
820
- assert_equal 'parked', @vehicle.state
821
- end
822
-
823
- def test_should_fail_if_event_has_no_transition
824
- @vehicle.state_event = 'park'
825
- assert !@vehicle.save
826
- assert_equal 'parked', @vehicle.state
827
- end
828
-
829
- def test_should_return_original_action_value_on_success
830
- assert_equal @vehicle, @vehicle.save
831
- end
832
-
833
- def test_should_transition_state_on_success
834
- @vehicle.save
835
- assert_equal 'idling', @vehicle.state
836
- end
837
- end
838
-
839
- class MotorcycleTest < Test::Unit::TestCase
840
- def setup
841
- @motorcycle = Motorcycle.new
842
- end
843
-
844
- def test_should_be_in_idling_state
845
- assert_equal 'idling', @motorcycle.state
846
- end
847
-
848
- def test_should_allow_park
849
- assert @motorcycle.park
850
- end
851
-
852
- def test_should_not_allow_ignite
853
- assert !@motorcycle.ignite
854
- end
855
-
856
- def test_should_allow_shift_up
857
- assert @motorcycle.shift_up
858
- end
859
-
860
- def test_should_not_allow_shift_down
861
- assert !@motorcycle.shift_down
862
- end
863
-
864
- def test_should_not_allow_crash
865
- assert !@motorcycle.crash
866
- end
867
-
868
- def test_should_not_allow_repair
869
- assert !@motorcycle.repair
870
- end
871
-
872
- def test_should_inherit_decibels_from_superclass
873
- @motorcycle.park
874
- assert_equal 0.0, @motorcycle.decibels
875
- end
876
-
877
- def test_should_use_decibels_defined_in_state
878
- @motorcycle.shift_up
879
- assert_equal 1.0, @motorcycle.decibels
880
- end
881
- end
882
-
883
- class CarTest < Test::Unit::TestCase
884
- def setup
885
- @car = Car.new
886
- end
887
-
888
- def test_should_be_in_parked_state
889
- assert_equal 'parked', @car.state
890
- end
891
-
892
- def test_should_not_have_the_seatbelt_on
893
- assert !@car.seatbelt_on
894
- end
895
-
896
- def test_should_not_allow_park
897
- assert !@car.park
898
- end
899
-
900
- def test_should_allow_ignite
901
- assert @car.ignite
902
- assert_equal 'idling', @car.state
903
- end
904
-
905
- def test_should_not_allow_idle
906
- assert !@car.idle
907
- end
908
-
909
- def test_should_not_allow_shift_up
910
- assert !@car.shift_up
911
- end
912
-
913
- def test_should_not_allow_shift_down
914
- assert !@car.shift_down
915
- end
916
-
917
- def test_should_not_allow_crash
918
- assert !@car.crash
919
- end
920
-
921
- def test_should_not_allow_repair
922
- assert !@car.repair
923
- end
924
-
925
- def test_should_allow_reverse
926
- assert @car.reverse
927
- end
928
- end
929
-
930
- class CarBackingUpTest < Test::Unit::TestCase
931
- def setup
932
- @car = Car.new
933
- @car.reverse
934
- end
935
-
936
- def test_should_be_in_backing_up_state
937
- assert_equal 'backing_up', @car.state
938
- end
939
-
940
- def test_should_allow_park
941
- assert @car.park
942
- end
943
-
944
- def test_should_not_allow_ignite
945
- assert !@car.ignite
946
- end
947
-
948
- def test_should_allow_idle
949
- assert @car.idle
950
- end
951
-
952
- def test_should_allow_shift_up
953
- assert @car.shift_up
954
- end
955
-
956
- def test_should_not_allow_shift_down
957
- assert !@car.shift_down
958
- end
959
-
960
- def test_should_not_allow_crash
961
- assert !@car.crash
962
- end
963
-
964
- def test_should_not_allow_repair
965
- assert !@car.repair
966
- end
967
-
968
- def test_should_not_allow_reverse
969
- assert !@car.reverse
970
- end
971
- end
972
-
973
- class AutoShopAvailableTest < Test::Unit::TestCase
974
- def setup
975
- @auto_shop = AutoShop.new
976
- end
977
-
978
- def test_should_be_in_available_state
979
- assert_equal 'available', @auto_shop.state
980
- end
981
-
982
- def test_should_allow_tow_vehicle
983
- assert @auto_shop.tow_vehicle
984
- end
985
-
986
- def test_should_not_allow_fix_vehicle
987
- assert !@auto_shop.fix_vehicle
988
- end
989
- end
990
-
991
- class AutoShopBusyTest < Test::Unit::TestCase
992
- def setup
993
- @auto_shop = AutoShop.new
994
- @auto_shop.tow_vehicle
995
- end
996
-
997
- def test_should_be_in_busy_state
998
- assert_equal 'busy', @auto_shop.state
999
- end
1000
-
1001
- def test_should_have_incremented_number_of_customers
1002
- assert_equal 1, @auto_shop.num_customers
1003
- end
1004
-
1005
- def test_should_not_allow_tow_vehicle
1006
- assert !@auto_shop.tow_vehicle
1007
- end
1008
-
1009
- def test_should_allow_fix_vehicle
1010
- assert @auto_shop.fix_vehicle
1011
- end
1012
- end
1013
-
1014
- class TrafficLightStopTest < Test::Unit::TestCase
1015
- def setup
1016
- @light = TrafficLight.new
1017
- @light.state = 'stop'
1018
- end
1019
-
1020
- def test_should_use_stop_color
1021
- assert_equal 'red', @light.color
1022
- end
1023
-
1024
- def test_should_pass_arguments_through
1025
- assert_equal 'RED', @light.color(:upcase!)
1026
- end
1027
-
1028
- def test_should_pass_block_through
1029
- color = @light.color {|value| value.upcase!}
1030
- assert_equal 'RED', color
1031
- end
1032
-
1033
- def test_should_use_stop_capture_violations
1034
- assert_equal true, @light.capture_violations?
1035
- end
1036
- end
1037
-
1038
- class TrafficLightProceedTest < Test::Unit::TestCase
1039
- def setup
1040
- @light = TrafficLight.new
1041
- @light.state = 'proceed'
1042
- end
1043
-
1044
- def test_should_use_proceed_color
1045
- assert_equal 'green', @light.color
1046
- end
1047
-
1048
- def test_should_use_proceed_capture_violations
1049
- assert_equal false, @light.capture_violations?
1050
- end
1051
- end
1052
-
1053
- class TrafficLightCautionTest < Test::Unit::TestCase
1054
- def setup
1055
- @light = TrafficLight.new
1056
- @light.state = 'caution'
1057
- end
1058
-
1059
- def test_should_use_caution_color
1060
- assert_equal 'yellow', @light.color
1061
- end
1062
-
1063
- def test_should_use_caution_capture_violations
1064
- assert_equal true, @light.capture_violations?
1065
- end
1066
- end