Class: Seh::Event

Inherits:
OpenStruct
  • Object
show all
Defined in:
lib/seh/event.rb

Instance Method Summary collapse

Constructor Details

#initialize {|_self| ... } ⇒ Event

Returns a new instance of Event.

Yields:

  • (_self)

Yield Parameters:

  • _self (Seh::Event) —

    the object that the method was called on



6
7
8
9
10
11
12
13
14
15
16
17
18
# File 'lib/seh/event.rb', line 6

def initialize
  super
  @state = :ready
  @types = Set.new
  @targets = Set.new
  @start_callbacks = []
  @finish_callbacks = []
  @stage_callbacks = {}
  @stage_decision_blocks = {}
  @stages = Set.new
  @abort = false
  yield self if block_given?
end

Instance Method Details

#abort ⇒ Object

Abort this Event. After #abort is called, some in-progress work may still be completed. Abort semantics:

- if #abort is called before #dispatch, #dispatch return immediately, no target will know the event occurred, and no callbacks will be executed
- if #abort is called by a target while visiting the set of targets, each target will still receive the event but no stage callbacks will be exewcuted
- if #abort is called during start callbacks, start will complete and no stage or finish callbacks will be run
- if #abort is called during a stage callback, the current stage will complete and no other stage or finish callbacks will be run
- if #abort is called during a finish callback, finish will complete, i.e. calling #abort during a finish callbacks is fairly pointless

Returns:

  • nil



50
51
52
53
# File 'lib/seh/event.rb', line 50

def abort
  @abort = true
  nil
end

#aborted? ⇒ Boolean

Returns true if #abort has been called, false otherwise.

Returns:

  • (Boolean) —

    true if #abort has been called, false otherwise



56
57
58
# File 'lib/seh/event.rb', line 56

def aborted?
  @abort
end

#add_stage(new_stage, &stage_decision_block) ⇒ Object

Add the passed new stage to this event

Parameters:

  • new_stage —
    • a stage to add to this event

Returns:

  • nil



82
83
84
85
86
87
88
# File 'lib/seh/event.rb', line 82

def add_stage new_stage, &stage_decision_block
  raise "Event#add_stage is disallowed after Event#dispatch is called" unless @state == :ready
  @stages << new_stage
  @stage_callbacks[new_stage] ||= []
  @stage_decision_blocks[new_stage] = stage_decision_block if block_given?
  nil
end

#bind(stage, &block) ⇒ Object

Bind the passed block as a callback for the passed stage

Parameters:

  • stage —
    • a stage which has been added using #add_stage

Returns:

  • nil



102
103
104
105
# File 'lib/seh/event.rb', line 102

def bind stage, &block
  @stage_callbacks[stage] << block if block_given?
  nil
end

#dispatch ⇒ Object

Dispatch this event, notifying all targets of the event and executing any callbacks. #dispatch may only be called once Dispatch algorithm:

  1. determine the full set of targets affected by this event

  2. run callbacks on targets which match this event's types

  3. run stage callbacks contained in this event; typically targets will append stage callbacks to this event using Event#bind, #start, #finish Callback execution order:

    start callbacks
    stage callabcks - in the order stages were added
    finish callbacks
    

    Callbacks in the same stage have arbitrary execution order

Returns:

  • nil



32
33
34
35
36
37
38
39
40
# File 'lib/seh/event.rb', line 32

def dispatch
  raise "Event#dispatch may only be called once" unless @state == :ready
  @state = :inflight
  return if @abort
  run_target_callbacks
  run_stage_callbacks
  @state = :done
  nil
end

#finish(&block) ⇒ Object

Bind the passed block as a finish callback

Returns:

  • nil



118
119
120
121
# File 'lib/seh/event.rb', line 118

def finish &block
  @finish_callbacks << block if block_given?
  nil
end

#match_type?(event_type) ⇒ Boolean

Return true if this event's types match the passed EventType

Parameters:

  • event_type —
    • an EventType to match against this event's types

Returns:

  • (Boolean) —

    true or false - result of passed EventType#match on this event's types



93
94
95
96
# File 'lib/seh/event.rb', line 93

def match_type? event_type
  event_type = EventType.new event_type unless event_type.is_a? EventType
  event_type.match @types
end

#start(&block) ⇒ Object

Bind the passed block as a start callback

Returns:

  • nil



110
111
112
113
# File 'lib/seh/event.rb', line 110

def start &block
  @start_callbacks << block if block_given?
  nil
end

#target(*targets) ⇒ Object

Add targets to this event. May not be called after or during #dispatch

Parameters:

  • targets —
    • zero or more EventTarget objects to add to this event

Returns:

  • nil



63
64
65
66
67
# File 'lib/seh/event.rb', line 63

def target *targets
  raise "Event#target is disallowed after Event#dispatch is called" unless @state == :ready
  targets.each { |target| @targets << target }
  nil
end

#type(*event_types) ⇒ Object

Add event types to this event. May not be called after or during #dispatch

Parameters:

  • types —
    • zero or more types to add to this Event. The Event is simultaneously all of these types

Returns:

  • nil



72
73
74
75
76
# File 'lib/seh/event.rb', line 72

def type *event_types
  raise "Event#type is disallowed after Event#dispatch is called" unless @state == :ready
  event_types.each { |type| @types << type }
  nil
end