aprsd 4.0.2__py3-none-any.whl → 4.1.0__py3-none-any.whl

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.
@@ -1,6 +1,7 @@
1
1
  import datetime
2
2
  import logging
3
3
  import select
4
+ import socket
4
5
  import threading
5
6
 
6
7
  import aprslib
@@ -18,7 +19,7 @@ from aprslib.exceptions import (
18
19
  import aprsd
19
20
  from aprsd.packets import core
20
21
 
21
- LOG = logging.getLogger("APRSD")
22
+ LOG = logging.getLogger('APRSD')
22
23
 
23
24
 
24
25
  class Aprsdis(aprslib.IS):
@@ -31,7 +32,7 @@ class Aprsdis(aprslib.IS):
31
32
  aprsd_keepalive = datetime.datetime.now()
32
33
 
33
34
  # Which server we are connected to?
34
- server_string = "None"
35
+ server_string = 'None'
35
36
 
36
37
  # timeout in seconds
37
38
  select_timeout = 1
@@ -39,10 +40,10 @@ class Aprsdis(aprslib.IS):
39
40
 
40
41
  def stop(self):
41
42
  self.thread_stop = True
42
- LOG.warning("Shutdown Aprsdis client.")
43
+ LOG.warning('Shutdown Aprsdis client.')
43
44
 
44
45
  def close(self):
45
- LOG.warning("Closing Aprsdis client.")
46
+ LOG.warning('Closing Aprsdis client.')
46
47
  super().close()
47
48
 
48
49
  @wrapt.synchronized(lock)
@@ -54,6 +55,57 @@ class Aprsdis(aprslib.IS):
54
55
  """If the connection is alive or not."""
55
56
  return self._connected
56
57
 
58
+ def _connect(self):
59
+ """
60
+ Attemps connection to the server
61
+ """
62
+
63
+ self.logger.info(
64
+ 'Attempting connection to %s:%s', self.server[0], self.server[1]
65
+ )
66
+
67
+ try:
68
+ self._open_socket()
69
+
70
+ peer = self.sock.getpeername()
71
+
72
+ self.logger.info('Connected to %s', str(peer))
73
+
74
+ # 5 second timeout to receive server banner
75
+ self.sock.setblocking(1)
76
+ self.sock.settimeout(5)
77
+
78
+ self.sock.setsockopt(socket.SOL_SOCKET, socket.SO_KEEPALIVE, 1)
79
+ # MACOS doesn't have TCP_KEEPIDLE
80
+ if hasattr(socket, 'TCP_KEEPIDLE'):
81
+ self.sock.setsockopt(socket.IPPROTO_TCP, socket.TCP_KEEPIDLE, 1)
82
+ self.sock.setsockopt(socket.IPPROTO_TCP, socket.TCP_KEEPINTVL, 3)
83
+ self.sock.setsockopt(socket.IPPROTO_TCP, socket.TCP_KEEPCNT, 5)
84
+
85
+ banner = self.sock.recv(512)
86
+ if is_py3:
87
+ banner = banner.decode('latin-1')
88
+
89
+ if banner[0] == '#':
90
+ self.logger.debug('Banner: %s', banner.rstrip())
91
+ else:
92
+ raise ConnectionError('invalid banner from server')
93
+
94
+ except ConnectionError as e:
95
+ self.logger.error(str(e))
96
+ self.close()
97
+ raise
98
+ except (socket.error, socket.timeout) as e:
99
+ self.close()
100
+
101
+ self.logger.error('Socket error: %s' % str(e))
102
+ if str(e) == 'timed out':
103
+ raise ConnectionError('no banner from server') from e
104
+ else:
105
+ raise ConnectionError(e) from e
106
+
107
+ self._connected = True
108
+
57
109
  def _socket_readlines(self, blocking=False):
58
110
  """
59
111
  Generator for complete lines, received from the server
@@ -61,12 +113,12 @@ class Aprsdis(aprslib.IS):
61
113
  try:
62
114
  self.sock.setblocking(0)
63
115
  except OSError as e:
64
- self.logger.error(f"socket error when setblocking(0): {str(e)}")
65
- raise aprslib.ConnectionDrop("connection dropped")
116
+ self.logger.error(f'socket error when setblocking(0): {str(e)}')
117
+ raise aprslib.ConnectionDrop('connection dropped') from e
66
118
 
67
119
  while not self.thread_stop:
68
- short_buf = b""
69
- newline = b"\r\n"
120
+ short_buf = b''
121
+ newline = b'\r\n'
70
122
 
71
123
  # set a select timeout, so we get a chance to exit
72
124
  # when user hits CTRL-C
@@ -91,11 +143,11 @@ class Aprsdis(aprslib.IS):
91
143
  # We could just not be blocking, so empty is expected
92
144
  continue
93
145
  else:
94
- self.logger.error("socket.recv(): returned empty")
95
- raise aprslib.ConnectionDrop("connection dropped")
146
+ self.logger.error('socket.recv(): returned empty')
147
+ raise aprslib.ConnectionDrop('connection dropped')
96
148
  except OSError as e:
97
149
  # self.logger.error("socket error on recv(): %s" % str(e))
98
- if "Resource temporarily unavailable" in str(e):
150
+ if 'Resource temporarily unavailable' in str(e):
99
151
  if not blocking:
100
152
  if len(self.buf) == 0:
101
153
  break
@@ -111,22 +163,22 @@ class Aprsdis(aprslib.IS):
111
163
  """
112
164
  Sends login string to server
113
165
  """
114
- login_str = "user {0} pass {1} vers github.com/craigerl/aprsd {3}{2}\r\n"
166
+ login_str = 'user {0} pass {1} vers Python-APRSD {3}{2}\r\n'
115
167
  login_str = login_str.format(
116
168
  self.callsign,
117
169
  self.passwd,
118
- (" filter " + self.filter) if self.filter != "" else "",
170
+ (' filter ' + self.filter) if self.filter != '' else '',
119
171
  aprsd.__version__,
120
172
  )
121
173
 
122
- self.logger.debug("Sending login information")
174
+ self.logger.debug('Sending login information')
123
175
 
124
176
  try:
125
177
  self._sendall(login_str)
126
178
  self.sock.settimeout(5)
127
179
  test = self.sock.recv(len(login_str) + 100)
128
180
  if is_py3:
129
- test = test.decode("latin-1")
181
+ test = test.decode('latin-1')
130
182
  test = test.rstrip()
131
183
 
132
184
  self.logger.debug("Server: '%s'", test)
@@ -134,26 +186,26 @@ class Aprsdis(aprslib.IS):
134
186
  if not test:
135
187
  raise LoginError(f"Server Response Empty: '{test}'")
136
188
 
137
- _, _, callsign, status, e = test.split(" ", 4)
138
- s = e.split(",")
189
+ _, _, callsign, status, e = test.split(' ', 4)
190
+ s = e.split(',')
139
191
  if len(s):
140
- server_string = s[0].replace("server ", "")
192
+ server_string = s[0].replace('server ', '')
141
193
  else:
142
- server_string = e.replace("server ", "")
194
+ server_string = e.replace('server ', '')
143
195
 
144
- if callsign == "":
145
- raise LoginError("Server responded with empty callsign???")
196
+ if callsign == '':
197
+ raise LoginError('Server responded with empty callsign???')
146
198
  if callsign != self.callsign:
147
- raise LoginError(f"Server: {test}")
148
- if status != "verified," and self.passwd != "-1":
149
- raise LoginError("Password is incorrect")
199
+ raise LoginError(f'Server: {test}')
200
+ if status != 'verified,' and self.passwd != '-1':
201
+ raise LoginError('Password is incorrect')
150
202
 
151
- if self.passwd == "-1":
152
- self.logger.info("Login successful (receive only)")
203
+ if self.passwd == '-1':
204
+ self.logger.info('Login successful (receive only)')
153
205
  else:
154
- self.logger.info("Login successful")
206
+ self.logger.info('Login successful')
155
207
 
156
- self.logger.info(f"Connected to {server_string}")
208
+ self.logger.info(f'Connected to {server_string}')
157
209
  self.server_string = server_string
158
210
 
159
211
  except LoginError as e:
@@ -164,7 +216,7 @@ class Aprsdis(aprslib.IS):
164
216
  self.close()
165
217
  self.logger.error(f"Failed to login '{e}'")
166
218
  self.logger.exception(e)
167
- raise LoginError("Failed to login")
219
+ raise LoginError('Failed to login') from e
168
220
 
169
221
  def consumer(self, callback, blocking=True, immortal=False, raw=False):
170
222
  """
@@ -180,21 +232,21 @@ class Aprsdis(aprslib.IS):
180
232
  """
181
233
 
182
234
  if not self._connected:
183
- raise ConnectionError("not connected to a server")
235
+ raise ConnectionError('not connected to a server')
184
236
 
185
- line = b""
237
+ line = b''
186
238
 
187
239
  while True and not self.thread_stop:
188
240
  try:
189
241
  for line in self._socket_readlines(blocking):
190
- if line[0:1] != b"#":
242
+ if line[0:1] != b'#':
191
243
  self.aprsd_keepalive = datetime.datetime.now()
192
244
  if raw:
193
245
  callback(line)
194
246
  else:
195
247
  callback(self._parse(line))
196
248
  else:
197
- self.logger.debug("Server: %s", line.decode("utf8"))
249
+ self.logger.debug('Server: %s', line.decode('utf8'))
198
250
  self.aprsd_keepalive = datetime.datetime.now()
199
251
  except ParseError as exp:
200
252
  self.logger.log(
@@ -211,7 +263,7 @@ class Aprsdis(aprslib.IS):
211
263
  exp.packet,
212
264
  )
213
265
  except LoginError as exp:
214
- self.logger.error("%s: %s", exp.__class__.__name__, exp)
266
+ self.logger.error('%s: %s', exp.__class__.__name__, exp)
215
267
  except (KeyboardInterrupt, SystemExit):
216
268
  raise
217
269
  except (ConnectionDrop, ConnectionError):
@@ -227,7 +279,7 @@ class Aprsdis(aprslib.IS):
227
279
  except StopIteration:
228
280
  break
229
281
  except Exception:
230
- self.logger.error("APRS Packet: %s", line)
282
+ self.logger.error('APRS Packet: %s', line)
231
283
  raise
232
284
 
233
285
  if not blocking:
@@ -18,12 +18,13 @@ class KISS3Client:
18
18
 
19
19
  # date for last time we heard from the server
20
20
  aprsd_keepalive = datetime.datetime.now()
21
+ _connected = False
21
22
 
22
23
  def __init__(self):
23
24
  self.setup()
24
25
 
25
26
  def is_alive(self):
26
- return True
27
+ return self._connected
27
28
 
28
29
  def setup(self):
29
30
  # we can be TCP kiss or Serial kiss
@@ -56,17 +57,33 @@ class KISS3Client:
56
57
  self.path = CONF.kiss_tcp.path
57
58
 
58
59
  LOG.debug('Starting KISS interface connection')
59
- self.kiss.start()
60
+ try:
61
+ self.kiss.start()
62
+ if self.kiss.protocol.transport.is_closing():
63
+ LOG.warning('KISS transport is closing, not setting consumer callback')
64
+ self._connected = False
65
+ else:
66
+ self._connected = True
67
+ except Exception:
68
+ LOG.error('Failed to start KISS interface.')
69
+ self._connected = False
60
70
 
61
71
  @trace.trace
62
72
  def stop(self):
73
+ if not self._connected:
74
+ # do nothing since we aren't connected
75
+ return
76
+
63
77
  try:
64
78
  self.kiss.stop()
65
79
  self.kiss.loop.call_soon_threadsafe(
66
80
  self.kiss.protocol.transport.close,
67
81
  )
68
- except Exception as ex:
69
- LOG.exception(ex)
82
+ except Exception:
83
+ LOG.error('Failed to stop KISS interface.')
84
+
85
+ def close(self):
86
+ self.stop()
70
87
 
71
88
  def set_filter(self, filter):
72
89
  # This does nothing right now.
@@ -86,8 +103,14 @@ class KISS3Client:
86
103
  LOG.exception(ex)
87
104
 
88
105
  def consumer(self, callback):
106
+ if not self._connected:
107
+ raise Exception('KISS transport is not connected')
108
+
89
109
  self._parse_callback = callback
90
- self.kiss.read(callback=self.parse_frame, min_frames=None)
110
+ if not self.kiss.protocol.transport.is_closing():
111
+ self.kiss.read(callback=self.parse_frame, min_frames=1)
112
+ else:
113
+ self._connected = False
91
114
 
92
115
  def send(self, packet):
93
116
  """Send an APRS Message object."""
aprsd/client/kiss.py CHANGED
@@ -140,3 +140,4 @@ class KISSClient(base.APRSClient):
140
140
  except Exception as ex:
141
141
  LOG.error(f'Consumer failed {ex}')
142
142
  LOG.error(ex)
143
+ raise ex
aprsd/cmds/listen.py CHANGED
@@ -20,8 +20,10 @@ from aprsd import cli_helper, packets, plugin, threads, utils
20
20
  from aprsd.client import client_factory
21
21
  from aprsd.main import cli
22
22
  from aprsd.packets import collector as packet_collector
23
+ from aprsd.packets import core, seen_list
23
24
  from aprsd.packets import log as packet_log
24
- from aprsd.packets import seen_list
25
+ from aprsd.packets.filter import PacketFilter
26
+ from aprsd.packets.filters import dupe_filter, packet_type
25
27
  from aprsd.stats import collector
26
28
  from aprsd.threads import keepalive, rx
27
29
  from aprsd.threads import stats as stats_thread
@@ -29,7 +31,7 @@ from aprsd.threads.aprsd import APRSDThread
29
31
 
30
32
  # setup the global logger
31
33
  # log.basicConfig(level=log.DEBUG) # level=10
32
- LOG = logging.getLogger("APRSD")
34
+ LOG = logging.getLogger('APRSD')
33
35
  CONF = cfg.CONF
34
36
  LOGU = logger
35
37
  console = Console()
@@ -37,9 +39,9 @@ console = Console()
37
39
 
38
40
  def signal_handler(sig, frame):
39
41
  threads.APRSDThreadList().stop_all()
40
- if "subprocess" not in str(frame):
42
+ if 'subprocess' not in str(frame):
41
43
  LOG.info(
42
- "Ctrl+C, Sending all threads exit! Can take up to 10 seconds {}".format(
44
+ 'Ctrl+C, Sending all threads exit! Can take up to 10 seconds {}'.format(
43
45
  datetime.datetime.now(),
44
46
  ),
45
47
  )
@@ -48,90 +50,66 @@ def signal_handler(sig, frame):
48
50
  collector.Collector().collect()
49
51
 
50
52
 
51
- class APRSDListenThread(rx.APRSDRXThread):
53
+ class APRSDListenProcessThread(rx.APRSDFilterThread):
52
54
  def __init__(
53
55
  self,
54
56
  packet_queue,
55
57
  packet_filter=None,
56
58
  plugin_manager=None,
57
- enabled_plugins=[],
59
+ enabled_plugins=None,
58
60
  log_packets=False,
59
61
  ):
60
- super().__init__(packet_queue)
62
+ super().__init__('ListenProcThread', packet_queue)
61
63
  self.packet_filter = packet_filter
62
64
  self.plugin_manager = plugin_manager
63
65
  if self.plugin_manager:
64
- LOG.info(f"Plugins {self.plugin_manager.get_message_plugins()}")
66
+ LOG.info(f'Plugins {self.plugin_manager.get_message_plugins()}')
65
67
  self.log_packets = log_packets
66
68
 
67
- def process_packet(self, *args, **kwargs):
68
- packet = self._client.decode_packet(*args, **kwargs)
69
- filters = {
70
- packets.Packet.__name__: packets.Packet,
71
- packets.AckPacket.__name__: packets.AckPacket,
72
- packets.BeaconPacket.__name__: packets.BeaconPacket,
73
- packets.GPSPacket.__name__: packets.GPSPacket,
74
- packets.MessagePacket.__name__: packets.MessagePacket,
75
- packets.MicEPacket.__name__: packets.MicEPacket,
76
- packets.ObjectPacket.__name__: packets.ObjectPacket,
77
- packets.StatusPacket.__name__: packets.StatusPacket,
78
- packets.ThirdPartyPacket.__name__: packets.ThirdPartyPacket,
79
- packets.WeatherPacket.__name__: packets.WeatherPacket,
80
- packets.UnknownPacket.__name__: packets.UnknownPacket,
81
- }
82
-
83
- if self.packet_filter:
84
- filter_class = filters[self.packet_filter]
85
- if isinstance(packet, filter_class):
86
- if self.log_packets:
87
- packet_log.log(packet)
88
- if self.plugin_manager:
89
- # Don't do anything with the reply
90
- # This is the listen only command.
91
- self.plugin_manager.run(packet)
92
- else:
93
- if self.log_packets:
94
- packet_log.log(packet)
95
- if self.plugin_manager:
96
- # Don't do anything with the reply.
97
- # This is the listen only command.
98
- self.plugin_manager.run(packet)
99
-
100
- packet_collector.PacketCollector().rx(packet)
69
+ def print_packet(self, packet):
70
+ if self.log_packets:
71
+ packet_log.log(packet)
72
+
73
+ def process_packet(self, packet: type[core.Packet]):
74
+ if self.plugin_manager:
75
+ # Don't do anything with the reply.
76
+ # This is the listen only command.
77
+ self.plugin_manager.run(packet)
101
78
 
102
79
 
103
80
  class ListenStatsThread(APRSDThread):
104
81
  """Log the stats from the PacketList."""
105
82
 
106
83
  def __init__(self):
107
- super().__init__("PacketStatsLog")
84
+ super().__init__('PacketStatsLog')
108
85
  self._last_total_rx = 0
86
+ self.period = 31
109
87
 
110
88
  def loop(self):
111
- if self.loop_count % 10 == 0:
89
+ if self.loop_count % self.period == 0:
112
90
  # log the stats every 10 seconds
113
91
  stats_json = collector.Collector().collect()
114
- stats = stats_json["PacketList"]
115
- total_rx = stats["rx"]
116
- packet_count = len(stats["packets"])
92
+ stats = stats_json['PacketList']
93
+ total_rx = stats['rx']
94
+ packet_count = len(stats['packets'])
117
95
  rx_delta = total_rx - self._last_total_rx
118
- rate = rx_delta / 10
96
+ rate = rx_delta / self.period
119
97
 
120
98
  # Log summary stats
121
99
  LOGU.opt(colors=True).info(
122
- f"<green>RX Rate: {rate} pps</green> "
123
- f"<yellow>Total RX: {total_rx}</yellow> "
124
- f"<red>RX Last 10 secs: {rx_delta}</red> "
125
- f"<white>Packets in PacketList: {packet_count}</white>",
100
+ f'<green>RX Rate: {rate:.2f} pps</green> '
101
+ f'<yellow>Total RX: {total_rx}</yellow> '
102
+ f'<red>RX Last {self.period} secs: {rx_delta}</red> '
103
+ f'<white>Packets in PacketListStats: {packet_count}</white>',
126
104
  )
127
105
  self._last_total_rx = total_rx
128
106
 
129
107
  # Log individual type stats
130
- for k, v in stats["types"].items():
131
- thread_hex = f"fg {utils.hex_from_name(k)}"
108
+ for k, v in stats['types'].items():
109
+ thread_hex = f'fg {utils.hex_from_name(k)}'
132
110
  LOGU.opt(colors=True).info(
133
- f"<{thread_hex}>{k:<15}</{thread_hex}> "
134
- f"<blue>RX: {v['rx']}</blue> <red>TX: {v['tx']}</red>",
111
+ f'<{thread_hex}>{k:<15}</{thread_hex}> '
112
+ f'<blue>RX: {v["rx"]}</blue> <red>TX: {v["tx"]}</red>',
135
113
  )
136
114
 
137
115
  time.sleep(1)
@@ -141,19 +119,19 @@ class ListenStatsThread(APRSDThread):
141
119
  @cli.command()
142
120
  @cli_helper.add_options(cli_helper.common_options)
143
121
  @click.option(
144
- "--aprs-login",
145
- envvar="APRS_LOGIN",
122
+ '--aprs-login',
123
+ envvar='APRS_LOGIN',
146
124
  show_envvar=True,
147
- help="What callsign to send the message from.",
125
+ help='What callsign to send the message from.',
148
126
  )
149
127
  @click.option(
150
- "--aprs-password",
151
- envvar="APRS_PASSWORD",
128
+ '--aprs-password',
129
+ envvar='APRS_PASSWORD',
152
130
  show_envvar=True,
153
- help="the APRS-IS password for APRS_LOGIN",
131
+ help='the APRS-IS password for APRS_LOGIN',
154
132
  )
155
133
  @click.option(
156
- "--packet-filter",
134
+ '--packet-filter',
157
135
  type=click.Choice(
158
136
  [
159
137
  packets.AckPacket.__name__,
@@ -170,35 +148,37 @@ class ListenStatsThread(APRSDThread):
170
148
  ],
171
149
  case_sensitive=False,
172
150
  ),
173
- help="Filter by packet type",
151
+ multiple=True,
152
+ default=[],
153
+ help='Filter by packet type',
174
154
  )
175
155
  @click.option(
176
- "--enable-plugin",
156
+ '--enable-plugin',
177
157
  multiple=True,
178
- help="Enable a plugin. This is the name of the file in the plugins directory.",
158
+ help='Enable a plugin. This is the name of the file in the plugins directory.',
179
159
  )
180
160
  @click.option(
181
- "--load-plugins",
161
+ '--load-plugins',
182
162
  default=False,
183
163
  is_flag=True,
184
- help="Load plugins as enabled in aprsd.conf ?",
164
+ help='Load plugins as enabled in aprsd.conf ?',
185
165
  )
186
166
  @click.argument(
187
- "filter",
167
+ 'filter',
188
168
  nargs=-1,
189
169
  required=True,
190
170
  )
191
171
  @click.option(
192
- "--log-packets",
172
+ '--log-packets',
193
173
  default=False,
194
174
  is_flag=True,
195
- help="Log incoming packets.",
175
+ help='Log incoming packets.',
196
176
  )
197
177
  @click.option(
198
- "--enable-packet-stats",
178
+ '--enable-packet-stats',
199
179
  default=False,
200
180
  is_flag=True,
201
- help="Enable packet stats periodic logging.",
181
+ help='Enable packet stats periodic logging.',
202
182
  )
203
183
  @click.pass_context
204
184
  @cli_helper.process_standard_options
@@ -228,46 +208,46 @@ def listen(
228
208
 
229
209
  if not aprs_login:
230
210
  click.echo(ctx.get_help())
231
- click.echo("")
232
- ctx.fail("Must set --aprs-login or APRS_LOGIN")
211
+ click.echo('')
212
+ ctx.fail('Must set --aprs-login or APRS_LOGIN')
233
213
  ctx.exit()
234
214
 
235
215
  if not aprs_password:
236
216
  click.echo(ctx.get_help())
237
- click.echo("")
238
- ctx.fail("Must set --aprs-password or APRS_PASSWORD")
217
+ click.echo('')
218
+ ctx.fail('Must set --aprs-password or APRS_PASSWORD')
239
219
  ctx.exit()
240
220
 
241
221
  # CONF.aprs_network.login = aprs_login
242
222
  # config["aprs"]["password"] = aprs_password
243
223
 
244
- LOG.info(f"APRSD Listen Started version: {aprsd.__version__}")
224
+ LOG.info(f'APRSD Listen Started version: {aprsd.__version__}')
245
225
 
246
226
  CONF.log_opt_values(LOG, logging.DEBUG)
247
227
  collector.Collector()
248
228
 
249
229
  # Try and load saved MsgTrack list
250
- LOG.debug("Loading saved MsgTrack object.")
230
+ LOG.debug('Loading saved MsgTrack object.')
251
231
 
252
232
  # Initialize the client factory and create
253
233
  # The correct client object ready for use
254
234
  # Make sure we have 1 client transport enabled
255
235
  if not client_factory.is_client_enabled():
256
- LOG.error("No Clients are enabled in config.")
236
+ LOG.error('No Clients are enabled in config.')
257
237
  sys.exit(-1)
258
238
 
259
239
  # Creates the client object
260
- LOG.info("Creating client connection")
240
+ LOG.info('Creating client connection')
261
241
  aprs_client = client_factory.create()
262
242
  LOG.info(aprs_client)
263
243
  if not aprs_client.login_success:
264
244
  # We failed to login, will just quit!
265
- msg = f"Login Failure: {aprs_client.login_failure}"
245
+ msg = f'Login Failure: {aprs_client.login_failure}'
266
246
  LOG.error(msg)
267
247
  print(msg)
268
248
  sys.exit(-1)
269
249
 
270
- LOG.debug(f"Filter by '{filter}'")
250
+ LOG.debug(f"Filter messages on aprsis server by '{filter}'")
271
251
  aprs_client.set_filter(filter)
272
252
 
273
253
  keepalive_thread = keepalive.KeepAliveThread()
@@ -276,10 +256,19 @@ def listen(
276
256
  # just deregister the class from the packet collector
277
257
  packet_collector.PacketCollector().unregister(seen_list.SeenList)
278
258
 
259
+ # we don't want the dupe filter to run here.
260
+ PacketFilter().unregister(dupe_filter.DupePacketFilter)
261
+ if packet_filter:
262
+ LOG.info('Enabling packet filtering for {packet_filter}')
263
+ packet_type.PacketTypeFilter().set_allow_list(packet_filter)
264
+ PacketFilter().register(packet_type.PacketTypeFilter)
265
+ else:
266
+ LOG.info('No packet filtering enabled.')
267
+
279
268
  pm = None
280
269
  if load_plugins:
281
270
  pm = plugin.PluginManager()
282
- LOG.info("Loading plugins")
271
+ LOG.info('Loading plugins')
283
272
  pm.setup_plugins(load_help_plugin=False)
284
273
  elif enable_plugin:
285
274
  pm = plugin.PluginManager()
@@ -290,33 +279,37 @@ def listen(
290
279
  else:
291
280
  LOG.warning(
292
281
  "Not Loading any plugins use --load-plugins to load what's "
293
- "defined in the config file.",
282
+ 'defined in the config file.',
294
283
  )
295
284
 
296
285
  if pm:
297
286
  for p in pm.get_plugins():
298
- LOG.info("Loaded plugin %s", p.__class__.__name__)
287
+ LOG.info('Loaded plugin %s', p.__class__.__name__)
299
288
 
300
289
  stats = stats_thread.APRSDStatsStoreThread()
301
290
  stats.start()
302
291
 
303
- LOG.debug("Create APRSDListenThread")
304
- listen_thread = APRSDListenThread(
292
+ LOG.debug('Start APRSDRxThread')
293
+ rx_thread = rx.APRSDRXThread(packet_queue=threads.packet_queue)
294
+ rx_thread.start()
295
+
296
+ LOG.debug('Create APRSDListenProcessThread')
297
+ listen_thread = APRSDListenProcessThread(
305
298
  packet_queue=threads.packet_queue,
306
299
  packet_filter=packet_filter,
307
300
  plugin_manager=pm,
308
301
  enabled_plugins=enable_plugin,
309
302
  log_packets=log_packets,
310
303
  )
311
- LOG.debug("Start APRSDListenThread")
304
+ LOG.debug('Start APRSDListenProcessThread')
312
305
  listen_thread.start()
313
306
  if enable_packet_stats:
314
307
  listen_stats = ListenStatsThread()
315
308
  listen_stats.start()
316
309
 
317
310
  keepalive_thread.start()
318
- LOG.debug("keepalive Join")
311
+ LOG.debug('keepalive Join')
319
312
  keepalive_thread.join()
320
- LOG.debug("listen_thread Join")
313
+ rx_thread.join()
321
314
  listen_thread.join()
322
315
  stats.join()
aprsd/cmds/server.py CHANGED
@@ -147,7 +147,7 @@ def server(ctx, flush):
147
147
  server_threads.register(keepalive.KeepAliveThread())
148
148
  server_threads.register(stats_thread.APRSDStatsStoreThread())
149
149
  server_threads.register(
150
- rx.APRSDPluginRXThread(
150
+ rx.APRSDRXThread(
151
151
  packet_queue=threads.packet_queue,
152
152
  ),
153
153
  )