Class: FlowEngine::Node

Inherits:
Object
  • Object
show all
Defined in:
lib/flowengine/node.rb

Overview

A single step in the flow: question metadata, input config, and conditional transitions. Used by Engine to determine the next step and by UI/export to render the step.

Instance Attribute Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(id:, type:, question:, decorations: nil, options: nil, fields: nil, transitions: [], visibility_rule: nil, max_clarifications: 0) ⇒ Node

Returns a new instance of Node.

Parameters:

  • id (Symbol) —

    step id

  • type (Symbol) —

    step/input type

  • question (String) —

    label/prompt

  • decorations (Object, nil) (defaults to: nil) —

    optional UI decorations (not used by engine)

  • options (Array, Hash, nil) (defaults to: nil) —

    option list or key=>label hash for select steps

  • fields (Array, nil) (defaults to: nil) —

    field list for matrix-style steps

  • transitions (Array<Transition>) (defaults to: []) —

    conditional next-step transitions (default: [])

  • visibility_rule (Rules::Base, nil) (defaults to: nil) —

    optional rule for visibility (default: always visible)

  • max_clarifications (Integer) (defaults to: 0) —

    max follow-up rounds for :ai_intake (default: 0)



29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
# File 'lib/flowengine/node.rb', line 29

def initialize(id:, # rubocop:disable Metrics/ParameterLists
               type:,
               question:,
               decorations: nil,
               options: nil,
               fields: nil,
               transitions: [],
               visibility_rule: nil,
               max_clarifications: 0)
  @id = id
  @type = type
  @question = question
  @decorations = decorations
  extract_options(options)
  @fields = fields&.freeze
  @transitions = transitions.freeze
  @visibility_rule = visibility_rule
  @max_clarifications = max_clarifications
  freeze
end

Instance Attribute Details

#fields ⇒ Array? (readonly)

field names for number_matrix etc.; nil otherwise

Returns:

  • (Array, nil) —

    the current value of fields



16
17
18
# File 'lib/flowengine/node.rb', line 16

def fields
  @fields
end

#id ⇒ Symbol (readonly)

unique step identifier

Returns:

  • (Symbol) —

    the current value of id



16
17
18
# File 'lib/flowengine/node.rb', line 16

def id
  @id
end

#max_clarifications ⇒ Integer (readonly)

max follow-up rounds for :ai_intake steps (default: 0)

Returns:

  • (Integer) —

    the current value of max_clarifications



16
17
18
# File 'lib/flowengine/node.rb', line 16

def max_clarifications
  @max_clarifications
end

#option_labels ⇒ Hash? (readonly)

key => display label mapping (nil when options are plain strings)

Returns:

  • (Hash, nil) —

    the current value of option_labels



16
17
18
# File 'lib/flowengine/node.rb', line 16

def option_labels
  @option_labels
end

#options ⇒ Array? (readonly)

option keys for select steps; nil for other types

Returns:

  • (Array, nil) —

    the current value of options



16
17
18
# File 'lib/flowengine/node.rb', line 16

def options
  @options
end

#question ⇒ String (readonly)

prompt text for the step

Returns:

  • (String) —

    the current value of question



16
17
18
# File 'lib/flowengine/node.rb', line 16

def question
  @question
end

#transitions ⇒ Array<Transition> (readonly)

ordered list of conditional next-step rules

Returns:

  • (Array<Transition>) —

    the current value of transitions



16
17
18
# File 'lib/flowengine/node.rb', line 16

def transitions
  @transitions
end

#type ⇒ Symbol (readonly)

input type (e.g. :multi_select, :number_matrix, :ai_intake)

Returns:

  • (Symbol) —

    the current value of type



16
17
18
# File 'lib/flowengine/node.rb', line 16

def type
  @type
end

#visibility_rule ⇒ Rules::Base? (readonly)

rule controlling whether this node is visible (DAG mode)

Returns:

  • (Rules::Base, nil) —

    the current value of visibility_rule



16
17
18
# File 'lib/flowengine/node.rb', line 16

def visibility_rule
  @visibility_rule
end

Instance Method Details

#ai_intake? ⇒ Boolean

Returns true if this is an AI intake step.

Returns:

  • (Boolean) —

    true if this is an AI intake step



51
52
53
# File 'lib/flowengine/node.rb', line 51

def ai_intake?
  type == :ai_intake
end

#next_step_id(answers) ⇒ Symbol?

Resolves the next step id from current answers by evaluating transitions in order.

Parameters:

  • answers (Hash) —

    current answer state (step_id => value)

Returns:

  • (Symbol, nil) —

    id of the next step, or nil if no transition matches (flow end)



59
60
61
62
# File 'lib/flowengine/node.rb', line 59

def next_step_id(answers)
  match = transitions.find { |t| t.applies?(answers) }
  match&.target
end

#visible?(answers) ⇒ Boolean

Whether this node should be considered visible given current answers (for DAG/visibility).

Parameters:

  • answers (Hash) —

    current answer state

Returns:

  • (Boolean) —

    true if no visibility_rule, else result of rule evaluation



68
69
70
71
72
# File 'lib/flowengine/node.rb', line 68

def visible?(answers)
  return true if visibility_rule.nil?

  visibility_rule.evaluate(answers)
end