mirror of
https://github.com/craigerl/aprsd.git
synced 2024-12-25 03:37:36 -05:00
commit
f932c203d7
@ -7,7 +7,7 @@ import re
|
|||||||
import smtplib
|
import smtplib
|
||||||
import time
|
import time
|
||||||
|
|
||||||
from aprsd import messaging, threads
|
from aprsd import messaging, stats, threads
|
||||||
import imapclient
|
import imapclient
|
||||||
from validate_email import validate_email
|
from validate_email import validate_email
|
||||||
|
|
||||||
@ -269,6 +269,7 @@ def send_email(to_addr, content):
|
|||||||
[to_addr],
|
[to_addr],
|
||||||
msg.as_string(),
|
msg.as_string(),
|
||||||
)
|
)
|
||||||
|
stats.APRSDStats().email_tx_inc()
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
msg = getattr(e, "message", repr(e))
|
msg = getattr(e, "message", repr(e))
|
||||||
LOG.error("Sendmail Error!!!! '{}'", msg)
|
LOG.error("Sendmail Error!!!! '{}'", msg)
|
||||||
@ -366,6 +367,7 @@ class APRSDEmailThread(threads.APRSDThread):
|
|||||||
past = datetime.datetime.now()
|
past = datetime.datetime.now()
|
||||||
while not self.thread_stop:
|
while not self.thread_stop:
|
||||||
time.sleep(5)
|
time.sleep(5)
|
||||||
|
stats.APRSDStats().email_thread_update()
|
||||||
# always sleep for 5 seconds and see if we need to check email
|
# always sleep for 5 seconds and see if we need to check email
|
||||||
# This allows CTRL-C to stop the execution of this loop sooner
|
# This allows CTRL-C to stop the execution of this loop sooner
|
||||||
# than check_email_delay time
|
# than check_email_delay time
|
||||||
|
38
aprsd/flask.py
Normal file
38
aprsd/flask.py
Normal file
@ -0,0 +1,38 @@
|
|||||||
|
import json
|
||||||
|
|
||||||
|
import aprsd
|
||||||
|
from aprsd import messaging, stats
|
||||||
|
import flask
|
||||||
|
import flask_classful
|
||||||
|
|
||||||
|
|
||||||
|
class APRSDFlask(flask_classful.FlaskView):
|
||||||
|
config = None
|
||||||
|
|
||||||
|
def set_config(self, config):
|
||||||
|
self.config = config
|
||||||
|
|
||||||
|
def index(self):
|
||||||
|
return "Hello"
|
||||||
|
# return flask.render_template("index.html", message=msg)
|
||||||
|
|
||||||
|
def stats(self):
|
||||||
|
stats_obj = stats.APRSDStats()
|
||||||
|
track = messaging.MsgTrack()
|
||||||
|
|
||||||
|
result = {
|
||||||
|
"version": aprsd.__version__,
|
||||||
|
"uptime": stats_obj.uptime,
|
||||||
|
"size_tracker": len(track),
|
||||||
|
"stats": stats_obj.stats(),
|
||||||
|
}
|
||||||
|
return json.dumps(result)
|
||||||
|
|
||||||
|
|
||||||
|
def init_flask(config):
|
||||||
|
flask_app = flask.Flask("aprsd")
|
||||||
|
server = APRSDFlask()
|
||||||
|
server.set_config(config)
|
||||||
|
# flask_app.route('/', methods=['GET'])(server.index)
|
||||||
|
flask_app.route("/stats", methods=["GET"])(server.stats)
|
||||||
|
return flask_app
|
@ -32,7 +32,7 @@ import time
|
|||||||
|
|
||||||
# local imports here
|
# local imports here
|
||||||
import aprsd
|
import aprsd
|
||||||
from aprsd import client, email, messaging, plugin, threads, utils
|
from aprsd import client, email, flask, messaging, plugin, stats, threads, utils
|
||||||
import aprslib
|
import aprslib
|
||||||
from aprslib.exceptions import LoginError
|
from aprslib.exceptions import LoginError
|
||||||
import click
|
import click
|
||||||
@ -157,7 +157,9 @@ def signal_handler(sig, frame):
|
|||||||
)
|
)
|
||||||
threads.APRSDThreadList().stop_all()
|
threads.APRSDThreadList().stop_all()
|
||||||
server_event.set()
|
server_event.set()
|
||||||
time.sleep(1)
|
LOG.info("EXITING STATS")
|
||||||
|
LOG.info(stats.APRSDStats())
|
||||||
|
# time.sleep(1)
|
||||||
signal.signal(signal.SIGTERM, sys.exit(0))
|
signal.signal(signal.SIGTERM, sys.exit(0))
|
||||||
|
|
||||||
|
|
||||||
@ -384,19 +386,12 @@ def send_message(
|
|||||||
default=False,
|
default=False,
|
||||||
help="Flush out all old aged messages on disk.",
|
help="Flush out all old aged messages on disk.",
|
||||||
)
|
)
|
||||||
@click.option(
|
|
||||||
"--stats-server",
|
|
||||||
is_flag=True,
|
|
||||||
default=False,
|
|
||||||
help="Run a stats web server on port 5001?",
|
|
||||||
)
|
|
||||||
def server(
|
def server(
|
||||||
loglevel,
|
loglevel,
|
||||||
quiet,
|
quiet,
|
||||||
disable_validation,
|
disable_validation,
|
||||||
config_file,
|
config_file,
|
||||||
flush,
|
flush,
|
||||||
stats_server,
|
|
||||||
):
|
):
|
||||||
"""Start the aprsd server process."""
|
"""Start the aprsd server process."""
|
||||||
global event
|
global event
|
||||||
@ -416,6 +411,7 @@ def server(
|
|||||||
|
|
||||||
setup_logging(config, loglevel, quiet)
|
setup_logging(config, loglevel, quiet)
|
||||||
LOG.info("APRSD Started version: {}".format(aprsd.__version__))
|
LOG.info("APRSD Started version: {}".format(aprsd.__version__))
|
||||||
|
stats.APRSDStats(config)
|
||||||
|
|
||||||
email_enabled = config["aprsd"]["email"].get("enabled", False)
|
email_enabled = config["aprsd"]["email"].get("enabled", False)
|
||||||
|
|
||||||
@ -463,18 +459,25 @@ def server(
|
|||||||
|
|
||||||
messaging.MsgTrack().restart()
|
messaging.MsgTrack().restart()
|
||||||
|
|
||||||
cntr = 0
|
keepalive = threads.KeepAliveThread()
|
||||||
while not server_event.is_set():
|
keepalive.start()
|
||||||
# to keep the log noise down
|
|
||||||
if cntr % 12 == 0:
|
try:
|
||||||
tracker = messaging.MsgTrack()
|
web_enabled = utils.check_config_option(config, ["aprsd", "web", "enabled"])
|
||||||
LOG.debug("KeepAlive Tracker({}): {}".format(len(tracker), str(tracker)))
|
except Exception:
|
||||||
cntr += 1
|
web_enabled = False
|
||||||
time.sleep(10)
|
|
||||||
|
if web_enabled:
|
||||||
|
app = flask.init_flask(config)
|
||||||
|
app.run(
|
||||||
|
host=config["aprsd"]["web"]["host"],
|
||||||
|
port=config["aprsd"]["web"]["port"],
|
||||||
|
)
|
||||||
|
|
||||||
# If there are items in the msgTracker, then save them
|
# If there are items in the msgTracker, then save them
|
||||||
tracker = messaging.MsgTrack()
|
tracker = messaging.MsgTrack()
|
||||||
tracker.save()
|
tracker.save()
|
||||||
|
LOG.info(stats.APRSDStats())
|
||||||
LOG.info("APRSD Exiting.")
|
LOG.info("APRSD Exiting.")
|
||||||
|
|
||||||
|
|
||||||
|
@ -9,7 +9,7 @@ import re
|
|||||||
import threading
|
import threading
|
||||||
import time
|
import time
|
||||||
|
|
||||||
from aprsd import client, threads, utils
|
from aprsd import client, stats, threads, utils
|
||||||
|
|
||||||
LOG = logging.getLogger("APRSD")
|
LOG = logging.getLogger("APRSD")
|
||||||
|
|
||||||
@ -49,7 +49,7 @@ class MsgTrack:
|
|||||||
if cls._instance is None:
|
if cls._instance is None:
|
||||||
cls._instance = super().__new__(cls)
|
cls._instance = super().__new__(cls)
|
||||||
cls._instance.track = {}
|
cls._instance.track = {}
|
||||||
cls._start_time = datetime.datetime.now()
|
cls._instance._start_time = datetime.datetime.now()
|
||||||
cls._instance.lock = threading.Lock()
|
cls._instance.lock = threading.Lock()
|
||||||
return cls._instance
|
return cls._instance
|
||||||
|
|
||||||
@ -57,6 +57,7 @@ class MsgTrack:
|
|||||||
with self.lock:
|
with self.lock:
|
||||||
key = int(msg.id)
|
key = int(msg.id)
|
||||||
self.track[key] = msg
|
self.track[key] = msg
|
||||||
|
stats.APRSDStats().msgs_tracked_inc()
|
||||||
self.total_messages_tracked += 1
|
self.total_messages_tracked += 1
|
||||||
|
|
||||||
def get(self, id):
|
def get(self, id):
|
||||||
@ -251,6 +252,7 @@ class RawMessage(Message):
|
|||||||
fromcall=self.fromcall,
|
fromcall=self.fromcall,
|
||||||
)
|
)
|
||||||
cl.sendall(repr(self))
|
cl.sendall(repr(self))
|
||||||
|
stats.APRSDStats().msgs_sent_inc()
|
||||||
|
|
||||||
|
|
||||||
class TextMessage(Message):
|
class TextMessage(Message):
|
||||||
@ -267,7 +269,7 @@ class TextMessage(Message):
|
|||||||
|
|
||||||
def __repr__(self):
|
def __repr__(self):
|
||||||
"""Build raw string to send over the air."""
|
"""Build raw string to send over the air."""
|
||||||
return "{}>APRS::{}:{}{{{}\n".format(
|
return "{}>APZ100::{}:{}{{{}\n".format(
|
||||||
self.fromcall,
|
self.fromcall,
|
||||||
self.tocall.ljust(9),
|
self.tocall.ljust(9),
|
||||||
self._filter_for_send(),
|
self._filter_for_send(),
|
||||||
@ -315,6 +317,7 @@ class TextMessage(Message):
|
|||||||
fromcall=self.fromcall,
|
fromcall=self.fromcall,
|
||||||
)
|
)
|
||||||
cl.sendall(repr(self))
|
cl.sendall(repr(self))
|
||||||
|
stats.APRSDStats().msgs_tx_inc()
|
||||||
|
|
||||||
|
|
||||||
class SendMessageThread(threads.APRSDThread):
|
class SendMessageThread(threads.APRSDThread):
|
||||||
@ -374,6 +377,7 @@ class SendMessageThread(threads.APRSDThread):
|
|||||||
msg_num=msg.id,
|
msg_num=msg.id,
|
||||||
)
|
)
|
||||||
cl.sendall(repr(msg))
|
cl.sendall(repr(msg))
|
||||||
|
stats.APRSDStats().msgs_tx_inc()
|
||||||
msg.last_send_time = datetime.datetime.now()
|
msg.last_send_time = datetime.datetime.now()
|
||||||
msg.last_send_attempt += 1
|
msg.last_send_attempt += 1
|
||||||
|
|
||||||
@ -389,7 +393,7 @@ class AckMessage(Message):
|
|||||||
super().__init__(fromcall, tocall, msg_id=msg_id)
|
super().__init__(fromcall, tocall, msg_id=msg_id)
|
||||||
|
|
||||||
def __repr__(self):
|
def __repr__(self):
|
||||||
return "{}>APRS::{}:ack{}\n".format(
|
return "{}>APZ100::{}:ack{}\n".format(
|
||||||
self.fromcall,
|
self.fromcall,
|
||||||
self.tocall.ljust(9),
|
self.tocall.ljust(9),
|
||||||
self.id,
|
self.id,
|
||||||
@ -411,6 +415,7 @@ class AckMessage(Message):
|
|||||||
retry_number=i,
|
retry_number=i,
|
||||||
)
|
)
|
||||||
cl.sendall(repr(self))
|
cl.sendall(repr(self))
|
||||||
|
stats.APRSDStats().ack_tx_inc()
|
||||||
# aprs duplicate detection is 30 secs?
|
# aprs duplicate detection is 30 secs?
|
||||||
# (21 only sends first, 28 skips middle)
|
# (21 only sends first, 28 skips middle)
|
||||||
time.sleep(31)
|
time.sleep(31)
|
||||||
@ -478,6 +483,7 @@ class SendAckThread(threads.APRSDThread):
|
|||||||
retry_number=self.ack.last_send_attempt,
|
retry_number=self.ack.last_send_attempt,
|
||||||
)
|
)
|
||||||
cl.sendall(repr(self.ack))
|
cl.sendall(repr(self.ack))
|
||||||
|
stats.APRSDStats().ack_tx_inc()
|
||||||
self.ack.last_send_attempt += 1
|
self.ack.last_send_attempt += 1
|
||||||
self.ack.last_send_time = datetime.datetime.now()
|
self.ack.last_send_time = datetime.datetime.now()
|
||||||
time.sleep(5)
|
time.sleep(5)
|
||||||
|
@ -48,7 +48,7 @@ class LocationPlugin(plugin.APRSDPluginBase):
|
|||||||
lat = aprs_data["entries"][0]["lat"]
|
lat = aprs_data["entries"][0]["lat"]
|
||||||
lon = aprs_data["entries"][0]["lng"]
|
lon = aprs_data["entries"][0]["lng"]
|
||||||
try: # altitude not always provided
|
try: # altitude not always provided
|
||||||
alt = aprs_data["entries"][0]["altitude"]
|
alt = float(aprs_data["entries"][0]["altitude"])
|
||||||
except Exception:
|
except Exception:
|
||||||
alt = 0
|
alt = 0
|
||||||
altfeet = int(alt * 3.28084)
|
altfeet = int(alt * 3.28084)
|
||||||
|
161
aprsd/stats.py
Normal file
161
aprsd/stats.py
Normal file
@ -0,0 +1,161 @@
|
|||||||
|
import datetime
|
||||||
|
import logging
|
||||||
|
import threading
|
||||||
|
|
||||||
|
LOG = logging.getLogger("APRSD")
|
||||||
|
|
||||||
|
|
||||||
|
class APRSDStats:
|
||||||
|
|
||||||
|
_instance = None
|
||||||
|
lock = None
|
||||||
|
config = None
|
||||||
|
|
||||||
|
start_time = None
|
||||||
|
|
||||||
|
_msgs_tracked = 0
|
||||||
|
_msgs_tx = 0
|
||||||
|
_msgs_rx = 0
|
||||||
|
|
||||||
|
_msgs_mice_rx = 0
|
||||||
|
|
||||||
|
_ack_tx = 0
|
||||||
|
_ack_rx = 0
|
||||||
|
|
||||||
|
_email_thread_last_time = None
|
||||||
|
_email_tx = 0
|
||||||
|
_email_rx = 0
|
||||||
|
|
||||||
|
def __new__(cls, *args, **kwargs):
|
||||||
|
if cls._instance is None:
|
||||||
|
cls._instance = super().__new__(cls)
|
||||||
|
# any initializetion here
|
||||||
|
cls._instance.lock = threading.Lock()
|
||||||
|
cls._instance.start_time = datetime.datetime.now()
|
||||||
|
return cls._instance
|
||||||
|
|
||||||
|
def __init__(self, config=None):
|
||||||
|
if config:
|
||||||
|
self.config = config
|
||||||
|
|
||||||
|
@property
|
||||||
|
def uptime(self):
|
||||||
|
with self.lock:
|
||||||
|
return str(datetime.datetime.now() - self.start_time)
|
||||||
|
|
||||||
|
@property
|
||||||
|
def msgs_tx(self):
|
||||||
|
with self.lock:
|
||||||
|
return self._msgs_tx
|
||||||
|
|
||||||
|
def msgs_tx_inc(self):
|
||||||
|
with self.lock:
|
||||||
|
self._msgs_tx += 1
|
||||||
|
|
||||||
|
@property
|
||||||
|
def msgs_rx(self):
|
||||||
|
with self.lock:
|
||||||
|
return self._msgs_rx
|
||||||
|
|
||||||
|
def msgs_rx_inc(self):
|
||||||
|
with self.lock:
|
||||||
|
self._msgs_rx += 1
|
||||||
|
|
||||||
|
@property
|
||||||
|
def msgs_mice_rx(self):
|
||||||
|
with self.lock:
|
||||||
|
return self._msgs_mice_rx
|
||||||
|
|
||||||
|
def msgs_mice_inc(self):
|
||||||
|
with self.lock:
|
||||||
|
self._msgs_mice_rx += 1
|
||||||
|
|
||||||
|
@property
|
||||||
|
def ack_tx(self):
|
||||||
|
with self.lock:
|
||||||
|
return self._ack_tx
|
||||||
|
|
||||||
|
def ack_tx_inc(self):
|
||||||
|
with self.lock:
|
||||||
|
self._ack_tx += 1
|
||||||
|
|
||||||
|
@property
|
||||||
|
def ack_rx(self):
|
||||||
|
with self.lock:
|
||||||
|
return self._ack_rx
|
||||||
|
|
||||||
|
def ack_rx_inc(self):
|
||||||
|
with self.lock:
|
||||||
|
self._ack_rx += 1
|
||||||
|
|
||||||
|
@property
|
||||||
|
def msgs_tracked(self):
|
||||||
|
with self.lock:
|
||||||
|
return self._msgs_tracked
|
||||||
|
|
||||||
|
def msgs_tracked_inc(self):
|
||||||
|
with self.lock:
|
||||||
|
self._msgs_tracked += 1
|
||||||
|
|
||||||
|
@property
|
||||||
|
def email_tx(self):
|
||||||
|
with self.lock:
|
||||||
|
return self._email_tx
|
||||||
|
|
||||||
|
def email_tx_inc(self):
|
||||||
|
with self.lock:
|
||||||
|
self._email_tx += 1
|
||||||
|
|
||||||
|
@property
|
||||||
|
def email_rx(self):
|
||||||
|
with self.lock:
|
||||||
|
return self._email_rx
|
||||||
|
|
||||||
|
def email_rx_inc(self):
|
||||||
|
with self.lock:
|
||||||
|
self._email_rx += 1
|
||||||
|
|
||||||
|
@property
|
||||||
|
def email_thread_time(self):
|
||||||
|
with self.lock:
|
||||||
|
return self._email_thread_last_time
|
||||||
|
|
||||||
|
def email_thread_update(self):
|
||||||
|
with self.lock:
|
||||||
|
self._email_thread_last_time = datetime.datetime.now()
|
||||||
|
|
||||||
|
def stats(self):
|
||||||
|
now = datetime.datetime.now()
|
||||||
|
stats = {
|
||||||
|
"messages": {
|
||||||
|
"tracked": self.msgs_tracked,
|
||||||
|
"sent": self.msgs_tx,
|
||||||
|
"recieved": self.msgs_rx,
|
||||||
|
"ack_sent": self.ack_tx,
|
||||||
|
"ack_recieved": self.ack_rx,
|
||||||
|
"mic-e recieved": self.msgs_mice_rx,
|
||||||
|
},
|
||||||
|
"email": {
|
||||||
|
"sent": self._email_tx,
|
||||||
|
"recieved": self._email_rx,
|
||||||
|
"thread_last_update": str(now - self._email_thread_last_time),
|
||||||
|
},
|
||||||
|
}
|
||||||
|
LOG.debug("STATS {}".format(stats))
|
||||||
|
return stats
|
||||||
|
|
||||||
|
def __str__(self):
|
||||||
|
return (
|
||||||
|
"Msgs TX:{} RX:{} ACK: TX:{} RX:{} "
|
||||||
|
"Email TX:{} RX:{} LastLoop:{} "
|
||||||
|
"Uptime: {}".format(
|
||||||
|
self._msgs_tx,
|
||||||
|
self._msgs_rx,
|
||||||
|
self._ack_tx,
|
||||||
|
self._ack_rx,
|
||||||
|
self._email_tx,
|
||||||
|
self._email_rx,
|
||||||
|
self._email_thread_last_time,
|
||||||
|
self.uptime,
|
||||||
|
)
|
||||||
|
)
|
4
aprsd/templates/index.html
Normal file
4
aprsd/templates/index.html
Normal file
@ -0,0 +1,4 @@
|
|||||||
|
<html>
|
||||||
|
|
||||||
|
<body><h1>{{ message }}</h1></body>
|
||||||
|
</html>
|
@ -1,10 +1,11 @@
|
|||||||
import abc
|
import abc
|
||||||
|
import datetime
|
||||||
import logging
|
import logging
|
||||||
import queue
|
import queue
|
||||||
import threading
|
import threading
|
||||||
import time
|
import time
|
||||||
|
|
||||||
from aprsd import client, messaging, plugin
|
from aprsd import client, messaging, plugin, stats
|
||||||
import aprslib
|
import aprslib
|
||||||
|
|
||||||
LOG = logging.getLogger("APRSD")
|
LOG = logging.getLogger("APRSD")
|
||||||
@ -63,6 +64,37 @@ class APRSDThread(threading.Thread, metaclass=abc.ABCMeta):
|
|||||||
LOG.debug("Exiting")
|
LOG.debug("Exiting")
|
||||||
|
|
||||||
|
|
||||||
|
class KeepAliveThread(APRSDThread):
|
||||||
|
cntr = 0
|
||||||
|
|
||||||
|
def __init__(self):
|
||||||
|
super().__init__("KeepAlive")
|
||||||
|
|
||||||
|
def loop(self):
|
||||||
|
if self.cntr % 6 == 0:
|
||||||
|
tracker = messaging.MsgTrack()
|
||||||
|
stats_obj = stats.APRSDStats()
|
||||||
|
now = datetime.datetime.now()
|
||||||
|
last_email = stats.APRSDStats().email_thread_time
|
||||||
|
if last_email:
|
||||||
|
email_thread_time = str(now - last_email)
|
||||||
|
else:
|
||||||
|
email_thread_time = "N/A"
|
||||||
|
|
||||||
|
LOG.debug(
|
||||||
|
"Tracker({}) EmailThread: {} "
|
||||||
|
" Msgs: TX:{} RX:{}".format(
|
||||||
|
len(tracker),
|
||||||
|
email_thread_time,
|
||||||
|
stats_obj.msgs_tx,
|
||||||
|
stats_obj.msgs_rx,
|
||||||
|
),
|
||||||
|
)
|
||||||
|
self.cntr += 1
|
||||||
|
time.sleep(10)
|
||||||
|
return True
|
||||||
|
|
||||||
|
|
||||||
class APRSDRXThread(APRSDThread):
|
class APRSDRXThread(APRSDThread):
|
||||||
def __init__(self, msg_queues, config):
|
def __init__(self, msg_queues, config):
|
||||||
super().__init__("RX_MSG")
|
super().__init__("RX_MSG")
|
||||||
@ -118,11 +150,13 @@ class APRSDRXThread(APRSDThread):
|
|||||||
)
|
)
|
||||||
tracker = messaging.MsgTrack()
|
tracker = messaging.MsgTrack()
|
||||||
tracker.remove(ack_num)
|
tracker.remove(ack_num)
|
||||||
|
stats.APRSDStats().ack_rx_inc()
|
||||||
return
|
return
|
||||||
|
|
||||||
def process_mic_e_packet(self, packet):
|
def process_mic_e_packet(self, packet):
|
||||||
LOG.info("Mic-E Packet detected. Currenlty unsupported.")
|
LOG.info("Mic-E Packet detected. Currenlty unsupported.")
|
||||||
messaging.log_packet(packet)
|
messaging.log_packet(packet)
|
||||||
|
stats.APRSDStats().msgs_mice_inc()
|
||||||
return
|
return
|
||||||
|
|
||||||
def process_message_packet(self, packet):
|
def process_message_packet(self, packet):
|
||||||
@ -196,6 +230,7 @@ class APRSDRXThread(APRSDThread):
|
|||||||
|
|
||||||
try:
|
try:
|
||||||
LOG.info("Got message: {}".format(packet))
|
LOG.info("Got message: {}".format(packet))
|
||||||
|
stats.APRSDStats().msgs_rx_inc()
|
||||||
|
|
||||||
msg = packet.get("message_text", None)
|
msg = packet.get("message_text", None)
|
||||||
msg_format = packet.get("format", None)
|
msg_format = packet.get("format", None)
|
||||||
|
@ -25,6 +25,11 @@ DEFAULT_CONFIG_DICT = {
|
|||||||
"plugin_dir": "~/.config/aprsd/plugins",
|
"plugin_dir": "~/.config/aprsd/plugins",
|
||||||
"enabled_plugins": plugin.CORE_PLUGINS,
|
"enabled_plugins": plugin.CORE_PLUGINS,
|
||||||
"units": "imperial",
|
"units": "imperial",
|
||||||
|
"web": {
|
||||||
|
"enabled": True,
|
||||||
|
"host": "0.0.0.0",
|
||||||
|
"port": 8001,
|
||||||
|
},
|
||||||
"email": {
|
"email": {
|
||||||
"enabled": True,
|
"enabled": True,
|
||||||
"shortcuts": {
|
"shortcuts": {
|
||||||
|
@ -23,6 +23,14 @@ aprsd.client module
|
|||||||
aprsd.dev module
|
aprsd.dev module
|
||||||
----------------
|
----------------
|
||||||
|
|
||||||
|
.. automodule:: aprsd.dev
|
||||||
|
:members:
|
||||||
|
:undoc-members:
|
||||||
|
:show-inheritance:
|
||||||
|
|
||||||
|
aprsd.dev module
|
||||||
|
----------------
|
||||||
|
|
||||||
.. automodule:: aprsd.dev
|
.. automodule:: aprsd.dev
|
||||||
:members:
|
:members:
|
||||||
:undoc-members:
|
:undoc-members:
|
||||||
@ -44,6 +52,14 @@ aprsd.fake\_aprs module
|
|||||||
:undoc-members:
|
:undoc-members:
|
||||||
:show-inheritance:
|
:show-inheritance:
|
||||||
|
|
||||||
|
aprsd.flask module
|
||||||
|
------------------
|
||||||
|
|
||||||
|
.. automodule:: aprsd.flask
|
||||||
|
:members:
|
||||||
|
:undoc-members:
|
||||||
|
:show-inheritance:
|
||||||
|
|
||||||
aprsd.fuzzyclock module
|
aprsd.fuzzyclock module
|
||||||
-----------------------
|
-----------------------
|
||||||
|
|
||||||
@ -79,6 +95,14 @@ aprsd.plugin module
|
|||||||
aprsd.plugin\_utils module
|
aprsd.plugin\_utils module
|
||||||
--------------------------
|
--------------------------
|
||||||
|
|
||||||
|
.. automodule:: aprsd.plugin_utils
|
||||||
|
:members:
|
||||||
|
:undoc-members:
|
||||||
|
:show-inheritance:
|
||||||
|
|
||||||
|
aprsd.plugin\_utils module
|
||||||
|
--------------------------
|
||||||
|
|
||||||
.. automodule:: aprsd.plugin_utils
|
.. automodule:: aprsd.plugin_utils
|
||||||
:members:
|
:members:
|
||||||
:undoc-members:
|
:undoc-members:
|
||||||
|
@ -12,3 +12,5 @@ py3-validate-email
|
|||||||
pre-commit
|
pre-commit
|
||||||
pytz
|
pytz
|
||||||
opencage
|
opencage
|
||||||
|
flask
|
||||||
|
flask_classful
|
||||||
|
@ -2,7 +2,7 @@
|
|||||||
# This file is autogenerated by pip-compile
|
# This file is autogenerated by pip-compile
|
||||||
# To update, run:
|
# To update, run:
|
||||||
#
|
#
|
||||||
# pip-compile
|
# pip-compile requirements.in
|
||||||
#
|
#
|
||||||
appdirs==1.4.4
|
appdirs==1.4.4
|
||||||
# via virtualenv
|
# via virtualenv
|
||||||
@ -24,6 +24,7 @@ click==7.1.2
|
|||||||
# via
|
# via
|
||||||
# -r requirements.in
|
# -r requirements.in
|
||||||
# click-completion
|
# click-completion
|
||||||
|
# flask
|
||||||
cryptography==3.3.1
|
cryptography==3.3.1
|
||||||
# via pyopenssl
|
# via pyopenssl
|
||||||
distlib==0.3.1
|
distlib==0.3.1
|
||||||
@ -34,6 +35,12 @@ filelock==3.0.12
|
|||||||
# via
|
# via
|
||||||
# py3-validate-email
|
# py3-validate-email
|
||||||
# virtualenv
|
# virtualenv
|
||||||
|
flask-classful==0.14.2
|
||||||
|
# via -r requirements.in
|
||||||
|
flask==1.1.2
|
||||||
|
# via
|
||||||
|
# -r requirements.in
|
||||||
|
# flask-classful
|
||||||
identify==1.5.13
|
identify==1.5.13
|
||||||
# via pre-commit
|
# via pre-commit
|
||||||
idna==2.10
|
idna==2.10
|
||||||
@ -42,8 +49,12 @@ idna==2.10
|
|||||||
# requests
|
# requests
|
||||||
imapclient==2.2.0
|
imapclient==2.2.0
|
||||||
# via -r requirements.in
|
# via -r requirements.in
|
||||||
|
itsdangerous==1.1.0
|
||||||
|
# via flask
|
||||||
jinja2==2.11.2
|
jinja2==2.11.2
|
||||||
# via click-completion
|
# via
|
||||||
|
# click-completion
|
||||||
|
# flask
|
||||||
markupsafe==1.1.1
|
markupsafe==1.1.1
|
||||||
# via jinja2
|
# via jinja2
|
||||||
nodeenv==1.5.0
|
nodeenv==1.5.0
|
||||||
@ -64,7 +75,7 @@ pyopenssl==20.0.1
|
|||||||
# via opencage
|
# via opencage
|
||||||
pytz==2020.5
|
pytz==2020.5
|
||||||
# via -r requirements.in
|
# via -r requirements.in
|
||||||
pyyaml==5.3.1
|
pyyaml==5.4.1
|
||||||
# via
|
# via
|
||||||
# -r requirements.in
|
# -r requirements.in
|
||||||
# pre-commit
|
# pre-commit
|
||||||
@ -91,3 +102,5 @@ urllib3==1.26.2
|
|||||||
# via requests
|
# via requests
|
||||||
virtualenv==20.4.0
|
virtualenv==20.4.0
|
||||||
# via pre-commit
|
# via pre-commit
|
||||||
|
werkzeug==1.0.1
|
||||||
|
# via flask
|
||||||
|
Loading…
Reference in New Issue
Block a user