1
0
Fork 0
mirror of https://github.com/aasm/aasm synced 2023-03-27 23:22:41 -04:00

changes that allow you to ask "machine.may_event?", and get back the boolean answer from any pending transition guards

This commit is contained in:
bokmann 2010-10-05 11:47:53 -04:00
parent 43b8c08c9a
commit 7339c68c28
2 changed files with 31 additions and 0 deletions

View file

@ -49,6 +49,13 @@ module AASM
sm.events[name] = AASM::SupportingClasses::Event.new(name, options, &block)
end
# an addition over standard aasm so that, before firing an event, you can ask
# may_event? and get back a boolean that tells you whether the guard method
# on the transition will let this happen.
define_method("may_#{name.to_s}?") do |*args|
aasm_test_event(name)
end
define_method("#{name.to_s}!") do |*args|
aasm_fire_event(name, true, *args)
end
@ -100,6 +107,12 @@ module AASM
aasm_events_for_state(aasm_current_state)
end
# filters the results of events_for_current_state so that only those that
# are really currently possible (given transition guards) are shown.
def aasm_permissible_events_for_current_state
aasm_events_for_current_state.select{ |e| self.send(("may_" + e.to_s + "?").to_sym) }
end
def aasm_events_for_state(state)
events = self.class.aasm_events.values.select {|event| event.transitions_from_state?(state) }
events.map {|event| event.name}

View file

@ -7,6 +7,24 @@ class AASM::SupportingClasses::Event
update(options, &block)
end
# a neutered version of fire - it doesn't actually fir the event, it just
# executes the transition guards to determine if a transition is even
# an option given current conditions.
def may_fire?(obj, to_state=nil)
transitions = @transitions.select { |t| t.from == obj.aasm_current_state }
return false if transitions.size == 0
result = false
transitions.each do |transition|
next if to_state and !Array(transition.to).include?(to_state)
if transition.perform(obj)
result = true
break
end
end
result
end
def fire(obj, to_state=nil, *args)
transitions = @transitions.select { |t| t.from == obj.aasm_current_state }
raise AASM::InvalidTransition, "Event '#{name}' cannot transition from '#{obj.aasm_current_state}'" if transitions.size == 0