rsmp 0.37.0 → 0.38.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (106) hide show
  1. checksums.yaml +4 -4
  2. data/.devcontainer/devcontainer.json +22 -0
  3. data/.github/workflows/rubocop.yaml +17 -0
  4. data/.gitignore +5 -6
  5. data/.rubocop.yml +80 -0
  6. data/Gemfile +13 -1
  7. data/Gemfile.lock +34 -1
  8. data/Rakefile +3 -3
  9. data/lib/rsmp/cli.rb +147 -124
  10. data/lib/rsmp/collect/ack_collector.rb +8 -7
  11. data/lib/rsmp/collect/aggregated_status_collector.rb +4 -4
  12. data/lib/rsmp/collect/alarm_collector.rb +31 -23
  13. data/lib/rsmp/collect/alarm_matcher.rb +3 -3
  14. data/lib/rsmp/collect/collector/logging.rb +17 -0
  15. data/lib/rsmp/collect/collector/reporting.rb +44 -0
  16. data/lib/rsmp/collect/collector/status.rb +34 -0
  17. data/lib/rsmp/collect/collector.rb +69 -150
  18. data/lib/rsmp/collect/command_matcher.rb +19 -6
  19. data/lib/rsmp/collect/command_response_collector.rb +7 -7
  20. data/lib/rsmp/collect/distributor.rb +14 -11
  21. data/lib/rsmp/collect/filter.rb +31 -15
  22. data/lib/rsmp/collect/matcher.rb +7 -11
  23. data/lib/rsmp/collect/queue.rb +4 -4
  24. data/lib/rsmp/collect/receiver.rb +10 -12
  25. data/lib/rsmp/collect/state_collector.rb +116 -77
  26. data/lib/rsmp/collect/status_collector.rb +6 -6
  27. data/lib/rsmp/collect/status_matcher.rb +17 -7
  28. data/lib/rsmp/{alarm_state.rb → component/alarm_state.rb} +76 -37
  29. data/lib/rsmp/{component.rb → component/component.rb} +15 -15
  30. data/lib/rsmp/component/component_base.rb +89 -0
  31. data/lib/rsmp/component/component_proxy.rb +75 -0
  32. data/lib/rsmp/component/components.rb +63 -0
  33. data/lib/rsmp/convert/export/json_schema.rb +116 -110
  34. data/lib/rsmp/convert/import/yaml.rb +21 -18
  35. data/lib/rsmp/{rsmp.rb → helpers/clock.rb} +5 -6
  36. data/lib/rsmp/{deep_merge.rb → helpers/deep_merge.rb} +2 -1
  37. data/lib/rsmp/helpers/error.rb +71 -0
  38. data/lib/rsmp/{inspect.rb → helpers/inspect.rb} +6 -10
  39. data/lib/rsmp/log/archive.rb +98 -0
  40. data/lib/rsmp/log/colorization.rb +41 -0
  41. data/lib/rsmp/log/filtering.rb +54 -0
  42. data/lib/rsmp/log/logger.rb +206 -0
  43. data/lib/rsmp/{logging.rb → log/logging.rb} +5 -7
  44. data/lib/rsmp/message.rb +159 -148
  45. data/lib/rsmp/{node.rb → node/node.rb} +19 -17
  46. data/lib/rsmp/{protocol.rb → node/protocol.rb} +5 -3
  47. data/lib/rsmp/node/site/site.rb +195 -0
  48. data/lib/rsmp/node/supervisor/modules/configuration.rb +59 -0
  49. data/lib/rsmp/node/supervisor/modules/connection.rb +140 -0
  50. data/lib/rsmp/node/supervisor/modules/sites.rb +64 -0
  51. data/lib/rsmp/node/supervisor/supervisor.rb +72 -0
  52. data/lib/rsmp/{task.rb → node/task.rb} +12 -14
  53. data/lib/rsmp/proxy/modules/acknowledgements.rb +144 -0
  54. data/lib/rsmp/proxy/modules/receive.rb +119 -0
  55. data/lib/rsmp/proxy/modules/send.rb +76 -0
  56. data/lib/rsmp/proxy/modules/state.rb +25 -0
  57. data/lib/rsmp/proxy/modules/tasks.rb +105 -0
  58. data/lib/rsmp/proxy/modules/versions.rb +69 -0
  59. data/lib/rsmp/proxy/modules/watchdogs.rb +66 -0
  60. data/lib/rsmp/proxy/proxy.rb +199 -0
  61. data/lib/rsmp/proxy/site/modules/aggregated_status.rb +52 -0
  62. data/lib/rsmp/proxy/site/modules/alarms.rb +27 -0
  63. data/lib/rsmp/proxy/site/modules/commands.rb +31 -0
  64. data/lib/rsmp/proxy/site/modules/status.rb +110 -0
  65. data/lib/rsmp/proxy/site/site_proxy.rb +205 -0
  66. data/lib/rsmp/proxy/supervisor/modules/aggregated_status.rb +47 -0
  67. data/lib/rsmp/proxy/supervisor/modules/alarms.rb +73 -0
  68. data/lib/rsmp/proxy/supervisor/modules/commands.rb +53 -0
  69. data/lib/rsmp/proxy/supervisor/modules/status.rb +204 -0
  70. data/lib/rsmp/proxy/supervisor/supervisor_proxy.rb +178 -0
  71. data/lib/rsmp/tlc/detector_logic.rb +18 -34
  72. data/lib/rsmp/tlc/input_states.rb +126 -0
  73. data/lib/rsmp/tlc/modules/detector_logics.rb +50 -0
  74. data/lib/rsmp/tlc/modules/display.rb +78 -0
  75. data/lib/rsmp/tlc/modules/helpers.rb +41 -0
  76. data/lib/rsmp/tlc/modules/inputs.rb +173 -0
  77. data/lib/rsmp/tlc/modules/modes.rb +253 -0
  78. data/lib/rsmp/tlc/modules/outputs.rb +30 -0
  79. data/lib/rsmp/tlc/modules/plans.rb +218 -0
  80. data/lib/rsmp/tlc/modules/signal_groups.rb +109 -0
  81. data/lib/rsmp/tlc/modules/startup_sequence.rb +22 -0
  82. data/lib/rsmp/tlc/modules/system.rb +140 -0
  83. data/lib/rsmp/tlc/modules/traffic_data.rb +49 -0
  84. data/lib/rsmp/tlc/signal_group.rb +37 -41
  85. data/lib/rsmp/tlc/signal_plan.rb +14 -11
  86. data/lib/rsmp/tlc/signal_priority.rb +39 -35
  87. data/lib/rsmp/tlc/startup_sequence.rb +59 -0
  88. data/lib/rsmp/tlc/traffic_controller.rb +38 -1010
  89. data/lib/rsmp/tlc/traffic_controller_site.rb +58 -57
  90. data/lib/rsmp/version.rb +1 -1
  91. data/lib/rsmp.rb +82 -48
  92. data/rsmp.gemspec +24 -31
  93. metadata +79 -139
  94. data/lib/rsmp/archive.rb +0 -76
  95. data/lib/rsmp/collect/message_matchers.rb +0 -0
  96. data/lib/rsmp/component_base.rb +0 -87
  97. data/lib/rsmp/component_proxy.rb +0 -57
  98. data/lib/rsmp/components.rb +0 -65
  99. data/lib/rsmp/error.rb +0 -71
  100. data/lib/rsmp/logger.rb +0 -216
  101. data/lib/rsmp/proxy.rb +0 -693
  102. data/lib/rsmp/site.rb +0 -188
  103. data/lib/rsmp/site_proxy.rb +0 -389
  104. data/lib/rsmp/supervisor.rb +0 -302
  105. data/lib/rsmp/supervisor_proxy.rb +0 -510
  106. data/lib/rsmp/tlc/inputs.rb +0 -134
@@ -1,12 +1,10 @@
1
1
  module RSMP
2
-
3
2
  # Filter messages based on type, direction and component id.
4
3
  # Used by Collectors.
5
4
  class Filter
6
-
7
5
  attr_reader :ingoing, :outgoing, :type, :component
8
6
 
9
- def initialize ingoing:true, outgoing:true, type:nil, component:nil
7
+ def initialize(ingoing: true, outgoing: true, type: nil, component: nil)
10
8
  @ingoing = ingoing
11
9
  @outgoing = outgoing
12
10
  @type = type ? [type].flatten : nil
@@ -14,23 +12,41 @@ module RSMP
14
12
  end
15
13
 
16
14
  # Check a message against our match criteria
17
- # Return true if there's a match, false if not
18
- def accept? message
15
+ def accept?(message)
16
+ return false unless direction_matches?(message)
17
+ return false unless type_matches?(message)
18
+ return false unless component_matches?(message)
19
+
20
+ true
21
+ end
22
+
23
+ private
24
+
25
+ def direction_matches?(message)
19
26
  return false if message.direction == :in && @ingoing == false
20
27
  return false if message.direction == :out && @outgoing == false
21
- if @type
22
- unless message.is_a?(MessageNotAck)
23
- return false unless @type.include? message.type
24
- end
25
- end
26
- if @component
27
- return false if message.attributes['cId'] && message.attributes['cId'] != @component
28
- end
28
+
29
29
  true
30
30
  end
31
31
 
32
- def reject? message
32
+ def type_matches?(message)
33
+ return true unless @type
34
+ return true if message.is_a?(MessageNotAck)
35
+
36
+ @type.include?(message.type)
37
+ end
38
+
39
+ def component_matches?(message)
40
+ return true unless @component
41
+ return true unless message.attributes['cId']
42
+
43
+ message.attributes['cId'] == @component
44
+ end
45
+
46
+ public
47
+
48
+ def reject?(message)
33
49
  !accept?(message)
34
50
  end
35
51
  end
36
- end
52
+ end
@@ -1,10 +1,9 @@
1
1
  module RSMP
2
-
3
2
  # Class that matches a single status or command item
4
3
  class Matcher
5
4
  attr_reader :want, :got, :message
6
5
 
7
- def initialize want
6
+ def initialize(want)
8
7
  @want = want
9
8
  @got = nil
10
9
  @message = nil
@@ -17,18 +16,16 @@ module RSMP
17
16
 
18
17
  # Check an item and set @done to true if it matches
19
18
  # Store the item and corresponding message if there's a positive or negative match
20
- def perform_match item, message, block
19
+ def perform_match(item, _message, block)
21
20
  matched = match? item
22
- if matched != nil
23
- if block
24
- status = block.call(nil,item)
25
- matched = status if status == true || status == false
26
- end
21
+ if !matched.nil? && block
22
+ status = block.call(nil, item)
23
+ matched = status if [true, false].include?(status)
27
24
  end
28
25
  matched
29
26
  end
30
27
 
31
- def keep message, item
28
+ def keep(message, item)
32
29
  @message = message
33
30
  @got = item
34
31
  end
@@ -38,7 +35,6 @@ module RSMP
38
35
  @got = nil
39
36
  end
40
37
 
41
- def match? item
42
- end
38
+ def match?(item); end
43
39
  end
44
40
  end
@@ -7,7 +7,7 @@ module RSMP
7
7
 
8
8
  attr_reader :messages
9
9
 
10
- def initialize distributor, filter: nil, task:
10
+ def initialize(distributor, task:, filter: nil)
11
11
  initialize_receiver distributor, filter: filter
12
12
  @condition = Async::Notification.new
13
13
  @task = task
@@ -18,7 +18,7 @@ module RSMP
18
18
  @messages = []
19
19
  end
20
20
 
21
- def wait_for_message timeout: nil
21
+ def wait_for_message(timeout: nil)
22
22
  if @messages.empty?
23
23
  if timeout
24
24
  @task.with_timeout(timeout) { @condition.wait }
@@ -31,9 +31,9 @@ module RSMP
31
31
  raise RSMP::TimeoutError
32
32
  end
33
33
 
34
- def handle_message message
34
+ def handle_message(message)
35
35
  @messages << message
36
36
  @condition.signal
37
37
  end
38
38
  end
39
- end
39
+ end
@@ -1,12 +1,12 @@
1
1
  # Receives items from a Distributor, as long as it's
2
2
  # installed as a receiver.
3
- # Optionally can filter mesage using a Filter.
3
+ # Optionally filter mesage using a Filter.
4
4
 
5
5
  module RSMP
6
6
  module Receiver
7
7
  include Inspect
8
8
 
9
- def initialize_receiver distributor, filter: nil
9
+ def initialize_receiver(distributor, filter: nil)
10
10
  @distributor = distributor
11
11
  @filter = filter
12
12
  end
@@ -19,22 +19,20 @@ module RSMP
19
19
  @distributor.remove_receiver(self)
20
20
  end
21
21
 
22
- def receive message
23
- handle_message(message) if accept_message?(message)
22
+ def receive(message)
23
+ handle_message(message) if accept_message?(message)
24
24
  end
25
25
 
26
- def receive_error error, options={}
27
- end
26
+ def receive_error(error, options = {}); end
28
27
 
29
- def accept_message? message
30
- @filter == nil || @filter.accept?(message)
28
+ def accept_message?(message)
29
+ @filter.nil? || @filter.accept?(message)
31
30
  end
32
31
 
33
- def reject_message? message
32
+ def reject_message?(message)
34
33
  !accept_message?(message)
35
34
  end
36
35
 
37
- def handle_message message
38
- end
36
+ def handle_message(message); end
39
37
  end
40
- end
38
+ end
@@ -35,91 +35,103 @@ module RSMP
35
35
  attr_reader :matchers
36
36
 
37
37
  # Initialize with a list of wanted statuses
38
- def initialize proxy, want, options={}
39
- raise ArgumentError.new("num option cannot be used") if options[:num]
40
- super proxy, options
38
+ def initialize(proxy, want, options = {})
39
+ raise ArgumentError, 'num option cannot be used' if options[:num]
40
+
41
+ super(proxy, options)
41
42
  @matchers = want.map { |item| build_matcher item }
42
43
  end
43
44
 
44
45
  # Build a matcher object.
45
46
  # Sub-classes should override to use their own matcher classes.
46
- def build_matcher want
47
+ def build_matcher(want)
47
48
  Matcher.new want
48
49
  end
49
50
 
50
51
  # Get a results
51
- def matcher_result want
52
- matcher = @matchers.find { |q| q.want == want}
52
+ def matcher_result(want)
53
+ matcher = @matchers.find { |q| q.want == want }
53
54
  raise unless matcher
55
+
54
56
  matcher.got
55
57
  end
56
58
 
57
59
  # Get an array of the last item received for each matcher
58
60
  def reached
59
- @matchers.map { |matcher| matcher.got }.compact
61
+ @matchers.map(&:got).compact
60
62
  end
61
63
 
62
64
  # Get messages from results
63
65
  def messages
64
- @matchers.map { |matcher| matcher.message }.uniq.compact
66
+ @matchers.map(&:message).uniq.compact
65
67
  end
66
68
 
67
69
  # Return progress as completes matchers vs. total number of matchers
68
70
  def progress
69
71
  need = @matchers.size
70
- reached = @matchers.count { |matcher| matcher.done? }
72
+ reached = @matchers.count(&:done?)
71
73
  { need: need, reached: reached }
72
74
  end
73
75
 
74
76
  # Are there matchers left to type_match?
75
77
  def done?
76
- @matchers.all? { |matcher| matcher.done? }
78
+ @matchers.all?(&:done?)
77
79
  end
78
80
 
79
81
  # Get a simplified hash of matchers, with values set to either true or false,
80
82
  # indicating which matchers have been matched.
81
83
  def matcher_status
82
- @matchers.map { |matcher| [matcher.want, matcher.done?] }.to_h
84
+ @matchers.to_h { |matcher| [matcher.want, matcher.done?] }
83
85
  end
84
86
 
85
87
  # Get a simply array of bools, showing which matchers have been matched.
86
88
  def summary
87
- @matchers.map { |matcher| matcher.done? }
89
+ @matchers.map(&:done?)
90
+ end
91
+
92
+ def log_match_result(message, matched, matcher, item)
93
+ type = { true => 'match', false => 'mismatch' }[matched]
94
+ @distributor.log "#{@title.capitalize} #{message.m_id_short} collect #{type} #{matcher.want}, item #{item}",
95
+ level: :debug
96
+ end
97
+
98
+ def handle_match_result(matched, matcher, message, item)
99
+ return if matched.nil?
100
+
101
+ log_match_result(message, matched, matcher, item)
102
+ if matched == true
103
+ matcher.keep message, item
104
+ elsif matched == false
105
+ matcher.forget
106
+ end
88
107
  end
89
108
 
90
- # Check if a messages matches our criteria.
91
- # Match each matcher against each item in the message
92
- def perform_match message
93
- return false if super(message) == false
109
+ def perform_match(message)
110
+ return false if super == false
94
111
  return unless collecting?
95
- @matchers.each do |matcher| # look through matchers
96
- get_items(message).each do |item| # look through items in message
97
- matched = matcher.perform_match(item,message,@block)
98
- return unless collecting?
99
- if matched != nil
100
- type = {true=>'match',false=>'mismatch'}[matched]
101
- @distributor.log "#{@title.capitalize} #{message.m_id_short} collect #{type} #{matcher.want}, item #{item}", level: :debug
102
- if matched == true
103
- matcher.keep message, item
104
- elsif matched == false
105
- matcher.forget
106
- end
107
- end
112
+
113
+ @matchers.each do |matcher|
114
+ break unless collecting?
115
+
116
+ get_items(message).each do |item|
117
+ matched = matcher.perform_match(item, message, @block)
118
+ break unless collecting?
119
+
120
+ handle_match_result(matched, matcher, message, item)
108
121
  end
109
122
  end
110
123
  end
111
124
 
112
125
  # don't collect anything. Matcher will collect them instead
113
- def keep message
114
- end
126
+ def keep(message); end
115
127
 
116
128
  def describe
117
- @matchers.map {|q| q.want.to_s }
129
+ @matchers.map { |q| q.want.to_s }
118
130
  end
119
131
 
120
132
  # return a string that describes the attributes that we're looking for
121
133
  def describe_matcher
122
- "#{super} matching #{matcher_want_hash.to_s}"
134
+ "#{super} matching #{matcher_want_hash}"
123
135
  end
124
136
 
125
137
  # return a hash that describe the status of all matchers
@@ -128,33 +140,45 @@ module RSMP
128
140
  @matchers.each do |matcher|
129
141
  want = matcher.want
130
142
  if want['cCI']
131
- cCI = want['cCI']
132
- h[cCI] ||= {}
133
- cO = h['cO']
134
- n = h['n']
135
- v = h['v']
136
- h[cCI][cO] ||= {}
137
- h[cCI][cO][n] = v
143
+ process_command_matcher(h, matcher, want)
138
144
  elsif want['sCI']
139
- sCI = want['sCI']
140
- h[sCI] ||= {}
141
- n = want['n']
142
- s = want['s']
143
- if matcher.got && matcher.got['s']
144
- h[sCI][n] = { {s=>matcher.got['s']} => matcher.done? }
145
- else
146
- h[sCI][n] = { s=>nil }
147
- end
145
+ process_status_matcher(h, matcher, want)
148
146
  end
149
147
  end
150
148
  h
151
149
  end
152
150
 
151
+ private
152
+
153
+ def process_command_matcher(hash, _matcher, want)
154
+ cci = want['cCI']
155
+ hash[cci] ||= {}
156
+ co = want['cO']
157
+ n = want['n']
158
+ v = want['v']
159
+ hash[cci][co] ||= {}
160
+ hash[cci][co][n] = v
161
+ end
162
+
163
+ def process_status_matcher(hash, matcher, want)
164
+ sci = want['sCI']
165
+ hash[sci] ||= {}
166
+ n = want['n']
167
+ s = want['s']
168
+ hash[sci][n] = if matcher.got && matcher.got['s']
169
+ { { s => matcher.got['s'] } => matcher.done? }
170
+ else
171
+ { s => nil }
172
+ end
173
+ end
174
+
175
+ public
176
+
153
177
  # return a string that describe how many many messages have been collected
154
178
  def describe_progress
155
179
  num_matchers = @matchers.size
156
- num_matched = @matchers.count { |matcher| matcher.done? }
157
- ".. Matched #{num_matched}/#{num_matchers} with #{progress_hash.to_s}"
180
+ num_matched = @matchers.count(&:done?)
181
+ ".. Matched #{num_matched}/#{num_matchers} with #{progress_hash}"
158
182
  end
159
183
 
160
184
  def matcher_want_hash
@@ -162,44 +186,59 @@ module RSMP
162
186
  @matchers.each do |matcher|
163
187
  item = matcher.want
164
188
  if item['cCI']
165
- cCI = item['cCI']
166
- h[cCI] ||= {}
167
- cO = item['cO']
168
- h[cCI][cO] ||= {}
169
- n = item['n']
170
- v = item['v']
171
- h[cCI][cO][n] = v || :any
189
+ add_command_want_to_hash(h, item)
172
190
  elsif item['sCI']
173
- sCI = item['sCI']
174
- h[sCI] ||= {}
175
- n = item['n']
176
- s = item['s']
177
- h[sCI][n] = s || :any
191
+ add_status_want_to_hash(h, item)
178
192
  end
179
193
  end
180
194
  h
181
195
  end
182
196
 
183
- # return a hash that describe the end result
197
+ def add_command_want_to_hash(hash, item)
198
+ cci = item['cCI']
199
+ hash[cci] ||= {}
200
+ co = item['cO']
201
+ hash[cci][co] ||= {}
202
+ n = item['n']
203
+ v = item['v']
204
+ hash[cci][co][n] = v || :any
205
+ end
206
+
207
+ def add_status_want_to_hash(hash, item)
208
+ sci = item['sCI']
209
+ hash[sci] ||= {}
210
+ n = item['n']
211
+ s = item['s']
212
+ hash[sci][n] = s || :any
213
+ end
214
+
215
+ def add_command_result(hash, want, got)
216
+ cci = want['cCI']
217
+ hash[cci] ||= {}
218
+ co = want['cO']
219
+ hash[cci][co] ||= {}
220
+ n = want['n']
221
+ v = got ? got['v'] : nil
222
+ hash[cci][co][n] = v
223
+ end
224
+
225
+ def add_status_result(hash, want, got)
226
+ sci = want['sCI']
227
+ hash[sci] ||= {}
228
+ n = want['n']
229
+ s = got ? got['s'] : nil
230
+ hash[sci][n] = s
231
+ end
232
+
184
233
  def matcher_got_hash
185
234
  h = {}
186
235
  @matchers.each do |matcher|
187
236
  want = matcher.want
188
237
  got = matcher.got
189
238
  if want['cCI']
190
- cCI = want['cCI']
191
- h[cCI] ||= {}
192
- cO = want['cO']
193
- h[cCI][cO] ||= {}
194
- n = want['n']
195
- v = got ? got['v'] : nil
196
- h[cCI][cO][n] = v
239
+ add_command_result(h, want, got)
197
240
  elsif want['sCI']
198
- sCI = want['sCI']
199
- h[sCI] ||= {}
200
- n = want['n']
201
- s = got ? got['s'] : nil
202
- h[sCI][n] = s
241
+ add_status_result(h, want, got)
203
242
  end
204
243
  end
205
244
  h
@@ -207,7 +246,7 @@ module RSMP
207
246
 
208
247
  # log when we end collecting
209
248
  def log_complete
210
- @distributor.log "#{identifier}: Completed with #{matcher_got_hash.to_s}", level: :collect
249
+ @distributor.log "#{identifier}: Completed with #{matcher_got_hash}", level: :collect
211
250
  end
212
251
  end
213
252
  end
@@ -1,24 +1,24 @@
1
1
  module RSMP
2
2
  # Base class for waiting for status updates or responses
3
3
  class StatusCollector < StateCollector
4
- def initialize proxy, want, options={}
4
+ def initialize(proxy, want, options = {})
5
5
  type = []
6
6
  type << 'StatusUpdate' unless options[:updates] == false
7
7
  type << 'StatusResponse' unless options[:reponses] == false
8
8
 
9
- super proxy, want, options.merge(
9
+ super(proxy, want, options.merge(
10
10
  title: 'status response',
11
11
  filter: RSMP::Filter.new(ingoing: true, outgoing: false, type: type)
12
- )
12
+ ))
13
13
  end
14
14
 
15
- def build_matcher want
15
+ def build_matcher(want)
16
16
  RSMP::StatusMatcher.new want
17
17
  end
18
18
 
19
19
  # Get items, in our case status values
20
- def get_items message
20
+ def get_items(message)
21
21
  message.attributes['sS'] || []
22
22
  end
23
23
  end
24
- end
24
+ end
@@ -1,12 +1,16 @@
1
1
  module RSMP
2
- # Match a specific status response or update
3
2
  class StatusMatcher < Matcher
4
- # Match a status value against a matcher
5
- def match? item
6
- return nil if @want['sCI'] && @want['sCI'] != item['sCI']
7
- return nil if @want['cO'] && @want['cO'] != item['cO']
8
- return nil if @want['n'] && @want['n'] != item['n']
3
+ def match_code?(item)
4
+ return false if @want['sCI'] && @want['sCI'] != item['sCI']
5
+ return false if @want['cO'] && @want['cO'] != item['cO']
6
+ return false if @want['n'] && @want['n'] != item['n']
7
+
8
+ true
9
+ end
10
+
11
+ def match_value?(item)
9
12
  return false if @want['q'] && @want['q'] != item['q']
13
+
10
14
  if @want['s'].is_a? Regexp
11
15
  return false if item['s'] !~ @want['s']
12
16
  elsif @want['s']
@@ -14,5 +18,11 @@ module RSMP
14
18
  end
15
19
  true
16
20
  end
21
+
22
+ def match?(item)
23
+ return nil unless match_code?(item)
24
+
25
+ match_value?(item)
26
+ end
17
27
  end
18
- end
28
+ end