Class: Legion::Extensions::Mesh::Helpers::Registry

Inherits:
Object
  • Object
show all
Defined in:
lib/legion/extensions/mesh/helpers/registry.rb

Instance Attribute Summary collapse

Instance Method Summary collapse

Constructor Details

#initializeRegistry

Returns a new instance of Registry.



10
11
12
13
14
# File 'lib/legion/extensions/mesh/helpers/registry.rb', line 10

def initialize
  @agents = {}
  @capabilities = Hash.new { |h, k| h[k] = [] }
  @messages = []
end

Instance Attribute Details

#agentsObject (readonly)

Returns the value of attribute agents.



8
9
10
# File 'lib/legion/extensions/mesh/helpers/registry.rb', line 8

def agents
  @agents
end

#capabilitiesObject (readonly)

Returns the value of attribute capabilities.



8
9
10
# File 'lib/legion/extensions/mesh/helpers/registry.rb', line 8

def capabilities
  @capabilities
end

#messagesObject (readonly)

Returns the value of attribute messages.



8
9
10
# File 'lib/legion/extensions/mesh/helpers/registry.rb', line 8

def messages
  @messages
end

Instance Method Details

#all_agentsObject



94
95
96
# File 'lib/legion/extensions/mesh/helpers/registry.rb', line 94

def all_agents
  @agents.values
end

#countObject



98
99
100
# File 'lib/legion/extensions/mesh/helpers/registry.rb', line 98

def count
  @agents.size
end

#expire_silent_agents(timeout: Topology::MESH_SILENCE_TIMEOUT) ⇒ Object



78
79
80
81
82
83
84
85
86
87
88
# File 'lib/legion/extensions/mesh/helpers/registry.rb', line 78

def expire_silent_agents(timeout: Topology::MESH_SILENCE_TIMEOUT)
  cutoff = Time.now.utc - timeout
  expired = []
  @agents.each_value do |agent|
    next unless agent[:status] == :online && agent[:last_seen] < cutoff

    agent[:status] = :offline
    expired << agent[:agent_id]
  end
  expired
end

#find_by_capability(capability) ⇒ Object



48
49
50
51
# File 'lib/legion/extensions/mesh/helpers/registry.rb', line 48

def find_by_capability(capability)
  agent_ids = @capabilities[capability] || []
  agent_ids.filter_map { |id| @agents[id] }
end

#heartbeat(agent_id) ⇒ Object



39
40
41
42
43
44
45
46
# File 'lib/legion/extensions/mesh/helpers/registry.rb', line 39

def heartbeat(agent_id)
  agent = @agents[agent_id]
  return nil unless agent

  agent[:last_seen] = Time.now.utc
  agent[:status] = :online
  agent[:generation] = (agent[:generation] || 0) + 1
end

#online_agentsObject



90
91
92
# File 'lib/legion/extensions/mesh/helpers/registry.rb', line 90

def online_agents
  @agents.values.select { |a| a[:status] == :online }
end

#register_agent(agent_id, capabilities: [], endpoint: nil, source: :native, node: nil) ⇒ Object



16
17
18
19
20
21
22
23
24
25
26
27
28
29
# File 'lib/legion/extensions/mesh/helpers/registry.rb', line 16

def register_agent(agent_id, capabilities: [], endpoint: nil, source: :native, node: nil)
  @agents[agent_id] = {
    agent_id:      agent_id,
    capabilities:  capabilities,
    endpoint:      endpoint,
    source:        source,
    node:          node || local_node_name,
    generation:    1,
    registered_at: Time.now.utc,
    last_seen:     Time.now.utc,
    status:        :online
  }
  capabilities.each { |cap| @capabilities[cap] << agent_id }
end

#route_message(from:, to: nil, capability: nil, pattern: :unicast, payload: {}, hops: 0) ⇒ Object



53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
# File 'lib/legion/extensions/mesh/helpers/registry.rb', line 53

def route_message(from:, to: nil, capability: nil, pattern: :unicast, payload: {}, hops: 0)
  if hops >= Topology::MAX_HOPS
    return { from: from, to: to, capability: capability, pattern: pattern,
             payload: payload, hops: hops, at: Time.now.utc,
             delivered_to: [], rejected: :max_hops_exceeded }
  end

  msg = {
    from: from, to: to, capability: capability,
    pattern: pattern, payload: payload, hops: hops, at: Time.now.utc
  }

  targets = case pattern
            when :unicast   then to ? [@agents[to]].compact : []
            when :multicast then capability ? find_by_capability(capability) : []
            when :broadcast then @agents.values
            else []
            end

  msg[:delivered_to] = targets.map { |t| t[:agent_id] }
  @messages << msg
  @messages.shift while @messages.size > 1000
  msg
end

#unregister_agent(agent_id) ⇒ Object



31
32
33
34
35
36
37
# File 'lib/legion/extensions/mesh/helpers/registry.rb', line 31

def unregister_agent(agent_id)
  agent = @agents.delete(agent_id)
  return nil unless agent

  agent[:capabilities].each { |cap| @capabilities[cap].delete(agent_id) }
  agent
end