openc3 5.6.1 → 5.7.2
Sign up to get free protection for your applications and to get access to all the features.
Potentially problematic release.
This version of openc3 might be problematic. Click here for more details.
- checksums.yaml +4 -4
- data/Gemfile +4 -0
- data/bin/openc3cli +39 -6
- data/data/config/interface_modifiers.yaml +71 -0
- data/data/config/protocols.yaml +46 -0
- data/lib/openc3/interfaces/interface.rb +1 -0
- data/lib/openc3/interfaces/protocols/cobs_protocol.rb +120 -0
- data/lib/openc3/interfaces/protocols/slip_protocol.rb +150 -0
- data/lib/openc3/interfaces/protocols/terminated_protocol.rb +2 -1
- data/lib/openc3/io/json_api.rb +1 -1
- data/lib/openc3/microservices/interface_decom_common.rb +0 -1
- data/lib/openc3/models/interface_model.rb +75 -2
- data/lib/openc3/models/microservice_model.rb +1 -1
- data/lib/openc3/models/reaction_model.rb +0 -3
- data/lib/openc3/models/target_model.rb +1 -1
- data/lib/openc3/models/widget_model.rb +6 -2
- data/lib/openc3/operators/operator.rb +11 -9
- data/lib/openc3/packets/parsers/xtce_parser.rb +4 -2
- data/lib/openc3/script/api_shared.rb +27 -24
- data/lib/openc3/script/storage.rb +4 -0
- data/lib/openc3/tools/table_manager/table_manager_core.rb +4 -2
- data/lib/openc3/utilities/ruby_lex_utils.rb +4 -27
- data/lib/openc3/utilities/store_autoload.rb +1 -0
- data/lib/openc3/version.rb +6 -6
- data/templates/widget/package.json +8 -8
- data/templates/widget/yarn.lock +201 -155
- metadata +4 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: b2926debd9479ec12631eab7287a0a4ff480c8c4957f7702de4c148f5e87a376
|
4
|
+
data.tar.gz: 687f5c815c7016f34feb4f484cbcf582c8e5d3ef621098beb0d3aacf612c49c0
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 4a33e7fe434b726dc9231bcf066d112114ca3e8109496ee4c2742b8925d4c3297f22a7e3d43ec5592ba298969eafd9e37713754efc1556f257ae9b584e7ef38c
|
7
|
+
data.tar.gz: b552b42d338e23625ed78f7fb429deb59a456bd5ab7c783930fe050d8c5ec360c39e2630f39f005c9b370c5f3a49f8d943a04951990edb8e261c5d5e1ab0bd71
|
data/Gemfile
CHANGED
data/bin/openc3cli
CHANGED
@@ -141,18 +141,21 @@ def migrate(args)
|
|
141
141
|
|
142
142
|
# Overwrite plugin.txt with specified targets
|
143
143
|
plugin = File.open('plugin.txt', 'w')
|
144
|
-
|
145
|
-
|
144
|
+
FileUtils.mkdir 'targets'
|
146
145
|
args.each do |target|
|
147
146
|
puts "Migrating target #{target}"
|
148
147
|
FileUtils.cp_r "../config/targets/#{target}", 'targets'
|
149
|
-
plugin.puts "TARGET #{target}"
|
148
|
+
plugin.puts "TARGET #{target} #{target}"
|
150
149
|
end
|
151
150
|
plugin.puts ""
|
152
151
|
|
153
|
-
|
154
|
-
|
155
|
-
|
152
|
+
files = Dir.glob('../lib/*')
|
153
|
+
files.concat(Dir.glob('../procedures/*'))
|
154
|
+
unless files.empty?
|
155
|
+
puts "Migrating /lib & /procedures to PROCEDURES target"
|
156
|
+
FileUtils.cp_r '../lib', "targets/PROCEDURES"
|
157
|
+
FileUtils.cp_r '../procedures', "targets/PROCEDURES"
|
158
|
+
end
|
156
159
|
|
157
160
|
# Migrate cmd_tlm_server.txt info to plugin.txt
|
158
161
|
Dir.glob('targets/**/cmd_tlm_server*.txt') do |file|
|
@@ -168,6 +171,36 @@ def migrate(args)
|
|
168
171
|
end
|
169
172
|
plugin.puts ''
|
170
173
|
end
|
174
|
+
|
175
|
+
# Migrate target.txt
|
176
|
+
Dir.glob('targets/**/target.txt') do |filename|
|
177
|
+
file = File.read(filename)
|
178
|
+
file.gsub!('LOG_RAW', 'LOG_STREAM')
|
179
|
+
file.gsub!('AUTO_SCREEN_SUBSTITUTE', '')
|
180
|
+
File.write(filename, file)
|
181
|
+
end
|
182
|
+
|
183
|
+
# Migrate some of the screens api
|
184
|
+
Dir.glob('targets/**/screens/*') do |file|
|
185
|
+
screen = File.read(file)
|
186
|
+
screen.gsub!('cmd(', 'api.cmd(')
|
187
|
+
screen.gsub!('cmd_no_checks(', 'api.cmd_no_checks(')
|
188
|
+
screen.gsub!('cmd_no_range_check(', 'api.cmd_no_range_check(')
|
189
|
+
screen.gsub!('cmd_no_hazardous_check(', 'api.cmd_no_hazardous_check(')
|
190
|
+
screen.gsub!('get_named_widget(', 'screen.getNamedWidget(')
|
191
|
+
lines = screen.split("\n")
|
192
|
+
lines.map! do |line|
|
193
|
+
if line.include?('Qt.')
|
194
|
+
line = "# FIXME (no Qt): #{line.sub("<%", "< %").sub("%>", "% >")}"
|
195
|
+
elsif line.include?('Cosmos::')
|
196
|
+
line = "# FIXME (no Cosmos::): #{line.sub("<%", "< %").sub("%>", "% >")}"
|
197
|
+
else
|
198
|
+
line
|
199
|
+
end
|
200
|
+
end
|
201
|
+
File.write(file, lines.join("\n"))
|
202
|
+
end
|
203
|
+
|
171
204
|
plugin.close
|
172
205
|
puts "Plugin complete: #{File.expand_path('.')}" # Remember we're inside the plugin dir
|
173
206
|
end
|
@@ -168,3 +168,74 @@ SECRET:
|
|
168
168
|
example: |
|
169
169
|
SECRET ENV USERNAME ENV_USERNAME USERNAME
|
170
170
|
SECRET FILE KEY "/tmp/DATA/cert" KEY
|
171
|
+
ENV:
|
172
|
+
summary: Sets an environment variable in the microservice.
|
173
|
+
since: 5.7.0
|
174
|
+
parameters:
|
175
|
+
- name: Key
|
176
|
+
required: true
|
177
|
+
description: Environment variable name
|
178
|
+
values: .+
|
179
|
+
- name: Value
|
180
|
+
required: true
|
181
|
+
description: Environment variable value
|
182
|
+
values: .+
|
183
|
+
example: |
|
184
|
+
ENV COMPANY OpenC3
|
185
|
+
WORK_DIR:
|
186
|
+
summary: Set the working directory
|
187
|
+
description: Working directory to run the microservice CMD in. Can be a path relative to the microservice folder in the plugin, or an absolute path in the container the microservice runs in.
|
188
|
+
since: 5.7.0
|
189
|
+
parameters:
|
190
|
+
- name: Directory
|
191
|
+
required: true
|
192
|
+
description: Working directory to run the microservice CMD in. Can be a path relative to the microservice folder in the plugin, or an absolute path in the container the microservice runs in.
|
193
|
+
values: .+
|
194
|
+
example: |
|
195
|
+
WORK_DIR '/openc3/lib/openc3/microservices'
|
196
|
+
PORT:
|
197
|
+
summary: Open port for the microservice
|
198
|
+
description: Kubernetes needs a Service to be applied to open a port so this is required for Kubernetes support
|
199
|
+
since: 5.7.0
|
200
|
+
parameters:
|
201
|
+
- name: Number
|
202
|
+
required: true
|
203
|
+
description: Port number
|
204
|
+
values: \d+
|
205
|
+
- name: Protocol
|
206
|
+
required: false
|
207
|
+
description: Port protocol. Default is TCP.
|
208
|
+
values: .+
|
209
|
+
example: |
|
210
|
+
PORT 7272
|
211
|
+
CMD:
|
212
|
+
summary: Command line to execute to run the microservice.
|
213
|
+
description: Command line to execute to run the microservice.
|
214
|
+
since: 5.7.0
|
215
|
+
parameters:
|
216
|
+
- name: Args
|
217
|
+
required: true
|
218
|
+
description: One or more arguments to exec to run the microservice.
|
219
|
+
values: .+
|
220
|
+
example: |
|
221
|
+
CMD ruby interface_microservice.rb DEFAULT__INTERFACE__INT1
|
222
|
+
CONTAINER:
|
223
|
+
summary: Docker Container
|
224
|
+
description: Container to execute and run the microservice in. Only used in COSMOS Enterprise Edition.
|
225
|
+
since: 5.7.0
|
226
|
+
parameters:
|
227
|
+
- name: Args
|
228
|
+
required: false
|
229
|
+
description: Name of the container
|
230
|
+
values: .+
|
231
|
+
ROUTE_PREFIX:
|
232
|
+
summary: Prefix of route
|
233
|
+
description: Prefix of route to the microservice to expose externally with Traefik
|
234
|
+
since: 5.7.0
|
235
|
+
parameters:
|
236
|
+
- name: Route Prefix
|
237
|
+
required: true
|
238
|
+
description: Route prefix. Must be unique across all scopes. Something like /myprefix
|
239
|
+
values: .*
|
240
|
+
example: |
|
241
|
+
ROUTE_PREFIX /interface
|
data/data/config/protocols.yaml
CHANGED
@@ -288,3 +288,49 @@ TEMPLATE:
|
|
288
288
|
or response timeouts. 'DISCONNECT' to disconnect after errors. The default
|
289
289
|
is 'LOG' to log an error and continue.
|
290
290
|
values: ["LOG", "DISCONNECT"]
|
291
|
+
SLIP:
|
292
|
+
description:
|
293
|
+
The SLIP Protocol implements RFC 1055. This is a terminated protocol which terminates
|
294
|
+
with a 0xC0 character, and escapes internally conflicting bytes.
|
295
|
+
parameters:
|
296
|
+
- name: Start Character
|
297
|
+
required: false
|
298
|
+
description:
|
299
|
+
Character to place at the beginning of a packet. Defaults to nil. Some variants of the
|
300
|
+
SLIP Protocol also place a 0xC0 byte at the beginning of packets.
|
301
|
+
values: \d+
|
302
|
+
- name: Read Strip Characters
|
303
|
+
required: false
|
304
|
+
description:
|
305
|
+
Whether or not to strip the start and end characters out of the packet when reading. Defaults
|
306
|
+
to true.
|
307
|
+
values: ["true", "false"]
|
308
|
+
- name: Read Enable Escaping
|
309
|
+
required: false
|
310
|
+
description: Whether or not to escape conflicting characters in the packet om reads. Defaults to true.
|
311
|
+
values: ["true", "false"]
|
312
|
+
- name: Write Enable Escaping
|
313
|
+
required: false
|
314
|
+
description: Whether or not to escape conflicting characters in the packet on writes. Defaults to true.
|
315
|
+
values: ["true", "false"]
|
316
|
+
- name: End Character
|
317
|
+
required: false
|
318
|
+
description: Character to end packets with. Defaults to 0xC0.
|
319
|
+
values: \d+
|
320
|
+
- name: Escape Character
|
321
|
+
required: false
|
322
|
+
description: Character that indicates an escape sequence. Defaults to 0xDB.
|
323
|
+
values: \d+
|
324
|
+
- name: Escaped End Character
|
325
|
+
required: false
|
326
|
+
description: Escaped version of the end character. Defaults to 0xDC.
|
327
|
+
values: \d+
|
328
|
+
- name: Escaped Escape Character
|
329
|
+
required: false
|
330
|
+
description: Escaped version of the escape character. Defaults to 0xDD.
|
331
|
+
values: \d+
|
332
|
+
COBS:
|
333
|
+
description:
|
334
|
+
The COBS Protocol implements the Consistent Overhead Byte Stuffing Protocol. This is a terminated protocol which terminates
|
335
|
+
with a 0x00 character, and escapes internal 0's using a unique algorithm that only adds one byte of overhead for every
|
336
|
+
254 bytes.
|
@@ -0,0 +1,120 @@
|
|
1
|
+
# encoding: ascii-8bit
|
2
|
+
|
3
|
+
# Copyright 2023 OpenC3, Inc.
|
4
|
+
# All Rights Reserved.
|
5
|
+
#
|
6
|
+
# This program is free software; you can modify and/or redistribute it
|
7
|
+
# under the terms of the GNU Affero General Public License
|
8
|
+
# as published by the Free Software Foundation; version 3 with
|
9
|
+
# attribution addendums as found in the LICENSE.txt
|
10
|
+
#
|
11
|
+
# This program is distributed in the hope that it will be useful,
|
12
|
+
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
13
|
+
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
14
|
+
# GNU Affero General Public License for more details.
|
15
|
+
#
|
16
|
+
# This file may also be used under the terms of a commercial license
|
17
|
+
# if purchased from OpenC3, Inc.
|
18
|
+
|
19
|
+
require 'openc3/interfaces/protocols/terminated_protocol'
|
20
|
+
require 'openc3/config/config_parser'
|
21
|
+
|
22
|
+
# This file implements the COBS protocol as here:
|
23
|
+
# https://en.wikipedia.org/wiki/Consistent_Overhead_Byte_Stuffing
|
24
|
+
# http://www.stuartcheshire.org/papers/COBSforToN.pdf
|
25
|
+
|
26
|
+
# COBS is a framing protocol and is therefore expected to be used for packet deliniation
|
27
|
+
|
28
|
+
module OpenC3
|
29
|
+
|
30
|
+
# Usage in plugin.txt:
|
31
|
+
#
|
32
|
+
# INTERFACE ...
|
33
|
+
# PROTOCOL READ_WRITE CobsProtocol
|
34
|
+
|
35
|
+
class CobsProtocol < TerminatedProtocol
|
36
|
+
|
37
|
+
# @param allow_empty_data [true/false/nil] See Protocol#initialize
|
38
|
+
def initialize(allow_empty_data = nil)
|
39
|
+
|
40
|
+
strip_read_termination = true
|
41
|
+
discard_leading_bytes = 0
|
42
|
+
sync_pattern = nil
|
43
|
+
fill_fields = false # Handled in write_data below
|
44
|
+
|
45
|
+
super(
|
46
|
+
"", # Write termination handled in write_data below
|
47
|
+
"00",
|
48
|
+
strip_read_termination,
|
49
|
+
discard_leading_bytes,
|
50
|
+
sync_pattern,
|
51
|
+
fill_fields,
|
52
|
+
allow_empty_data
|
53
|
+
)
|
54
|
+
end
|
55
|
+
|
56
|
+
def read_data(data)
|
57
|
+
data = super(data)
|
58
|
+
return data if data.length <= 0 or Symbol === data
|
59
|
+
|
60
|
+
result_data = ''
|
61
|
+
while data.length > 1
|
62
|
+
# Read the offset to the next zero byte
|
63
|
+
# Note: This may be off the end of the data. If so, the packet is over
|
64
|
+
zero_offset = data[0].unpack('C')[0]
|
65
|
+
if zero_offset == 0xFF # No zeros in this segment
|
66
|
+
result_data << data[1..254]
|
67
|
+
data = data[255..-1]
|
68
|
+
elsif zero_offset <= 1 # End of data or 1 zero
|
69
|
+
result_data << "\x00"
|
70
|
+
data = data[1..-1]
|
71
|
+
else # Mid range zero or end of packet
|
72
|
+
result_data << data[1..(zero_offset - 1)]
|
73
|
+
data = data[zero_offset..-1]
|
74
|
+
result_data << "\x00" if data.length >= 1
|
75
|
+
end
|
76
|
+
end
|
77
|
+
|
78
|
+
return result_data
|
79
|
+
end
|
80
|
+
|
81
|
+
def write_data(data)
|
82
|
+
# Intentionally not calling super()
|
83
|
+
|
84
|
+
need_insert = false
|
85
|
+
result_data = ''
|
86
|
+
while data.length > 0
|
87
|
+
index = data.index("\x00")
|
88
|
+
if (index and index > 253) or (index.nil? and data.length >= 254)
|
89
|
+
result_data << "\xFF"
|
90
|
+
result_data << data[0..253]
|
91
|
+
data = data[254..-1]
|
92
|
+
need_insert = false
|
93
|
+
else # index <= 254 or (index.nil? and data.length < 254)
|
94
|
+
if index
|
95
|
+
result_data << [index + 1].pack('C')
|
96
|
+
if index >= 1
|
97
|
+
result_data << data[0..(index - 1)]
|
98
|
+
end
|
99
|
+
data = data[(index + 1)..-1]
|
100
|
+
need_insert = true
|
101
|
+
else
|
102
|
+
result_data << [data.length + 1].pack('C')
|
103
|
+
result_data << data
|
104
|
+
data = ''
|
105
|
+
need_insert = false
|
106
|
+
end
|
107
|
+
end
|
108
|
+
end
|
109
|
+
|
110
|
+
# Handle a zero at the end of the packet
|
111
|
+
result_data << "\x01" if need_insert
|
112
|
+
|
113
|
+
# Terminate message with 0x00
|
114
|
+
result_data << "\x00"
|
115
|
+
|
116
|
+
return result_data
|
117
|
+
end
|
118
|
+
end
|
119
|
+
|
120
|
+
end
|
@@ -0,0 +1,150 @@
|
|
1
|
+
# encoding: ascii-8bit
|
2
|
+
|
3
|
+
# Copyright 2023 OpenC3, Inc.
|
4
|
+
# All Rights Reserved.
|
5
|
+
#
|
6
|
+
# This program is free software; you can modify and/or redistribute it
|
7
|
+
# under the terms of the GNU Affero General Public License
|
8
|
+
# as published by the Free Software Foundation; version 3 with
|
9
|
+
# attribution addendums as found in the LICENSE.txt
|
10
|
+
#
|
11
|
+
# This program is distributed in the hope that it will be useful,
|
12
|
+
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
13
|
+
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
14
|
+
# GNU Affero General Public License for more details.
|
15
|
+
#
|
16
|
+
# This file may also be used under the terms of a commercial license
|
17
|
+
# if purchased from OpenC3, Inc.
|
18
|
+
|
19
|
+
require 'openc3/interfaces/protocols/terminated_protocol'
|
20
|
+
require 'openc3/config/config_parser'
|
21
|
+
|
22
|
+
# This file implements the SLIP protocol as documented in RFC 1055
|
23
|
+
# https://datatracker.ietf.org/doc/html/rfc1055
|
24
|
+
|
25
|
+
# SLIP is a framing protocol and is therefore expected to be used for packet deliniation
|
26
|
+
|
27
|
+
module OpenC3
|
28
|
+
|
29
|
+
# Usage in plugin.txt:
|
30
|
+
#
|
31
|
+
# INTERFACE ...
|
32
|
+
# PROTOCOL READ_WRITE SlipProtocol
|
33
|
+
|
34
|
+
class SlipProtocol < TerminatedProtocol
|
35
|
+
|
36
|
+
# Note: Characters are expected to be given as integers
|
37
|
+
# @param start_char [Integer/nil] Character to place at the start of frames (Defaults to nil)
|
38
|
+
# @param read_strip_characters [true/false] Strip off start_char and end_char from reads
|
39
|
+
# @param read_enable_escaping [true/false] Whether to enable or disable character escaping on reads
|
40
|
+
# @param write_enable_escaping [true/false] Whether to enable or disable character escaping on writes
|
41
|
+
# @param end_char [Integer] Character to place at the end of frames (Defaults to 0xC0)
|
42
|
+
# @param esc_char [Integer] Escape character (Defaults to 0xDB)
|
43
|
+
# @param esc_end_char [Integer] Character to Escape End character (Defaults to 0xDC)
|
44
|
+
# @param esc_esc_char [Integer] Character to Escape Escape character (Defaults to 0xDD)
|
45
|
+
# @param allow_empty_data [true/false/nil] See Protocol#initialize
|
46
|
+
def initialize(
|
47
|
+
start_char = nil,
|
48
|
+
read_strip_characters = true,
|
49
|
+
read_enable_escaping = true,
|
50
|
+
write_enable_escaping = true,
|
51
|
+
end_char = 0xC0,
|
52
|
+
esc_char = 0xDB,
|
53
|
+
esc_end_char = 0xDC,
|
54
|
+
esc_esc_char = 0xDD,
|
55
|
+
allow_empty_data = nil)
|
56
|
+
|
57
|
+
@start_char = ConfigParser.handle_nil(start_char)
|
58
|
+
@start_char = [Integer(end_char)].pack('C') if @start_char
|
59
|
+
@end_char = [Integer(end_char)].pack('C')
|
60
|
+
@esc_char = [Integer(esc_char)].pack('C')
|
61
|
+
@esc_end_char = [Integer(esc_end_char)].pack('C')
|
62
|
+
@esc_esc_char = [Integer(esc_esc_char)].pack('C')
|
63
|
+
@replace_end = @esc_char + @esc_end_char
|
64
|
+
@replace_esc = @esc_char + @esc_esc_char
|
65
|
+
@read_strip_characters = ConfigParser.handle_true_false(read_strip_characters)
|
66
|
+
raise "read_strip_characters must be true or false" if @read_strip_characters != true and @read_strip_characters != false
|
67
|
+
@read_enable_escaping = ConfigParser.handle_true_false(read_enable_escaping)
|
68
|
+
raise "read_enable_escaping must be true or false" if @read_enable_escaping != true and @read_enable_escaping != false
|
69
|
+
@write_enable_escaping = ConfigParser.handle_true_false(write_enable_escaping)
|
70
|
+
raise "write_enable_escaping must be true or false" if @write_enable_escaping != true and @write_enable_escaping != false
|
71
|
+
|
72
|
+
strip_read_termination = false
|
73
|
+
discard_leading_bytes = 0
|
74
|
+
if @start_char
|
75
|
+
sync_pattern = sprintf("%0X", Integer(start_char))
|
76
|
+
else
|
77
|
+
sync_pattern = nil
|
78
|
+
end
|
79
|
+
fill_fields = false # Handled in write_data below
|
80
|
+
|
81
|
+
super(
|
82
|
+
"", # Write termination handled in write_data below
|
83
|
+
sprintf("%0X", Integer(end_char)), # Expects Hex Character String
|
84
|
+
strip_read_termination,
|
85
|
+
discard_leading_bytes,
|
86
|
+
sync_pattern,
|
87
|
+
fill_fields,
|
88
|
+
allow_empty_data
|
89
|
+
)
|
90
|
+
end
|
91
|
+
|
92
|
+
def read_data(data)
|
93
|
+
data = super(data)
|
94
|
+
return data if data.length <= 0 or Symbol === data
|
95
|
+
|
96
|
+
if @read_strip_characters
|
97
|
+
if @start_char
|
98
|
+
data = data[1..-1]
|
99
|
+
end
|
100
|
+
data = data[0..-2]
|
101
|
+
end
|
102
|
+
|
103
|
+
if @read_enable_escaping
|
104
|
+
data = data.gsub(@replace_end, @end_char).gsub(@replace_esc, @esc_char)
|
105
|
+
end
|
106
|
+
|
107
|
+
return data
|
108
|
+
end
|
109
|
+
|
110
|
+
def write_data(data)
|
111
|
+
# Intentionally not calling super()
|
112
|
+
|
113
|
+
if @write_enable_escaping
|
114
|
+
data = data.gsub(@esc_char, @replace_esc).gsub(@end_char, @replace_end)
|
115
|
+
end
|
116
|
+
|
117
|
+
if @start_char
|
118
|
+
data = @start_char + data
|
119
|
+
end
|
120
|
+
|
121
|
+
data << @end_char
|
122
|
+
|
123
|
+
return data
|
124
|
+
end
|
125
|
+
|
126
|
+
def reduce_to_single_packet
|
127
|
+
return :STOP if @data.length <= 0
|
128
|
+
if @start_char
|
129
|
+
index = @data[1..-1].index(@read_termination_characters)
|
130
|
+
index = index + 1 if index
|
131
|
+
else
|
132
|
+
index = @data.index(@read_termination_characters)
|
133
|
+
end
|
134
|
+
|
135
|
+
# Reduce to packet data and setup current_data for next packet
|
136
|
+
if index
|
137
|
+
if index > 0
|
138
|
+
packet_data = @data[0..(index + @read_termination_characters.length - 1)]
|
139
|
+
else # @data begins with the termination characters
|
140
|
+
packet_data = @data[0..(@read_termination_characters.length - 1)]
|
141
|
+
end
|
142
|
+
@data.replace(@data[(index + @read_termination_characters.length)..-1])
|
143
|
+
return packet_data
|
144
|
+
else
|
145
|
+
return :STOP
|
146
|
+
end
|
147
|
+
end
|
148
|
+
end
|
149
|
+
|
150
|
+
end
|
@@ -17,7 +17,7 @@
|
|
17
17
|
# All changes Copyright 2022, OpenC3, Inc.
|
18
18
|
# All Rights Reserved
|
19
19
|
#
|
20
|
-
# This file may also be used under the terms of a commercial license
|
20
|
+
# This file may also be used under the terms of a commercial license
|
21
21
|
# if purchased from OpenC3, Inc.
|
22
22
|
|
23
23
|
require 'openc3/config/config_parser'
|
@@ -52,6 +52,7 @@ module OpenC3
|
|
52
52
|
@write_termination_characters = write_termination_characters.hex_to_byte_string
|
53
53
|
@read_termination_characters = read_termination_characters.hex_to_byte_string
|
54
54
|
@strip_read_termination = ConfigParser.handle_true_false(strip_read_termination)
|
55
|
+
raise "strip_read_termination must be true or false" if @strip_read_termination != true and @strip_read_termination != false
|
55
56
|
|
56
57
|
super(discard_leading_bytes, sync_pattern, fill_fields, allow_empty_data)
|
57
58
|
end
|
data/lib/openc3/io/json_api.rb
CHANGED
@@ -65,7 +65,7 @@ module OpenC3
|
|
65
65
|
|
66
66
|
def _request(*method_params, **kw_params)
|
67
67
|
kw_params[:scope] = $openc3_scope unless kw_params[:scope]
|
68
|
-
kw_params[:json]
|
68
|
+
kw_params[:json] = true unless kw_params[:json]
|
69
69
|
@json_api.request(*method_params, **kw_params)
|
70
70
|
end
|
71
71
|
end
|
@@ -44,6 +44,12 @@ module OpenC3
|
|
44
44
|
attr_accessor :log_stream
|
45
45
|
attr_accessor :needs_dependencies
|
46
46
|
attr_accessor :secrets
|
47
|
+
attr_accessor :cmd
|
48
|
+
attr_accessor :container
|
49
|
+
attr_accessor :env
|
50
|
+
attr_accessor :work_dir
|
51
|
+
attr_accessor :ports
|
52
|
+
attr_accessor :prefix
|
47
53
|
|
48
54
|
# NOTE: The following three class methods are used by the ModelController
|
49
55
|
# and are reimplemented to enable various Model class methods to work
|
@@ -109,6 +115,12 @@ module OpenC3
|
|
109
115
|
plugin: nil,
|
110
116
|
needs_dependencies: false,
|
111
117
|
secrets: [],
|
118
|
+
cmd: nil,
|
119
|
+
work_dir: '/openc3/lib/openc3/microservices',
|
120
|
+
ports: [],
|
121
|
+
env: {},
|
122
|
+
container: nil,
|
123
|
+
prefix: nil,
|
112
124
|
scope:
|
113
125
|
)
|
114
126
|
if self.class._get_type == 'INTERFACE'
|
@@ -129,6 +141,17 @@ module OpenC3
|
|
129
141
|
@protocols = protocols
|
130
142
|
@log_stream = log_stream
|
131
143
|
@needs_dependencies = needs_dependencies
|
144
|
+
@cmd = cmd
|
145
|
+
unless @cmd
|
146
|
+
type = self.class._get_type
|
147
|
+
microservice_name = "#{@scope}__#{type}__#{@name}"
|
148
|
+
@cmd = ["ruby", "#{type.downcase}_microservice.rb", microservice_name]
|
149
|
+
end
|
150
|
+
@work_dir = work_dir
|
151
|
+
@ports = ports
|
152
|
+
@env = env
|
153
|
+
@container = container
|
154
|
+
@prefix = prefix
|
132
155
|
@secrets = secrets
|
133
156
|
end
|
134
157
|
|
@@ -187,6 +210,12 @@ module OpenC3
|
|
187
210
|
'plugin' => @plugin,
|
188
211
|
'needs_dependencies' => @needs_dependencies,
|
189
212
|
'secrets' => @secrets.as_json(*a),
|
213
|
+
'cmd' => @cmd,
|
214
|
+
'work_dir' => @work_dir,
|
215
|
+
'ports' => @ports,
|
216
|
+
'env' => @env,
|
217
|
+
'container' => @container,
|
218
|
+
'prefix' => @prefix,
|
190
219
|
'updated_at' => @updated_at
|
191
220
|
}
|
192
221
|
end
|
@@ -266,6 +295,46 @@ module OpenC3
|
|
266
295
|
@secrets[-1] << parameters[4]
|
267
296
|
end
|
268
297
|
|
298
|
+
when 'ENV'
|
299
|
+
parser.verify_num_parameters(2, 2, "#{keyword} <Key> <Value>")
|
300
|
+
@env[parameters[0]] = parameters[1]
|
301
|
+
|
302
|
+
when 'PORT'
|
303
|
+
usage = "PORT <Number> <Protocol (Optional)"
|
304
|
+
parser.verify_num_parameters(1, 2, usage)
|
305
|
+
begin
|
306
|
+
@ports << [Integer(parameters[0])]
|
307
|
+
rescue # In case Integer fails
|
308
|
+
raise ConfigParser::Error.new(parser, "Port must be an integer: #{parameters[0]}", usage)
|
309
|
+
end
|
310
|
+
protocol = ConfigParser.handle_nil(parameters[1])
|
311
|
+
if protocol
|
312
|
+
# Per https://kubernetes.io/docs/concepts/services-networking/service/#protocol-support
|
313
|
+
if %w(TCP UDP SCTP).include?(protocol.upcase)
|
314
|
+
@ports[-1] << protocol.upcase
|
315
|
+
else
|
316
|
+
raise ConfigParser::Error.new(parser, "Unknown port protocol: #{parameters[1]}", usage)
|
317
|
+
end
|
318
|
+
else
|
319
|
+
@ports[-1] << 'TCP'
|
320
|
+
end
|
321
|
+
|
322
|
+
when 'WORK_DIR'
|
323
|
+
parser.verify_num_parameters(1, 1, "#{keyword} <Dir>")
|
324
|
+
@work_dir = parameters[0]
|
325
|
+
|
326
|
+
when 'CMD'
|
327
|
+
parser.verify_num_parameters(1, nil, "#{keyword} <Args>")
|
328
|
+
@cmd = parameters.dup
|
329
|
+
|
330
|
+
when 'CONTAINER'
|
331
|
+
parser.verify_num_parameters(1, 1, "#{keyword} <Container Image Name>")
|
332
|
+
@container = parameters[0]
|
333
|
+
|
334
|
+
when 'ROUTE_PREFIX'
|
335
|
+
parser.verify_num_parameters(1, 1, "#{keyword} <Route Prefix>")
|
336
|
+
@prefix = parameters[0]
|
337
|
+
|
269
338
|
else
|
270
339
|
raise ConfigParser::Error.new(parser, "Unknown keyword and parameters for Interface/Router: #{keyword} #{parameters.join(" ")}")
|
271
340
|
|
@@ -280,12 +349,16 @@ module OpenC3
|
|
280
349
|
microservice_name = "#{@scope}__#{type}__#{@name}"
|
281
350
|
microservice = MicroserviceModel.new(
|
282
351
|
name: microservice_name,
|
283
|
-
work_dir:
|
284
|
-
cmd:
|
352
|
+
work_dir: @work_dir,
|
353
|
+
cmd: @cmd,
|
354
|
+
env: @env,
|
355
|
+
ports: @ports,
|
356
|
+
container: @container,
|
285
357
|
target_names: @target_names,
|
286
358
|
plugin: @plugin,
|
287
359
|
needs_dependencies: @needs_dependencies,
|
288
360
|
secrets: @secrets,
|
361
|
+
prefix: @prefix,
|
289
362
|
scope: @scope
|
290
363
|
)
|
291
364
|
unless validate_only
|
@@ -168,7 +168,7 @@ module OpenC3
|
|
168
168
|
protocol = ConfigParser.handle_nil(parameters[1])
|
169
169
|
if protocol
|
170
170
|
# Per https://kubernetes.io/docs/concepts/services-networking/service/#protocol-support
|
171
|
-
if %w(TCP UDP SCTP
|
171
|
+
if %w(TCP UDP SCTP).include?(protocol.upcase)
|
172
172
|
@ports[-1] << protocol.upcase
|
173
173
|
else
|
174
174
|
raise ConfigParser::Error.new(parser, "Unknown port protocol: #{parameters[1]}", usage)
|
@@ -108,9 +108,6 @@ module OpenC3
|
|
108
108
|
unless snooze.is_a?(Integer)
|
109
109
|
raise ReactionInputError.new "invalid snooze value: #{snooze}"
|
110
110
|
end
|
111
|
-
if snooze < 30
|
112
|
-
raise ReactionInputError.new "invalid snooze: '#{snooze}' must be greater than 30"
|
113
|
-
end
|
114
111
|
return snooze
|
115
112
|
end
|
116
113
|
|
@@ -227,7 +227,7 @@ module OpenC3
|
|
227
227
|
raise "Unknown type #{type} for #{target_name} #{packet_name}" unless VALID_TYPES.include?(type)
|
228
228
|
|
229
229
|
begin
|
230
|
-
Store.hset("#{scope}
|
230
|
+
Store.hset("#{scope}__openc3#{type.to_s.downcase}__#{target_name}", packet_name, JSON.generate(packet.as_json(:allow_nan => true)))
|
231
231
|
rescue JSON::GeneratorError => err
|
232
232
|
Logger.error("Invalid text present in #{target_name} #{packet_name} #{type.to_s.downcase} packet")
|
233
233
|
raise err
|