aprsd 3.4.3__tar.gz → 3.4.4__tar.gz

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 (219) hide show
  1. {aprsd-3.4.3 → aprsd-3.4.4}/ChangeLog.md +69 -0
  2. {aprsd-3.4.3 → aprsd-3.4.4}/PKG-INFO +89 -33
  3. {aprsd-3.4.3 → aprsd-3.4.4}/README.rst +63 -7
  4. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/client/aprsis.py +39 -10
  5. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/client/base.py +47 -10
  6. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/client/drivers/aprsis.py +5 -2
  7. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/client/factory.py +6 -1
  8. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/client/fake.py +5 -2
  9. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/client/kiss.py +26 -5
  10. aprsd-3.4.4/aprsd/client/stats.py +20 -0
  11. aprsd-3.4.4/aprsd/cmds/admin.py +57 -0
  12. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/cmds/dev.py +1 -1
  13. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/cmds/fetch_stats.py +155 -0
  14. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/cmds/healthcheck.py +2 -2
  15. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/cmds/listen.py +93 -6
  16. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/cmds/server.py +18 -10
  17. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/cmds/webchat.py +41 -53
  18. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/conf/common.py +11 -0
  19. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/main.py +10 -6
  20. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/packets/core.py +28 -27
  21. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/packets/packet_list.py +13 -23
  22. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/plugin.py +12 -5
  23. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/plugins/email.py +6 -0
  24. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/plugins/fortune.py +2 -2
  25. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/plugins/location.py +6 -4
  26. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/stats/__init__.py +0 -2
  27. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/stats/collector.py +6 -1
  28. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/threads/aprsd.py +47 -5
  29. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/threads/keep_alive.py +8 -0
  30. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/threads/rx.py +40 -12
  31. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/threads/tx.py +31 -6
  32. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/utils/__init__.py +20 -5
  33. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/utils/counter.py +15 -12
  34. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/utils/trace.py +4 -2
  35. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/static/js/send-message.js +48 -21
  36. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/wsgi.py +8 -1
  37. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd.egg-info/PKG-INFO +89 -33
  38. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd.egg-info/SOURCES.txt +4 -0
  39. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd.egg-info/requires.txt +25 -25
  40. {aprsd-3.4.3 → aprsd-3.4.4}/requirements-dev.txt +13 -13
  41. {aprsd-3.4.3 → aprsd-3.4.4}/requirements.in +1 -2
  42. {aprsd-3.4.3 → aprsd-3.4.4}/requirements.txt +13 -13
  43. aprsd-3.4.4/tests/client/test_aprsis.py +88 -0
  44. aprsd-3.4.4/tests/client/test_client_base.py +140 -0
  45. aprsd-3.4.4/tests/client/test_factory.py +75 -0
  46. {aprsd-3.4.3 → aprsd-3.4.4}/tests/cmds/test_webchat.py +4 -0
  47. {aprsd-3.4.3 → aprsd-3.4.4}/tests/test_main.py +1 -7
  48. aprsd-3.4.3/aprsd/client/stats.py +0 -38
  49. {aprsd-3.4.3 → aprsd-3.4.4}/.coveragerc +0 -0
  50. {aprsd-3.4.3 → aprsd-3.4.4}/.github/workflows/codeql.yml +0 -0
  51. {aprsd-3.4.3 → aprsd-3.4.4}/.github/workflows/manual_build.yml +0 -0
  52. {aprsd-3.4.3 → aprsd-3.4.4}/.github/workflows/master-build.yml +0 -0
  53. {aprsd-3.4.3 → aprsd-3.4.4}/.github/workflows/python.yml +0 -0
  54. {aprsd-3.4.3 → aprsd-3.4.4}/.github/workflows/release_build.yml +0 -0
  55. {aprsd-3.4.3 → aprsd-3.4.4}/.pre-commit-config.yaml +0 -0
  56. {aprsd-3.4.3 → aprsd-3.4.4}/.readthedocs.yaml +0 -0
  57. {aprsd-3.4.3 → aprsd-3.4.4}/AUTHORS +0 -0
  58. {aprsd-3.4.3 → aprsd-3.4.4}/INSTALL.txt +0 -0
  59. {aprsd-3.4.3 → aprsd-3.4.4}/LICENSE +0 -0
  60. {aprsd-3.4.3 → aprsd-3.4.4}/MANIFEST.in +0 -0
  61. {aprsd-3.4.3 → aprsd-3.4.4}/Makefile +0 -0
  62. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/__init__.py +0 -0
  63. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/cli_helper.py +0 -0
  64. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/client/__init__.py +0 -0
  65. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/client/drivers/__init__.py +0 -0
  66. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/client/drivers/fake.py +0 -0
  67. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/client/drivers/kiss.py +0 -0
  68. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/cmds/__init__.py +0 -0
  69. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/cmds/completion.py +0 -0
  70. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/cmds/list_plugins.py +0 -0
  71. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/cmds/send_message.py +0 -0
  72. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/conf/__init__.py +0 -0
  73. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/conf/client.py +0 -0
  74. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/conf/log.py +0 -0
  75. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/conf/opts.py +0 -0
  76. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/conf/plugin_common.py +0 -0
  77. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/conf/plugin_email.py +0 -0
  78. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/exception.py +0 -0
  79. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/log/__init__.py +0 -0
  80. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/log/log.py +0 -0
  81. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/packets/__init__.py +0 -0
  82. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/packets/collector.py +0 -0
  83. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/packets/log.py +0 -0
  84. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/packets/seen_list.py +0 -0
  85. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/packets/tracker.py +0 -0
  86. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/packets/watch_list.py +0 -0
  87. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/plugin_utils.py +0 -0
  88. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/plugins/__init__.py +0 -0
  89. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/plugins/notify.py +0 -0
  90. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/plugins/ping.py +0 -0
  91. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/plugins/time.py +0 -0
  92. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/plugins/version.py +0 -0
  93. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/plugins/weather.py +0 -0
  94. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/stats/app.py +0 -0
  95. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/threads/__init__.py +0 -0
  96. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/threads/log_monitor.py +0 -0
  97. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/threads/registry.py +0 -0
  98. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/threads/stats.py +0 -0
  99. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/utils/fuzzyclock.py +0 -0
  100. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/utils/json.py +0 -0
  101. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/utils/objectstore.py +0 -0
  102. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/utils/ring_buffer.py +0 -0
  103. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/__init__.py +0 -0
  104. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/admin/__init__.py +0 -0
  105. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/admin/static/css/index.css +0 -0
  106. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/admin/static/css/prism.css +0 -0
  107. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/admin/static/css/tabs.css +0 -0
  108. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/admin/static/images/Untitled.png +0 -0
  109. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/admin/static/images/aprs-symbols-16-0.png +0 -0
  110. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/admin/static/images/aprs-symbols-16-1.png +0 -0
  111. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/admin/static/images/aprs-symbols-64-0.png +0 -0
  112. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/admin/static/images/aprs-symbols-64-1.png +0 -0
  113. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/admin/static/images/aprs-symbols-64-2.png +0 -0
  114. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/admin/static/js/charts.js +0 -0
  115. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/admin/static/js/echarts.js +0 -0
  116. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/admin/static/js/logs.js +0 -0
  117. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/admin/static/js/main.js +0 -0
  118. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/admin/static/js/prism.js +0 -0
  119. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/admin/static/js/send-message.js +0 -0
  120. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/admin/static/js/tabs.js +0 -0
  121. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/admin/templates/index.html +0 -0
  122. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/static/css/chat.css +0 -0
  123. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/static/css/index.css +0 -0
  124. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/static/css/style.css.map +0 -0
  125. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/static/css/tabs.css +0 -0
  126. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/static/css/upstream/bootstrap.min.css +0 -0
  127. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/static/css/upstream/font.woff2 +0 -0
  128. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/static/css/upstream/google-fonts.css +0 -0
  129. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/static/css/upstream/jquery-ui.css +0 -0
  130. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/static/css/upstream/jquery.toast.css +0 -0
  131. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/static/css/upstream/themes/default/assets/fonts/LatoLatin-Bold.woff +0 -0
  132. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/static/css/upstream/themes/default/assets/fonts/LatoLatin-Bold.woff2 +0 -0
  133. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/static/css/upstream/themes/default/assets/fonts/LatoLatin-Regular.woff +0 -0
  134. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/static/css/upstream/themes/default/assets/fonts/LatoLatin-Regular.woff2 +0 -0
  135. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/static/css/upstream/themes/default/assets/fonts/icons.woff +0 -0
  136. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/static/css/upstream/themes/default/assets/fonts/icons.woff2 +0 -0
  137. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/static/css/upstream/themes/default/assets/fonts/outline-icons.woff +0 -0
  138. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/static/css/upstream/themes/default/assets/fonts/outline-icons.woff2 +0 -0
  139. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/static/images/Untitled.png +0 -0
  140. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/static/images/aprs-symbols-16-0.png +0 -0
  141. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/static/images/aprs-symbols-16-1.png +0 -0
  142. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/static/images/aprs-symbols-64-0.png +0 -0
  143. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/static/images/aprs-symbols-64-1.png +0 -0
  144. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/static/images/aprs-symbols-64-2.png +0 -0
  145. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/static/images/globe.svg +0 -0
  146. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/static/js/gps.js +0 -0
  147. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/static/js/main.js +0 -0
  148. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/static/js/tabs.js +0 -0
  149. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/static/js/upstream/bootstrap.bundle.min.js +0 -0
  150. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/static/js/upstream/jquery-3.7.1.min.js +0 -0
  151. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/static/js/upstream/jquery-ui.min.js +0 -0
  152. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/static/js/upstream/jquery.toast.js +0 -0
  153. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/static/js/upstream/semantic.min.js +0 -0
  154. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/static/js/upstream/socket.io.min.js +0 -0
  155. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd/web/chat/templates/index.html +0 -0
  156. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd-lnav.json +0 -0
  157. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd.egg-info/dependency_links.txt +0 -0
  158. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd.egg-info/entry_points.txt +0 -0
  159. {aprsd-3.4.3 → aprsd-3.4.4}/aprsd.egg-info/top_level.txt +0 -0
  160. {aprsd-3.4.3 → aprsd-3.4.4}/docker/Dockerfile +0 -0
  161. {aprsd-3.4.3 → aprsd-3.4.4}/docker/bin/admin.sh +0 -0
  162. {aprsd-3.4.3 → aprsd-3.4.4}/docker/bin/listen.sh +0 -0
  163. {aprsd-3.4.3 → aprsd-3.4.4}/docker/bin/run.sh +0 -0
  164. {aprsd-3.4.3 → aprsd-3.4.4}/docker/bin/setup.sh +0 -0
  165. {aprsd-3.4.3 → aprsd-3.4.4}/docker/build.sh +0 -0
  166. {aprsd-3.4.3 → aprsd-3.4.4}/docker/docker-compose.yml +0 -0
  167. {aprsd-3.4.3 → aprsd-3.4.4}/docs/_static/.keep +0 -0
  168. {aprsd-3.4.3 → aprsd-3.4.4}/docs/_static/aprsd_overview.png +0 -0
  169. {aprsd-3.4.3 → aprsd-3.4.4}/docs/_static/aprsd_overview.svg +0 -0
  170. {aprsd-3.4.3 → aprsd-3.4.4}/docs/_templates/.keep +0 -0
  171. {aprsd-3.4.3 → aprsd-3.4.4}/docs/apidoc/aprsd.client.drivers.rst +0 -0
  172. {aprsd-3.4.3 → aprsd-3.4.4}/docs/apidoc/aprsd.client.rst +0 -0
  173. {aprsd-3.4.3 → aprsd-3.4.4}/docs/apidoc/aprsd.cmds.rst +0 -0
  174. {aprsd-3.4.3 → aprsd-3.4.4}/docs/apidoc/aprsd.conf.rst +0 -0
  175. {aprsd-3.4.3 → aprsd-3.4.4}/docs/apidoc/aprsd.log.rst +0 -0
  176. {aprsd-3.4.3 → aprsd-3.4.4}/docs/apidoc/aprsd.packets.rst +0 -0
  177. {aprsd-3.4.3 → aprsd-3.4.4}/docs/apidoc/aprsd.plugins.rst +0 -0
  178. {aprsd-3.4.3 → aprsd-3.4.4}/docs/apidoc/aprsd.rst +0 -0
  179. {aprsd-3.4.3 → aprsd-3.4.4}/docs/apidoc/aprsd.stats.rst +0 -0
  180. {aprsd-3.4.3 → aprsd-3.4.4}/docs/apidoc/aprsd.threads.rst +0 -0
  181. {aprsd-3.4.3 → aprsd-3.4.4}/docs/apidoc/aprsd.utils.rst +0 -0
  182. {aprsd-3.4.3 → aprsd-3.4.4}/docs/apidoc/aprsd.web.admin.rst +0 -0
  183. {aprsd-3.4.3 → aprsd-3.4.4}/docs/apidoc/aprsd.web.rst +0 -0
  184. {aprsd-3.4.3 → aprsd-3.4.4}/docs/apidoc/modules.rst +0 -0
  185. {aprsd-3.4.3 → aprsd-3.4.4}/docs/aprsd.drawio +0 -0
  186. {aprsd-3.4.3 → aprsd-3.4.4}/docs/changelog.rst +0 -0
  187. {aprsd-3.4.3 → aprsd-3.4.4}/docs/clean_docs.py +0 -0
  188. {aprsd-3.4.3 → aprsd-3.4.4}/docs/conf.py +0 -0
  189. {aprsd-3.4.3 → aprsd-3.4.4}/docs/configure.rst +0 -0
  190. {aprsd-3.4.3 → aprsd-3.4.4}/docs/index.rst +0 -0
  191. {aprsd-3.4.3 → aprsd-3.4.4}/docs/install.rst +0 -0
  192. {aprsd-3.4.3 → aprsd-3.4.4}/docs/links.rst +0 -0
  193. {aprsd-3.4.3 → aprsd-3.4.4}/docs/plugin.rst +0 -0
  194. {aprsd-3.4.3 → aprsd-3.4.4}/docs/readme.rst +0 -0
  195. {aprsd-3.4.3 → aprsd-3.4.4}/docs/server.rst +0 -0
  196. {aprsd-3.4.3 → aprsd-3.4.4}/examples/plugins/__init__.py +0 -0
  197. {aprsd-3.4.3 → aprsd-3.4.4}/examples/plugins/example_plugin.py +0 -0
  198. {aprsd-3.4.3 → aprsd-3.4.4}/gray.conf +0 -0
  199. {aprsd-3.4.3 → aprsd-3.4.4}/pyproject.toml +0 -0
  200. {aprsd-3.4.3 → aprsd-3.4.4}/requirements-dev.in +0 -0
  201. {aprsd-3.4.3 → aprsd-3.4.4}/setup.cfg +0 -0
  202. {aprsd-3.4.3 → aprsd-3.4.4}/setup.py +0 -0
  203. {aprsd-3.4.3 → aprsd-3.4.4}/tests/__init__.py +0 -0
  204. {aprsd-3.4.3 → aprsd-3.4.4}/tests/cmds/__init__.py +0 -0
  205. {aprsd-3.4.3 → aprsd-3.4.4}/tests/cmds/test_send_message.py +0 -0
  206. {aprsd-3.4.3 → aprsd-3.4.4}/tests/fake.py +0 -0
  207. {aprsd-3.4.3 → aprsd-3.4.4}/tests/plugins/__init__.py +0 -0
  208. {aprsd-3.4.3 → aprsd-3.4.4}/tests/plugins/test_fortune.py +0 -0
  209. {aprsd-3.4.3 → aprsd-3.4.4}/tests/plugins/test_location.py +0 -0
  210. {aprsd-3.4.3 → aprsd-3.4.4}/tests/plugins/test_notify.py +0 -0
  211. {aprsd-3.4.3 → aprsd-3.4.4}/tests/plugins/test_ping.py +0 -0
  212. {aprsd-3.4.3 → aprsd-3.4.4}/tests/plugins/test_time.py +0 -0
  213. {aprsd-3.4.3 → aprsd-3.4.4}/tests/plugins/test_version.py +0 -0
  214. {aprsd-3.4.3 → aprsd-3.4.4}/tests/plugins/test_weather.py +0 -0
  215. {aprsd-3.4.3 → aprsd-3.4.4}/tests/test_email.py +0 -0
  216. {aprsd-3.4.3 → aprsd-3.4.4}/tests/test_packets.py +0 -0
  217. {aprsd-3.4.3 → aprsd-3.4.4}/tests/test_plugin.py +0 -0
  218. {aprsd-3.4.3 → aprsd-3.4.4}/tools/fast8.sh +0 -0
  219. {aprsd-3.4.3 → aprsd-3.4.4}/tox.ini +0 -0
@@ -4,12 +4,81 @@ All notable changes to this project will be documented in this file. Dates are d
4
4
 
5
5
  Generated by [`auto-changelog`](https://github.com/CookPete/auto-changelog).
6
6
 
7
+ #### [3.4.4](https://github.com/craigerl/aprsd/compare/3.4.3...3.4.4)
8
+
9
+ > 6 December 2024
10
+
11
+ - Update counter.py [`#182`](https://github.com/craigerl/aprsd/pull/182)
12
+ - Added an option to disable the loading of the help plugin. [`#177`](https://github.com/craigerl/aprsd/pull/177)
13
+ - Added unit test for client base [`#181`](https://github.com/craigerl/aprsd/pull/181)
14
+ - Walt listen test [`#180`](https://github.com/craigerl/aprsd/pull/180)
15
+ - Bump werkzeug from 3.0.4 to 3.0.6 [`#178`](https://github.com/craigerl/aprsd/pull/178)
16
+ - Added new aprsd admin command [`0271ccd`](https://github.com/craigerl/aprsd/commit/0271ccd14582cf042846e9c65c64fe501538bc5a)
17
+ - Added some changes to listen [`df0ca04`](https://github.com/craigerl/aprsd/commit/df0ca0448373b1ce5707b01b2acaca9a50340715)
18
+ - Added some changes to listen [`d863474`](https://github.com/craigerl/aprsd/commit/d863474c133d7650f9c79d1a88f0a4a04a2b056f)
19
+ - Fix a small issue with packet sending failures [`3fd6069`](https://github.com/craigerl/aprsd/commit/3fd606946db8df368da0cd0e9f6e9a0c18d36525)
20
+ - Fix a small issue with packet sending failures [`f265e8f`](https://github.com/craigerl/aprsd/commit/f265e8f3541701eeaaba820ed93eb23902b40f05)
21
+ - Added new dump-stats command [`add18f1`](https://github.com/craigerl/aprsd/commit/add18f1a6f08a8eda6729c82634c0e68f73b48f8)
22
+ - Update PacketList [`7e8d7cd`](https://github.com/craigerl/aprsd/commit/7e8d7cdf8671fbc559400ef2041d5bbe6fdb8c6d)
23
+ - Updated APRSClient [`d808e21`](https://github.com/craigerl/aprsd/commit/d808e217a2bdd1cfffa7d69344a0b9a664bf2f6f)
24
+ - Calculate delta once and reuse it [`0be87d8`](https://github.com/craigerl/aprsd/commit/0be87d8b4f1fa258a5cd32188eccd4aa22b7446e)
25
+ - Added unit test for ClientFactory [`ab2de86`](https://github.com/craigerl/aprsd/commit/ab2de86726106582c06230ed4e513d78f0bafb03)
26
+ - Added unit test for APRSISClient [`224686c`](https://github.com/craigerl/aprsd/commit/224686cac5e4cefd559fb9149ccac18069914423)
27
+ - optimized Packet.get() [`579d0c9`](https://github.com/craigerl/aprsd/commit/579d0c95a085a7cb796ae9476da8c48fca201601)
28
+ - fixed name for dump-stats output [`563b068`](https://github.com/craigerl/aprsd/commit/563b06876c02eb9193b0c7559765e47d932a5978)
29
+ - updated README.rst [`229155d`](https://github.com/craigerl/aprsd/commit/229155d0ee63aa80c8bc4ffbdbb5a3eb8a4a6e7c)
30
+ - Only load EmailStats if email is enabled [`2fdc7b1`](https://github.com/craigerl/aprsd/commit/2fdc7b111d31006b568e820ee7aaa8290f5944b9)
31
+ - Added rich output for dump-stats [`d0018a8`](https://github.com/craigerl/aprsd/commit/d0018a8cd39d8d9b74b83655083b33be2e2b70a7)
32
+ - Allow disabling sending all AckPackets [`6e62ac1`](https://github.com/craigerl/aprsd/commit/6e62ac14b8cca193faf6c73464eb47e54efd7abe)
33
+ - Allow loading a specific list of plugins [`9f3c8f8`](https://github.com/craigerl/aprsd/commit/9f3c8f889f1866a7747bc82c1b3c2c39687dcb1c)
34
+ - Catch and log exceptions in consumer [`adcf94d`](https://github.com/craigerl/aprsd/commit/adcf94d8c755af7020ac93d7fb3731c637aefc3e)
35
+ - Fixed the protocol for Stats Collector [`bd0bcc1`](https://github.com/craigerl/aprsd/commit/bd0bcc19244a8a5bf0bf851533eb303e7845c8ca)
36
+ - Added new features to listen command. [`7d1e739`](https://github.com/craigerl/aprsd/commit/7d1e73950288c721bb5a07224bc4b5bb52bb9164)
37
+ - Don't break logging aprslib failures [`98a6210`](https://github.com/craigerl/aprsd/commit/98a62102b742960ff7202b0614fc2801dd60ad12)
38
+ - Change healthcheck email thread check timeout [`03ce5a3`](https://github.com/craigerl/aprsd/commit/03ce5a3d506a1304b93fd11cd2a43661f874d144)
39
+ - Addressing comments in PR. [`2471492`](https://github.com/craigerl/aprsd/commit/24714923be4c55fdac434a868707e917b6ed21b1)
40
+ - Update utils.trace [`c3df974`](https://github.com/craigerl/aprsd/commit/c3df97400458d1f3c72a03d0f9ae72addad63d29)
41
+ - Update requirements [`257fa0d`](https://github.com/craigerl/aprsd/commit/257fa0db7d9f9cef8b3235cacf954adb862a2bfb)
42
+ - Fixes for webchat UI. [`f0b9956`](https://github.com/craigerl/aprsd/commit/f0b99564d15fedb055c9e2cb1ea9146814024478)
43
+ - Sending message to new callsign displays in an active tab [`d42638e`](https://github.com/craigerl/aprsd/commit/d42638efe3ebb22d777573d934ed4dd8216ac705)
44
+ - Update WebChat [`9f7d169`](https://github.com/craigerl/aprsd/commit/9f7d169c18c6ac593d49efd9dde42bc40b28bc70)
45
+ - Update Client to report login status [`06c1fb9`](https://github.com/craigerl/aprsd/commit/06c1fb985efea1f6697bedbe340557cde7225bf4)
46
+ - Updated server client checks [`1c50c39`](https://github.com/craigerl/aprsd/commit/1c50c39e6104d6e9462fd9ed5e2deed7f9e6b1fe)
47
+ - Fixed broken unit tests [`c82e9ba`](https://github.com/craigerl/aprsd/commit/c82e9ba5977424e6f03ddbbfcbd816634ef667ce)
48
+ - Fixed pep8 failure on counter.py [`1eaa4b8`](https://github.com/craigerl/aprsd/commit/1eaa4b8e10f12ba8fe17b0cee44d6dee4a5689aa)
49
+ - No reason to create the client in init [`e99c906`](https://github.com/craigerl/aprsd/commit/e99c906fed564fecae0f389fa21f25e624db9088)
50
+ - Added APRSDThread pause/unpause capability [`95094b8`](https://github.com/craigerl/aprsd/commit/95094b874cc99201497cb7920a0c73c7c332e65a)
51
+ - Added client_exists() for client factory [`505565d`](https://github.com/craigerl/aprsd/commit/505565d3a6befaba3b57c87c22333b0e965ab347)
52
+ - Added pause_all, unpause_all in threadlist [`76d275d`](https://github.com/craigerl/aprsd/commit/76d275db9c8968ce5bd9b52e52fa39c9002aaa86)
53
+ - Make sure to sleep(1) in the main RX thread [`98a96cb`](https://github.com/craigerl/aprsd/commit/98a96cbe34ee50bbd242542c5891768608e586b4)
54
+ - Put safety checks around the timeago for keepalive [`be6357a`](https://github.com/craigerl/aprsd/commit/be6357a552e8c05b5fd5a94d4fb6318abaf78cfc)
55
+ - Properly report TCPKISS connection [`3e488db`](https://github.com/craigerl/aprsd/commit/3e488db3d7e864c6b4411ce67d5018648faeac2d)
56
+ - Fix call in kiss consumer [`aba5bb0`](https://github.com/craigerl/aprsd/commit/aba5bb03a2dd973e545a5f1ec0515c8f500ddadb)
57
+ - Update RX Packet dupe checking [`8f3da96`](https://github.com/craigerl/aprsd/commit/8f3da961e7802340f9a77d437631c6bbe94e0102)
58
+ - Webchat: Don't automatically fetch location KISS [`e8ae380`](https://github.com/craigerl/aprsd/commit/e8ae3807db87880ec65923854b07e5cc225a72c3)
59
+ - Fixed issue not processing null msg ids [`a17b80d`](https://github.com/craigerl/aprsd/commit/a17b80ddd871bfd16c59b29a9a7f7ef34f921f6c)
60
+ - Updated keepalive thread to report client [`8529f1f`](https://github.com/craigerl/aprsd/commit/8529f1f8d1a4a86a66aecfda6e6075c394bbff56)
61
+ - Fixed webchat popovers not working. [`3a8b8f2`](https://github.com/craigerl/aprsd/commit/3a8b8f26dda9d7b4099061b2a24a393fb639124c)
62
+ - Fixed issue with packet object and prepare() [`f66b962`](https://github.com/craigerl/aprsd/commit/f66b96288f7c594bc9775f28ffc93e3bbd3bb46f)
63
+ - Fixed webchat packets without msgNo [`d4ae726`](https://github.com/craigerl/aprsd/commit/d4ae72608b9d7c2da1b89c20bf58fcae796f552d)
64
+ - Added __contains__ to threadlist [`d94a3e7`](https://github.com/craigerl/aprsd/commit/d94a3e7b908fd313a8af0c71a4928114ea83cf35)
65
+ - Update healthcheck [`7fb0c74`](https://github.com/craigerl/aprsd/commit/7fb0c7454ea9fe4cd5886989e9890ef70a789fdf)
66
+ - Remove dataclasses from requirements [`db73a54`](https://github.com/craigerl/aprsd/commit/db73a540baf0c8d658d1f9efa08ba9f085ce01d4)
67
+ - Update requirements.dev [`0d8a1ac`](https://github.com/craigerl/aprsd/commit/0d8a1ac33441cf85270423b80264110fe9286754)
68
+ - Added new acked property to the core Packet [`3c058f3`](https://github.com/craigerl/aprsd/commit/3c058f3e7b89227c613234f8ae91687fbdf19ae1)
69
+ - Fixed some pep8 failures [`63bcd41`](https://github.com/craigerl/aprsd/commit/63bcd4139bb40718152b66002dfa45f236c54e11)
70
+
71
+ #### [3.4.3](https://github.com/craigerl/aprsd/compare/v3.4.3...3.4.3)
72
+
73
+ > 18 November 2024
74
+
7
75
  #### [v3.4.3](https://github.com/craigerl/aprsd/compare/v3.4.2...v3.4.3)
8
76
 
9
77
  > 29 October 2024
10
78
 
11
79
  - Change virtual env name to .venv [`882e907`](https://github.com/craigerl/aprsd/commit/882e90767dd967a4d1018c834a074b33ca9dcb06)
12
80
  - Fixed issue in send_message command [`ecf30d3`](https://github.com/craigerl/aprsd/commit/ecf30d33978e26150bf41ff60b97ff00ab5d5f96)
81
+ - Update Changelog for v3.4.3 [`5780626`](https://github.com/craigerl/aprsd/commit/578062648bb1c188e578c88000852e477a429364)
13
82
 
14
83
  #### [v3.4.2](https://github.com/craigerl/aprsd/compare/v3.4.1...v3.4.2)
15
84
 
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: aprsd
3
- Version: 3.4.3
3
+ Version: 3.4.4
4
4
  Summary: APRSd is a APRS-IS server that can be used to connect to APRS-IS and send and receive APRS packets.
5
5
  Author-email: Craig Lamparter <craig@craiger.org>, "Walter A. Boring IV" <waboring@hemna.com>, Emre Saglam <emresaglam@gmail.com>, Jason Martin <jhmartin@toger.us>, John <johng42@users.noreply.github.com>, Martiros Shakhzadyan <vrzh@vrzh.net>, Zoe Moore <zoenb@mailbox.org>, ranguli <hello@joshmurphy.ca>
6
6
  Maintainer-email: Craig Lamparter <craig@craiger.org>, "Walter A. Boring IV" <waboring@hemna.com>
@@ -207,17 +207,16 @@ Requires-Dist: ax253==0.1.5.post1
207
207
  Requires-Dist: beautifulsoup4==4.12.3
208
208
  Requires-Dist: bidict==0.23.1
209
209
  Requires-Dist: bitarray==3.0.0
210
- Requires-Dist: blinker==1.8.2
210
+ Requires-Dist: blinker==1.9.0
211
211
  Requires-Dist: certifi==2024.8.30
212
212
  Requires-Dist: charset-normalizer==3.4.0
213
213
  Requires-Dist: click==8.1.7
214
214
  Requires-Dist: click-params==0.5.0
215
215
  Requires-Dist: commonmark==0.9.1
216
- Requires-Dist: dataclasses==0.6
217
216
  Requires-Dist: dataclasses-json==0.6.7
218
217
  Requires-Dist: debtcollector==3.0.0
219
- Requires-Dist: deprecated==1.2.14
220
- Requires-Dist: flask==3.0.3
218
+ Requires-Dist: deprecated==1.2.15
219
+ Requires-Dist: flask==3.1.0
221
220
  Requires-Dist: flask-httpauth==4.8.0
222
221
  Requires-Dist: flask-socketio==5.4.1
223
222
  Requires-Dist: geographiclib==2.0
@@ -231,12 +230,12 @@ Requires-Dist: jinja2==3.1.4
231
230
  Requires-Dist: kiss3==8.0.0
232
231
  Requires-Dist: loguru==0.7.2
233
232
  Requires-Dist: markupsafe==3.0.2
234
- Requires-Dist: marshmallow==3.23.0
233
+ Requires-Dist: marshmallow==3.23.1
235
234
  Requires-Dist: mypy-extensions==1.0.0
236
235
  Requires-Dist: netaddr==1.3.0
237
- Requires-Dist: oslo-config==9.6.0
238
- Requires-Dist: oslo-i18n==6.4.0
239
- Requires-Dist: packaging==24.1
236
+ Requires-Dist: oslo-config==9.7.0
237
+ Requires-Dist: oslo-i18n==6.5.0
238
+ Requires-Dist: packaging==24.2
240
239
  Requires-Dist: pbr==6.1.0
241
240
  Requires-Dist: pluggy==1.5.0
242
241
  Requires-Dist: pygments==2.18.0
@@ -254,19 +253,20 @@ Requires-Dist: shellingham==1.5.4
254
253
  Requires-Dist: simple-websocket==1.1.0
255
254
  Requires-Dist: six==1.16.0
256
255
  Requires-Dist: soupsieve==2.6
257
- Requires-Dist: stevedore==5.3.0
256
+ Requires-Dist: stevedore==5.4.0
258
257
  Requires-Dist: tabulate==0.9.0
259
258
  Requires-Dist: thesmuggler==1.0.1
259
+ Requires-Dist: timeago==1.0.16
260
260
  Requires-Dist: typing-extensions==4.12.2
261
261
  Requires-Dist: typing-inspect==0.9.0
262
262
  Requires-Dist: tzlocal==5.2
263
263
  Requires-Dist: update-checker==0.18.0
264
264
  Requires-Dist: urllib3==2.2.3
265
265
  Requires-Dist: validators==0.22.0
266
- Requires-Dist: werkzeug==3.0.4
267
- Requires-Dist: wrapt==1.16.0
266
+ Requires-Dist: werkzeug==3.1.3
267
+ Requires-Dist: wrapt==1.17.0
268
268
  Requires-Dist: wsproto==1.2.0
269
- Requires-Dist: zipp==3.20.2
269
+ Requires-Dist: zipp==3.21.0
270
270
  Provides-Extra: dev
271
271
  Requires-Dist: add-trailing-comma==3.1.0; extra == "dev"
272
272
  Requires-Dist: alabaster==1.0.0; extra == "dev"
@@ -284,7 +284,7 @@ Requires-Dist: click==8.1.7; extra == "dev"
284
284
  Requires-Dist: colorama==0.4.6; extra == "dev"
285
285
  Requires-Dist: commonmark==0.9.1; extra == "dev"
286
286
  Requires-Dist: configargparse==1.7; extra == "dev"
287
- Requires-Dist: coverage[toml]==7.6.3; extra == "dev"
287
+ Requires-Dist: coverage[toml]==7.6.8; extra == "dev"
288
288
  Requires-Dist: distlib==0.3.9; extra == "dev"
289
289
  Requires-Dist: docutils==0.21.2; extra == "dev"
290
290
  Requires-Dist: exceptiongroup==1.2.2; extra == "dev"
@@ -292,22 +292,22 @@ Requires-Dist: filelock==3.16.1; extra == "dev"
292
292
  Requires-Dist: fixit==2.1.0; extra == "dev"
293
293
  Requires-Dist: flake8==7.1.1; extra == "dev"
294
294
  Requires-Dist: gray==0.15.0; extra == "dev"
295
- Requires-Dist: identify==2.6.1; extra == "dev"
295
+ Requires-Dist: identify==2.6.3; extra == "dev"
296
296
  Requires-Dist: idna==3.10; extra == "dev"
297
297
  Requires-Dist: imagesize==1.4.1; extra == "dev"
298
298
  Requires-Dist: iniconfig==2.0.0; extra == "dev"
299
299
  Requires-Dist: isort==5.13.2; extra == "dev"
300
300
  Requires-Dist: jinja2==3.1.4; extra == "dev"
301
- Requires-Dist: libcst==1.5.0; extra == "dev"
301
+ Requires-Dist: libcst==1.5.1; extra == "dev"
302
302
  Requires-Dist: m2r==0.3.1; extra == "dev"
303
303
  Requires-Dist: markupsafe==3.0.2; extra == "dev"
304
304
  Requires-Dist: mccabe==0.7.0; extra == "dev"
305
305
  Requires-Dist: mistune==0.8.4; extra == "dev"
306
306
  Requires-Dist: moreorless==0.4.0; extra == "dev"
307
- Requires-Dist: mypy==1.12.0; extra == "dev"
307
+ Requires-Dist: mypy==1.13.0; extra == "dev"
308
308
  Requires-Dist: mypy-extensions==1.0.0; extra == "dev"
309
309
  Requires-Dist: nodeenv==1.9.1; extra == "dev"
310
- Requires-Dist: packaging==24.1; extra == "dev"
310
+ Requires-Dist: packaging==24.2; extra == "dev"
311
311
  Requires-Dist: pathspec==0.12.1; extra == "dev"
312
312
  Requires-Dist: pep8-naming==0.14.1; extra == "dev"
313
313
  Requires-Dist: pip-tools==7.4.1; extra == "dev"
@@ -319,9 +319,9 @@ Requires-Dist: pyflakes==3.2.0; extra == "dev"
319
319
  Requires-Dist: pygments==2.18.0; extra == "dev"
320
320
  Requires-Dist: pyproject-api==1.8.0; extra == "dev"
321
321
  Requires-Dist: pyproject-hooks==1.2.0; extra == "dev"
322
- Requires-Dist: pytest==8.3.3; extra == "dev"
323
- Requires-Dist: pytest-cov==5.0.0; extra == "dev"
324
- Requires-Dist: pyupgrade==3.18.0; extra == "dev"
322
+ Requires-Dist: pytest==8.3.4; extra == "dev"
323
+ Requires-Dist: pytest-cov==6.0.0; extra == "dev"
324
+ Requires-Dist: pyupgrade==3.19.0; extra == "dev"
325
325
  Requires-Dist: pyyaml==6.0.2; extra == "dev"
326
326
  Requires-Dist: requests==2.32.3; extra == "dev"
327
327
  Requires-Dist: rich==12.6.0; extra == "dev"
@@ -333,17 +333,17 @@ Requires-Dist: sphinxcontrib-htmlhelp==2.1.0; extra == "dev"
333
333
  Requires-Dist: sphinxcontrib-jsmath==1.0.1; extra == "dev"
334
334
  Requires-Dist: sphinxcontrib-qthelp==2.0.0; extra == "dev"
335
335
  Requires-Dist: sphinxcontrib-serializinghtml==2.0.0; extra == "dev"
336
- Requires-Dist: tokenize-rt==6.0.0; extra == "dev"
336
+ Requires-Dist: tokenize-rt==6.1.0; extra == "dev"
337
337
  Requires-Dist: toml==0.10.2; extra == "dev"
338
- Requires-Dist: tomli==2.0.2; extra == "dev"
339
- Requires-Dist: tox==4.23.0; extra == "dev"
338
+ Requires-Dist: tomli==2.2.1; extra == "dev"
339
+ Requires-Dist: tox==4.23.2; extra == "dev"
340
340
  Requires-Dist: trailrunner==1.4.0; extra == "dev"
341
341
  Requires-Dist: typing-extensions==4.12.2; extra == "dev"
342
342
  Requires-Dist: unify==0.5; extra == "dev"
343
343
  Requires-Dist: untokenize==0.1.1; extra == "dev"
344
344
  Requires-Dist: urllib3==2.2.3; extra == "dev"
345
- Requires-Dist: virtualenv==20.27.0; extra == "dev"
346
- Requires-Dist: wheel==0.44.0; extra == "dev"
345
+ Requires-Dist: virtualenv==20.28.0; extra == "dev"
346
+ Requires-Dist: wheel==0.45.1; extra == "dev"
347
347
 
348
348
  ===============================================
349
349
  APRSD - Ham radio APRS-IS Message plugin server
@@ -358,6 +358,37 @@ ____________________
358
358
  `APRSD <http://github.com/craigerl/aprsd>`_ is a Ham radio `APRS <http://aprs.org>`_ message command gateway built on python.
359
359
 
360
360
 
361
+ Table of Contents
362
+ =================
363
+
364
+ 1. `What is APRSD <#what-is-aprsd>`_
365
+ 2. `APRSD Overview Diagram <#aprsd-overview-diagram>`_
366
+ 3. `Typical Use Case <#typical-use-case>`_
367
+ 4. `Installation <#installation>`_
368
+ 5. `Example Usage <#example-usage>`_
369
+ 6. `Help <#help>`_
370
+ 7. `Commands <#commands>`_
371
+ - `Configuration <#configuration>`_
372
+ - `Server <#server>`_
373
+ - `Current List of Built-in Plugins <#current-list-of-built-in-plugins>`_
374
+ - `Pypi.org APRSD Installable Plugin Packages <#pypiorg-aprsd-installable-plugin-packages>`_
375
+ - `🐍 APRSD Installed 3rd Party Plugins <#aprsd-installed-3rd-party-plugins>`_
376
+ - `Send Message <#send-message>`_
377
+ - `Send Email (Radio to SMTP Server) <#send-email-radio-to-smtp-server>`_
378
+ - `Receive Email (IMAP Server to Radio) <#receive-email-imap-server-to-radio>`_
379
+ - `Location <#location>`_
380
+ - `Web Admin Interface <#web-admin-interface>`_
381
+ 8. `Development <#development>`_
382
+ - `Building Your Own APRSD Plugins <#building-your-own-aprsd-plugins>`_
383
+ 9. `Workflow <#workflow>`_
384
+ 10. `Release <#release>`_
385
+ 11. `Docker Container <#docker-container>`_
386
+ - `Building <#building-1>`_
387
+ - `Official Build <#official-build>`_
388
+ - `Development Build <#development-build>`_
389
+ - `Running the Container <#running-the-container>`_
390
+
391
+
361
392
  What is APRSD
362
393
  =============
363
394
  APRSD is a python application for interacting with the APRS network and providing
@@ -494,8 +525,7 @@ look for incomming commands to the callsign configured in the config file
494
525
 
495
526
 
496
527
  Current list of built-in plugins
497
- ======================================
498
-
528
+ --------------------------------
499
529
  ::
500
530
 
501
531
  └─> aprsd list-plugins
@@ -647,18 +677,21 @@ AND... ping, fortune, time.....
647
677
 
648
678
  Web Admin Interface
649
679
  ===================
680
+ APRSD has a web admin interface that allows you to view the status of the running APRSD server instance.
681
+ The web admin interface shows graphs of packet counts, packet types, number of threads running, the latest
682
+ packets sent and received, and the status of each of the plugins that are loaded. You can also view the logfile
683
+ and view the raw APRSD configuration file.
684
+
650
685
  To start the web admin interface, You have to install gunicorn in your virtualenv that already has aprsd installed.
651
686
 
652
687
  ::
653
688
 
654
689
  source <path to APRSD's virtualenv>/bin/activate
655
- pip install gunicorn
656
- gunicorn --bind 0.0.0.0:8080 "aprsd.wsgi:app"
690
+ aprsd admin --loglevel INFO
657
691
 
658
692
  The web admin interface will be running on port 8080 on the local machine. http://localhost:8080
659
693
 
660
694
 
661
-
662
695
  Development
663
696
  ===========
664
697
 
@@ -667,7 +700,7 @@ Development
667
700
  * ``make``
668
701
 
669
702
  Workflow
670
- ========
703
+ --------
671
704
 
672
705
  While working aprsd, The workflow is as follows:
673
706
 
@@ -696,7 +729,7 @@ While working aprsd, The workflow is as follows:
696
729
 
697
730
 
698
731
  Release
699
- =======
732
+ -------
700
733
 
701
734
  To do release to pypi:
702
735
 
@@ -717,6 +750,29 @@ To do release to pypi:
717
750
  ``make upload``
718
751
 
719
752
 
753
+ Building your own APRSD plugins
754
+ -------------------------------
755
+
756
+ APRSD plugins are the mechanism by which APRSD can respond to APRS Messages. The plugins are loaded at server startup
757
+ and can also be loaded at listen startup. When a packet is received by APRSD, it is passed to each of the plugins
758
+ in the order they were registered in the config file. The plugins can then decide what to do with the packet.
759
+ When a plugin is called, it is passed a APRSD Packet object. The plugin can then do something with the packet and
760
+ return a reply message if desired. If a plugin does not want to reply to the packet, it can just return None.
761
+ When a plugin does return a reply message, APRSD will send the reply message to the appropriate destination.
762
+
763
+ For example, when a 'ping' message is received, the PingPlugin will return a reply message of 'pong'. When APRSD
764
+ receives the 'pong' message, it will be sent back to the original caller of the ping message.
765
+
766
+ APRSD plugins are simply python packages that can be installed from pypi.org. They are installed into the
767
+ aprsd virtualenv and can be imported by APRSD at runtime. The plugins are registered in the config file and loaded
768
+ at startup of the aprsd server command or the aprsd listen command.
769
+
770
+ Overview
771
+ --------
772
+ You can build your own plugins by following the instructions in the `Building your own APRSD plugins`_ section.
773
+
774
+ Plugins are called by APRSD when packe
775
+
720
776
  Docker Container
721
777
  ================
722
778
 
@@ -11,6 +11,37 @@ ____________________
11
11
  `APRSD <http://github.com/craigerl/aprsd>`_ is a Ham radio `APRS <http://aprs.org>`_ message command gateway built on python.
12
12
 
13
13
 
14
+ Table of Contents
15
+ =================
16
+
17
+ 1. `What is APRSD <#what-is-aprsd>`_
18
+ 2. `APRSD Overview Diagram <#aprsd-overview-diagram>`_
19
+ 3. `Typical Use Case <#typical-use-case>`_
20
+ 4. `Installation <#installation>`_
21
+ 5. `Example Usage <#example-usage>`_
22
+ 6. `Help <#help>`_
23
+ 7. `Commands <#commands>`_
24
+ - `Configuration <#configuration>`_
25
+ - `Server <#server>`_
26
+ - `Current List of Built-in Plugins <#current-list-of-built-in-plugins>`_
27
+ - `Pypi.org APRSD Installable Plugin Packages <#pypiorg-aprsd-installable-plugin-packages>`_
28
+ - `🐍 APRSD Installed 3rd Party Plugins <#aprsd-installed-3rd-party-plugins>`_
29
+ - `Send Message <#send-message>`_
30
+ - `Send Email (Radio to SMTP Server) <#send-email-radio-to-smtp-server>`_
31
+ - `Receive Email (IMAP Server to Radio) <#receive-email-imap-server-to-radio>`_
32
+ - `Location <#location>`_
33
+ - `Web Admin Interface <#web-admin-interface>`_
34
+ 8. `Development <#development>`_
35
+ - `Building Your Own APRSD Plugins <#building-your-own-aprsd-plugins>`_
36
+ 9. `Workflow <#workflow>`_
37
+ 10. `Release <#release>`_
38
+ 11. `Docker Container <#docker-container>`_
39
+ - `Building <#building-1>`_
40
+ - `Official Build <#official-build>`_
41
+ - `Development Build <#development-build>`_
42
+ - `Running the Container <#running-the-container>`_
43
+
44
+
14
45
  What is APRSD
15
46
  =============
16
47
  APRSD is a python application for interacting with the APRS network and providing
@@ -147,8 +178,7 @@ look for incomming commands to the callsign configured in the config file
147
178
 
148
179
 
149
180
  Current list of built-in plugins
150
- ======================================
151
-
181
+ --------------------------------
152
182
  ::
153
183
 
154
184
  └─> aprsd list-plugins
@@ -300,18 +330,21 @@ AND... ping, fortune, time.....
300
330
 
301
331
  Web Admin Interface
302
332
  ===================
333
+ APRSD has a web admin interface that allows you to view the status of the running APRSD server instance.
334
+ The web admin interface shows graphs of packet counts, packet types, number of threads running, the latest
335
+ packets sent and received, and the status of each of the plugins that are loaded. You can also view the logfile
336
+ and view the raw APRSD configuration file.
337
+
303
338
  To start the web admin interface, You have to install gunicorn in your virtualenv that already has aprsd installed.
304
339
 
305
340
  ::
306
341
 
307
342
  source <path to APRSD's virtualenv>/bin/activate
308
- pip install gunicorn
309
- gunicorn --bind 0.0.0.0:8080 "aprsd.wsgi:app"
343
+ aprsd admin --loglevel INFO
310
344
 
311
345
  The web admin interface will be running on port 8080 on the local machine. http://localhost:8080
312
346
 
313
347
 
314
-
315
348
  Development
316
349
  ===========
317
350
 
@@ -320,7 +353,7 @@ Development
320
353
  * ``make``
321
354
 
322
355
  Workflow
323
- ========
356
+ --------
324
357
 
325
358
  While working aprsd, The workflow is as follows:
326
359
 
@@ -349,7 +382,7 @@ While working aprsd, The workflow is as follows:
349
382
 
350
383
 
351
384
  Release
352
- =======
385
+ -------
353
386
 
354
387
  To do release to pypi:
355
388
 
@@ -370,6 +403,29 @@ To do release to pypi:
370
403
  ``make upload``
371
404
 
372
405
 
406
+ Building your own APRSD plugins
407
+ -------------------------------
408
+
409
+ APRSD plugins are the mechanism by which APRSD can respond to APRS Messages. The plugins are loaded at server startup
410
+ and can also be loaded at listen startup. When a packet is received by APRSD, it is passed to each of the plugins
411
+ in the order they were registered in the config file. The plugins can then decide what to do with the packet.
412
+ When a plugin is called, it is passed a APRSD Packet object. The plugin can then do something with the packet and
413
+ return a reply message if desired. If a plugin does not want to reply to the packet, it can just return None.
414
+ When a plugin does return a reply message, APRSD will send the reply message to the appropriate destination.
415
+
416
+ For example, when a 'ping' message is received, the PingPlugin will return a reply message of 'pong'. When APRSD
417
+ receives the 'pong' message, it will be sent back to the original caller of the ping message.
418
+
419
+ APRSD plugins are simply python packages that can be installed from pypi.org. They are installed into the
420
+ aprsd virtualenv and can be imported by APRSD at runtime. The plugins are registered in the config file and loaded
421
+ at startup of the aprsd server command or the aprsd listen command.
422
+
423
+ Overview
424
+ --------
425
+ You can build your own plugins by following the instructions in the `Building your own APRSD plugins`_ section.
426
+
427
+ Plugins are called by APRSD when packe
428
+
373
429
  Docker Container
374
430
  ================
375
431
 
@@ -23,13 +23,24 @@ class APRSISClient(base.APRSClient):
23
23
  max_timeout = {"hours": 0.0, "minutes": 2, "seconds": 0}
24
24
  self.max_delta = datetime.timedelta(**max_timeout)
25
25
 
26
- def stats(self) -> dict:
26
+ def stats(self, serializable=False) -> dict:
27
27
  stats = {}
28
28
  if self.is_configured():
29
+ if self._client:
30
+ keepalive = self._client.aprsd_keepalive
31
+ server_string = self._client.server_string
32
+ if serializable:
33
+ keepalive = keepalive.isoformat()
34
+ else:
35
+ keepalive = "None"
36
+ server_string = "None"
29
37
  stats = {
30
- "server_string": self._client.server_string,
31
- "sever_keepalive": self._client.aprsd_keepalive,
38
+ "connected": self.is_connected,
32
39
  "filter": self.filter,
40
+ "login_status": self.login_status,
41
+ "connection_keepalive": keepalive,
42
+ "server_string": server_string,
43
+ "transport": self.transport(),
33
44
  }
34
45
 
35
46
  return stats
@@ -99,22 +110,31 @@ class APRSISClient(base.APRSClient):
99
110
  self.connected = False
100
111
  backoff = 1
101
112
  aprs_client = None
113
+ retries = 3
114
+ retry_count = 0
102
115
  while not self.connected:
116
+ retry_count += 1
117
+ if retry_count >= retries:
118
+ break
103
119
  try:
104
120
  LOG.info(f"Creating aprslib client({host}:{port}) and logging in {user}.")
105
121
  aprs_client = aprsis.Aprsdis(user, passwd=password, host=host, port=port)
106
122
  # Force the log to be the same
107
123
  aprs_client.logger = LOG
108
124
  aprs_client.connect()
109
- self.connected = True
125
+ self.connected = self.login_status["success"] = True
126
+ self.login_status["message"] = aprs_client.server_string
110
127
  backoff = 1
111
128
  except LoginError as e:
112
129
  LOG.error(f"Failed to login to APRS-IS Server '{e}'")
113
- self.connected = False
130
+ self.connected = self.login_status["success"] = False
131
+ self.login_status["message"] = e.message
132
+ LOG.error(e.message)
114
133
  time.sleep(backoff)
115
134
  except Exception as e:
116
135
  LOG.error(f"Unable to connect to APRS-IS server. '{e}' ")
117
- self.connected = False
136
+ self.connected = self.login_status["success"] = False
137
+ self.login_status["message"] = e.message
118
138
  time.sleep(backoff)
119
139
  # Don't allow the backoff to go to inifinity.
120
140
  if backoff > 5:
@@ -126,7 +146,16 @@ class APRSISClient(base.APRSClient):
126
146
  return aprs_client
127
147
 
128
148
  def consumer(self, callback, blocking=False, immortal=False, raw=False):
129
- self._client.consumer(
130
- callback, blocking=blocking,
131
- immortal=immortal, raw=raw,
132
- )
149
+ if self._client:
150
+ try:
151
+ self._client.consumer(
152
+ callback, blocking=blocking,
153
+ immortal=immortal, raw=raw,
154
+ )
155
+ except Exception as e:
156
+ LOG.error(e)
157
+ LOG.info(e.__cause__)
158
+ raise e
159
+ else:
160
+ LOG.warning("client is None, might be resetting.")
161
+ self.connected = False
@@ -19,6 +19,10 @@ class APRSClient:
19
19
  _client = None
20
20
 
21
21
  connected = False
22
+ login_status = {
23
+ "success": False,
24
+ "message": None,
25
+ }
22
26
  filter = None
23
27
  lock = threading.Lock()
24
28
 
@@ -32,7 +36,23 @@ class APRSClient:
32
36
 
33
37
  @abc.abstractmethod
34
38
  def stats(self) -> dict:
35
- pass
39
+ """Return statistics about the client connection.
40
+
41
+ Returns:
42
+ dict: Statistics about the connection and packet handling
43
+ """
44
+
45
+ @property
46
+ def is_connected(self):
47
+ return self.connected
48
+
49
+ @property
50
+ def login_success(self):
51
+ return self.login_status.get("success", False)
52
+
53
+ @property
54
+ def login_failure(self):
55
+ return self.login_status["message"]
36
56
 
37
57
  def set_filter(self, filter):
38
58
  self.filter = filter
@@ -46,22 +66,31 @@ class APRSClient:
46
66
  return self._client
47
67
 
48
68
  def _create_client(self):
49
- self._client = self.setup_connection()
50
- if self.filter:
51
- LOG.info("Creating APRS client filter")
52
- self._client.set_filter(self.filter)
69
+ try:
70
+ self._client = self.setup_connection()
71
+ if self.filter:
72
+ LOG.info("Creating APRS client filter")
73
+ self._client.set_filter(self.filter)
74
+ except Exception as e:
75
+ LOG.error(f"Failed to create APRS client: {e}")
76
+ self._client = None
77
+ raise
53
78
 
54
79
  def stop(self):
55
80
  if self._client:
56
81
  LOG.info("Stopping client connection.")
57
82
  self._client.stop()
58
83
 
59
- def send(self, packet: core.Packet):
60
- """Send a packet to the network."""
84
+ def send(self, packet: core.Packet) -> None:
85
+ """Send a packet to the network.
86
+
87
+ Args:
88
+ packet: The APRS packet to send
89
+ """
61
90
  self.client.send(packet)
62
91
 
63
92
  @wrapt.synchronized(lock)
64
- def reset(self):
93
+ def reset(self) -> None:
65
94
  """Call this to force a rebuild/reconnect."""
66
95
  LOG.info("Resetting client connection.")
67
96
  if self._client:
@@ -76,7 +105,11 @@ class APRSClient:
76
105
 
77
106
  @abc.abstractmethod
78
107
  def setup_connection(self):
79
- pass
108
+ """Initialize and return the underlying APRS connection.
109
+
110
+ Returns:
111
+ object: The initialized connection object
112
+ """
80
113
 
81
114
  @staticmethod
82
115
  @abc.abstractmethod
@@ -90,7 +123,11 @@ class APRSClient:
90
123
 
91
124
  @abc.abstractmethod
92
125
  def decode_packet(self, *args, **kwargs):
93
- pass
126
+ """Decode raw APRS packet data into a Packet object.
127
+
128
+ Returns:
129
+ Packet: Decoded APRS packet
130
+ """
94
131
 
95
132
  @abc.abstractmethod
96
133
  def consumer(self, callback, blocking=False, immortal=False, raw=False):