Class: Philiprehberger::StateMachine::Definition

Inherits:
Object
  • Object
show all
Defined in:
lib/philiprehberger/state_machine/definition.rb

Overview

DSL class used inside the ‘state_machine` block to define events, transitions, and callbacks.

Instance Attribute Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(initial:) ⇒ Definition

Returns a new instance of Definition.

Parameters:

  • initial (Symbol)

    the initial state



11
12
13
14
15
16
17
18
# File 'lib/philiprehberger/state_machine/definition.rb', line 11

def initialize(initial:)
  @initial = initial
  @events = {}
  @callback_set = CallbackSet.new
  @auto_transitions = []
  @parallel_state_definitions = {}
  @final_states = []
end

Instance Attribute Details

#auto_transitionsObject (readonly)

Returns the value of attribute auto_transitions.



8
9
10
# File 'lib/philiprehberger/state_machine/definition.rb', line 8

def auto_transitions
  @auto_transitions
end

#callback_setObject (readonly)

Returns the value of attribute callback_set.



8
9
10
# File 'lib/philiprehberger/state_machine/definition.rb', line 8

def callback_set
  @callback_set
end

#eventsObject (readonly)

Returns the value of attribute events.



8
9
10
# File 'lib/philiprehberger/state_machine/definition.rb', line 8

def events
  @events
end

#final_statesObject (readonly)

Returns the value of attribute final_states.



8
9
10
# File 'lib/philiprehberger/state_machine/definition.rb', line 8

def final_states
  @final_states
end

#initialObject (readonly)

Returns the value of attribute initial.



8
9
10
# File 'lib/philiprehberger/state_machine/definition.rb', line 8

def initial
  @initial
end

#parallel_state_definitionsObject (readonly)

Returns the value of attribute parallel_state_definitions.



8
9
10
# File 'lib/philiprehberger/state_machine/definition.rb', line 8

def parallel_state_definitions
  @parallel_state_definitions
end

Instance Method Details

#after_transition(opts = {}) {|Object| ... } ⇒ Object

Register an after_transition callback.

Parameters:

  • opts (Hash) (defaults to: {})

    optional :from and :to state filters

Yields:

  • (Object)

    block receives the host object



66
67
68
# File 'lib/philiprehberger/state_machine/definition.rb', line 66

def after_transition(opts = {}, &)
  @callback_set.add(type: :after, conditions: opts, &)
end

#all_statesArray<Symbol>

Returns all unique states referenced in the definition.

Returns:

  • (Array<Symbol>)


99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
# File 'lib/philiprehberger/state_machine/definition.rb', line 99

def all_states
  states = [initial]
  events.each_value do |transitions|
    transitions.each do |t|
      states.concat(Array(t.from))
      states << t.to
    end
  end
  auto_transitions.each do |at|
    states.concat(Array(at.from))
    states << at.to
  end
  states.concat(@final_states)
  states.uniq
end

#auto_transition(from:, to:, after:, guard: nil) ⇒ Object

Define a timed automatic transition.

Parameters:

  • from (Symbol, Array<Symbol>)

    source state(s)

  • to (Symbol)

    target state

  • after (Numeric)

    seconds to wait before auto-transitioning

  • guard (Proc, nil) (defaults to: nil)

    optional guard condition



76
77
78
# File 'lib/philiprehberger/state_machine/definition.rb', line 76

def auto_transition(from:, to:, after:, guard: nil)
  @auto_transitions << AutoTransition.new(from: from, to: to, after: after, guard: guard)
end

#before_transition(opts = {}) {|Object| ... } ⇒ Object

Register a before_transition callback.

Parameters:

  • opts (Hash) (defaults to: {})

    optional :from and :to state filters

Yields:

  • (Object)

    block receives the host object



58
59
60
# File 'lib/philiprehberger/state_machine/definition.rb', line 58

def before_transition(opts = {}, &)
  @callback_set.add(type: :before, conditions: opts, &)
end

#enter_hooksObject



88
89
90
# File 'lib/philiprehberger/state_machine/definition.rb', line 88

def enter_hooks
  @enter_hooks || {}
end

#event(name) { ... } ⇒ Object

Define an event with transitions.

Parameters:

  • name (Symbol)

    event name

Yields:

  • block evaluated via TransitionBuilder



45
46
47
48
49
50
51
52
# File 'lib/philiprehberger/state_machine/definition.rb', line 45

def event(name, &)
  builder = TransitionBuilder.new
  builder.instance_eval(&)
  @events[name] = builder.transitions

  # Store parallel state definitions if any
  @parallel_state_definitions[name] = builder.parallel_definitions if builder.parallel_definitions.any?
end

#exit_hooksObject



92
93
94
# File 'lib/philiprehberger/state_machine/definition.rb', line 92

def exit_hooks
  @exit_hooks || {}
end

#final_state?(name) ⇒ Boolean

Returns true if the given state name is declared final.

Parameters:

  • name (Symbol)

    the state name

Returns:

  • (Boolean)


37
38
39
# File 'lib/philiprehberger/state_machine/definition.rb', line 37

def final_state?(name)
  @final_states.include?(name)
end

#on_enter(state, &block) ⇒ Object



80
81
82
# File 'lib/philiprehberger/state_machine/definition.rb', line 80

def on_enter(state, &block)
  (@enter_hooks ||= {})[state] = block
end

#on_exit(state, &block) ⇒ Object



84
85
86
# File 'lib/philiprehberger/state_machine/definition.rb', line 84

def on_exit(state, &block)
  (@exit_hooks ||= {})[state] = block
end

#state(name, final: false) ⇒ Object

Declare a state, optionally marking it as final/terminal.

Calling ‘state :name` without options is a no-op used for documentation and introspection. Passing `final: true` marks the state as terminal, enabling the `#final?` / `#terminal?` predicates on instances.

Parameters:

  • name (Symbol)

    the state name

  • final (Boolean) (defaults to: false)

    whether this state is terminal



28
29
30
31
# File 'lib/philiprehberger/state_machine/definition.rb', line 28

def state(name, final: false)
  @final_states << name if final && !@final_states.include?(name)
  name
end