Module: RSMP::TLC::Proxy::Status

Included in:
TrafficControllerProxy
Defined in:
lib/rsmp/tlc/proxy/status.rb

Overview

Status reading and waiting methods for a remote TLC. Covers status subscriptions, group waits, and plan/band reading.

Instance Method Summary collapse

Instance Method Details

#fetch_signal_plan(options: {}) ⇒ Object

Fetch the current signal plan from the remote TLC.



8
9
10
11
12
13
14
15
16
# File 'lib/rsmp/tlc/proxy/status.rb', line 8

def fetch_signal_plan(options: {})
  validate_ready 'fetch signal plan'
  timeout = options[:timeout] || @timeouts['status_response']
  collector = request_status_and_collect({ S0014: %i[status source] }, within: timeout)
  collector.ok!
  collector.messages.last.attributes['sS'].to_h do |item|
    [item['n'], item['s']]
  end
end

#read_current_plan(options: {}) ⇒ Object

Read the current signal plan number via S0014. Returns the plan number as an Integer.



83
84
85
86
87
88
89
# File 'lib/rsmp/tlc/proxy/status.rb', line 83

def read_current_plan(options: {})
  validate_ready 'read current plan'
  timeout = options[:timeout] || @timeouts['status_response']
  collector = request_status_and_collect({ S0014: [:status] }, within: timeout)
  collector.ok!
  collector.messages.first.attributes['sS'].first['s'].to_i
end

#read_cycle_times(options: {}) ⇒ Object

Read cycle times for all plans via S0028. Returns a hash of plan_nr (Integer) => cycle_time (Integer, seconds).



71
72
73
74
75
76
77
78
79
# File 'lib/rsmp/tlc/proxy/status.rb', line 71

def read_cycle_times(options: {})
  validate_ready 'read cycle times'
  timeout = options[:timeout] || @timeouts['status_response']
  collector = request_status_and_collect({ S0028: [:status] }, within: timeout)
  collector.ok!
  collector.messages.first.attributes['sS'].first['s'].split(',').to_h do |item|
    item.split('-').map(&:to_i)
  end
end

#read_dynamic_band(plan:, band:, options: {}) ⇒ Object

Read the value of a single dynamic band for a given plan and band index via S0023. Returns the band value as an Integer, or nil if not found.



93
94
95
96
97
98
99
# File 'lib/rsmp/tlc/proxy/status.rb', line 93

def read_dynamic_band(plan:, band:, options: {})
  validate_ready 'read dynamic band'
  timeout = options[:timeout] || @timeouts['status_response']
  collector = request_status_and_collect({ S0023: [:status] }, within: timeout)
  collector.ok!
  extract_band_value(collector, plan, band)
end

#wait_for_groups(state, timeout:) ⇒ Object

Wait for all signal groups to match state (as regex string, e.g. ‘c’ for yellow flash).



46
47
48
49
50
51
52
53
# File 'lib/rsmp/tlc/proxy/status.rb', line 46

def wait_for_groups(state, timeout:)
  regex = /^#{state}+$/
  wait_for_status(
    "all groups to reach state #{state}",
    [{ 'sCI' => 'S0001', 'n' => 'signalgroupstatus', 's' => regex }],
    timeout: timeout
  )
end

#wait_for_normal_control(timeout: nil) ⇒ Object

Wait for the TLC to return to normal control mode (functional position NormalControl, yellow flash off, startup mode off).



57
58
59
60
61
62
63
64
65
66
67
# File 'lib/rsmp/tlc/proxy/status.rb', line 57

def wait_for_normal_control(timeout: nil)
  wait_for_status(
    'normal control on, yellow flash off, startup mode off',
    [
      { 'sCI' => 'S0007', 'n' => 'status', 's' => /^True(,True)*$/ },
      { 'sCI' => 'S0011', 'n' => 'status', 's' => /^False(,False)*$/ },
      { 'sCI' => 'S0005', 'n' => 'status', 's' => 'False' }
    ],
    timeout: timeout
  )
end

#wait_for_status(description, status_list, update_rate: 0, timeout: nil, component_id: nil) ⇒ Object

Subscribe to one or more statuses and wait until they match the expected values. Raises RSMP::TimeoutError if the values don’t match within the timeout.

status_list items: { ‘sCI’ => …, ‘n’ => …, ‘s’ => <expected value or Regexp> } component_id defaults to the main TLC component. timeout defaults to @timeouts.



24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
# File 'lib/rsmp/tlc/proxy/status.rb', line 24

def wait_for_status(description, status_list, update_rate: 0, timeout: nil, component_id: nil)
  validate_ready 'wait for status'
  component_id ||= main.c_id
  timeout ||= @timeouts['command']

  subscribe_list = status_list.map do |item|
    entry = item.merge('uRt' => update_rate.to_s)
    entry = entry.merge('sOc' => true) if use_soc?
    entry
  end

  log "Wait for #{description}", level: :debug

  begin
    subscribe_to_status_and_collect(subscribe_list, component: component_id, within: timeout).ok!
  ensure
    unsubscribe_list = status_list.map { |item| item.slice('sCI', 'n') }
    unsubscribe_to_status unsubscribe_list, component: component_id
  end
end