Migrated to Loguru for logging and set up basic configuration, but it still needs adjustments. (0.21)

This commit is contained in:
Johannes Findeisen 2023-02-23 19:06:53 +01:00
commit 5843f4358f
4 changed files with 58 additions and 43 deletions

View file

@ -36,5 +36,8 @@ help:
run: run:
PYTHONPATH=$(shell pwd):$(shell pwd)/venv/lib/python$(PYTHON_VERSION)/site-packages/ bin/linspector -s ./etc PYTHONPATH=$(shell pwd):$(shell pwd)/venv/lib/python$(PYTHON_VERSION)/site-packages/ bin/linspector -s ./etc
rundev:
PYTHONPATH=$(shell pwd):$(shell pwd)/venv/lib/python$(PYTHON_VERSION)/site-packages/ bin/linspector -s ./etc.local
daemon: daemon:
PYTHONPATH=$(shell pwd):$(shell pwd)/venv/lib/python$(PYTHON_VRESION)/site-packages/ bin/linspector -d ./etc PYTHONPATH=$(shell pwd):$(shell pwd)/venv/lib/python$(PYTHON_VRESION)/site-packages/ bin/linspector -d ./etc

View file

@ -42,29 +42,29 @@ development environment.
### To do ### To do
- **Everything!** But the progress is fast and after some few days I am not far - **Everything!** But the progress is fast and after some few days I am not far
away to get a first working codebase. If the core is running I believe adding features away to get a first working codebase. If the core is running I believe adding features
will happen from day to day... ;) will happen from day to day... ;)
See TODO for internal tasks. See TODO for internal tasks.
### Ideas ### Ideas
- **Thousands!** For now the goal is to implement most features from the old version - **Thousands!** For now the goal is to implement most features from the old version
of Linspector. :) of Linspector. :)
### Manifest ### Manifest
- All of this project **must be MIT licensed**. When using 3rd party libraries make - All of this project **must be MIT licensed**. When using 3rd party libraries make
sure the license is compatible. sure the license is compatible.
- The core of Linspector should not use 3rd party libraries if possible. Only notifications, - The core of Linspector should not use 3rd party libraries if possible. Only notifications,
- plugins, services and tasks may use other libraries. But copying code into the - plugins, services and tasks may use other libraries. But copying code into the
source tree is ok when respecting the license. Not using 3rd party libraries source tree is ok when respecting the license. Not using 3rd party libraries
should always be preferred though. should always be preferred though.
- Inline comments should be all lowercase. Descriptions and documentation comments - Inline comments should be all lowercase. Descriptions and documentation comments
must be natural language. must be natural language.
- Arguments to functions must always be in alphabetical order. - Arguments to functions must always be in alphabetical order.
- Class member variables must always be in alphabetical order in __init__() or any - Class member variables must always be in alphabetical order in __init__() or any
function / method. function / method.
- Functions must always be in alphabetical order in classe. - Functions must always be in alphabetical order in classe.
- Every commit must run without errors even if not being a working version of Linspector. - Every commit must run without errors even if not being a working version of Linspector.
@ -72,13 +72,13 @@ See TODO for internal tasks.
Currently, the Linspector core requires the following 3rd party libraries: Currently, the Linspector core requires the following 3rd party libraries:
- [APScheduler](https://github.com/agronholm/apscheduler)- Apscheduler is the scheduler used in - [APScheduler](https://pypi.org/project/APScheduler/)- Apscheduler is the scheduler used in
Linspector for the execution of monitors. I started Linspector for the execution of monitors. I started
to use this library in very early versions of Linspector in 2011. Since the main task to use this library in very early versions of Linspector in 2011. Since the main task
in Linspector is the execution of jobs in regularly intervals I believe it is the right in Linspector is the execution of jobs in regularly intervals I believe it is the right
decision to make use of APScheduler directly in the core of the Linspector project. decision to make use of APScheduler directly in the core of the Linspector project.
- [Loguru](https://github.com/Delgan/loguru) - Linspector uses Loguru for file based logging. Loguru is a library - [Loguru](https://pypi.org/project/loguru/) - Linspector uses Loguru for file based logging. Loguru is a library
which aims to bring enjoyable logging in Python. which aims to bring enjoyable logging in Python.
### Other used libraries ### Other used libraries
@ -87,20 +87,20 @@ monitors, notifications, services or plugins sometimes need to make the use of
them may only affect parts of Linspector. Currently used libraries are: them may only affect parts of Linspector. Currently used libraries are:
- [CherryPy](https://cherrypy.dev/) - CherryPy is a pythonic, object-oriented HTTP framework. - [CherryPy](https://cherrypy.dev/) - CherryPy is a pythonic, object-oriented HTTP framework.
Used by the HTTPServer plugin. Used by the HTTPServer plugin.
- [fritzconnection](https://github.com/kbr/fritzconnection) - A Python-Tool to communicate with - [fritzconnection](https://github.com/kbr/fritzconnection) - A Python-Tool to communicate with
the AVM Fritz!Box. Uses the TR-064 protocol over UPnP. Used by the FritzboxPhoneStatus and the AVM Fritz!Box. Uses the TR-064 protocol over UPnP. Used by the FritzboxPhoneStatus and
FritzBoxUplink service. FritzBoxUplink service.
- [Paramiko](https://www.paramiko.org/) - Paramiko is a pure-Python (2.7, 3.4+) implementation - [Paramiko](https://www.paramiko.org/) - Paramiko is a pure-Python (2.7, 3.4+) implementation
of the SSHv2 protocol, providing both client and server functionality. Used by the SSH service. of the SSHv2 protocol, providing both client and server functionality. Used by the SSH service.
- [python-gammu](https://wammu.eu/python-gammu/) - Python bindings for the Gammu library. Used by the - [python-gammu](https://wammu.eu/python-gammu/) - Python bindings for the Gammu library. Used by the
SMS notification. SMS notification.
- [PySNMP](https://pysnmp.readthedocs.io/en/latest/) - PySNMP is a cross-platform, pure-Python - [PySNMP](https://pysnmp.readthedocs.io/en/latest/) - PySNMP is a cross-platform, pure-Python
SNMP engine implementation. It features fully-functional SNMP engine capable to act in SNMP engine implementation. It features fully-functional SNMP engine capable to act in
Agent/Manager/Proxy roles, talking SNMP v1/v2c/v3 protocol versions over IPv4/IPv6 and other Agent/Manager/Proxy roles, talking SNMP v1/v2c/v3 protocol versions over IPv4/IPv6 and other
network transports. Used by the SNMP services (get). network transports. Used by the SNMP services (get).
- [requests](https://requests.readthedocs.io/en/latest/) - Requests is an elegant and simple - [requests](https://requests.readthedocs.io/en/latest/) - Requests is an elegant and simple
HTTP library for Python, built for human beings. Used by the Speedtest service. HTTP library for Python, built for human beings. Used by the Speedtest service.
- [xmpp2](https://pypi.org/project/xmpp2/) - A XMPP client for Python. Used by the XMPP notification. - [xmpp2](https://pypi.org/project/xmpp2/) - A XMPP client for Python. Used by the XMPP notification.
These libraries are not being delivered with the Linspector source code and maybe have These libraries are not being delivered with the Linspector source code and maybe have
@ -131,8 +131,7 @@ scheme (See: [https://semver.org/](https://semver.org/)):
- 15.10 - Date based release - 15.10 - Date based release
- 23 - Serial release - 23 - Serial release
(More (More information: [https://packaging.python.org/en/latest/guides/distributing-packages-using-setuptools/#choosing-a-versioning-scheme](https://packaging.python.org/en/latest/guides/distributing-packages-using-setuptools/#choosing-a-versioning-scheme) &
information: [https://packaging.python.org/en/latest/guides/distributing-packages-using-setuptools/#choosing-a-versioning-scheme](https://packaging.python.org/en/latest/guides/distributing-packages-using-setuptools/#choosing-a-versioning-scheme) &
[https://peps.python.org/pep-0440/#public-version-identifiers](https://peps.python.org/pep-0440/#public-version-identifiers)) [https://peps.python.org/pep-0440/#public-version-identifiers](https://peps.python.org/pep-0440/#public-version-identifiers))
### Configuration file rules ### Configuration file rules

View file

@ -14,10 +14,10 @@ import sys
from linspector.configuration import Configuration from linspector.configuration import Configuration
from linspector.environment import Environment from linspector.environment import Environment
from linspector.linspector import Linspector from linspector.linspector import Linspector
from linspector.logger import Log
from linspector.monitors import Monitors from linspector.monitors import Monitors
from loguru import logger
__version__ = '0.20.5' __version__ = '0.21'
__author__ = 'Johannes Findeisen <you@hanez.org>' __author__ = 'Johannes Findeisen <you@hanez.org>'
@ -62,49 +62,61 @@ def main():
tasks = {} tasks = {}
try: try:
configuration = Configuration(args.configuration_path) configuration = Configuration(args.configuration_path, logger)
except Exception as err: except Exception as err:
print('[linspector] configuration error: {0}'.format(err)) logger.error('configuration error: {0}'.format(err))
sys.exit(1) sys.exit(1)
log = Log(configuration, args.stdout, args.verbose) logger.remove()
environment = Environment(log) log_level = "ERROR"
if configuration.get_option('linspector', 'log_level'):
log_level = configuration.get_option('linspector', 'log_level')
logger.add(sys.stderr, backtrace=True, colorize=True, diagnose=True, level=log_level)
# log.add(sys.stderr, backtrace=True, colorize=True, diagnose=True, format="{time} [{level}]: {message}", level="INFO")
# log.add(sys.stderr, format="{time} {level} {message}", filter="my_module", level="INFO")
if configuration.get_option('linspector', 'logfile'):
logger.add(configuration.get_option('linspector', 'logfile'), backtrace=True, diagnose=True, enqueue=True,
level=configuration.get_option('linspector', 'logfile_level'))
environment = Environment(logger)
try: try:
monitors = Monitors(configuration, environment, log, notifications, services, tasks) monitors = Monitors(configuration, environment, logger, notifications, services, tasks)
except Exception as err: except Exception as err:
log.warning('[linspector] monitor initialization error: {0}'.format(err)) logger.warning('monitor initialization error: {0}'.format(err))
try: try:
linspector = Linspector(configuration, environment, log, monitors, plugins, scheduler) linspector = Linspector(configuration, environment, logger, monitors, plugins, scheduler)
# linspector.print_debug() # linspector.print_debug()
except Exception as err: except Exception as err:
log.critical('[linspector] core initialization error: {0}'.format(err)) logger.critical('core initialization error: {0}'.format(err))
logger.critical('program terminating...')
sys.exit(1) sys.exit(1)
# daemon initialization # daemon initialization
if args.daemon: if args.daemon:
try: try:
from linspector.linspectord import Linspectord from linspector.linspectord import Linspectord
linspectord = Linspectord(configuration, environment, linspector, log) linspectord = Linspectord(configuration, environment, linspector, logger)
# do handling of restart, start and stop commands but for now "start" is enough... ;) # do handling of restart, start and stop commands but for now "start" is enough... ;)
if args.kill: if args.kill:
log.info('[linspector] stopping daemon.') logger.info('stopping daemon.')
linspectord.stop() linspectord.stop()
elif args.restart: elif args.restart:
log.info('[linspector] restarting daemon.') logger.info('restarting daemon.')
linspectord.restart() linspectord.restart()
else: else:
log.info('[linspector] starting daemon.') logger.info('starting daemon.')
linspectord.start() linspectord.start()
except Exception as err: except Exception as err:
log.critical('[linspector] daemon error: {0}'.format(err)) logger.critical('daemon error: {0}'.format(err))
sys.exit(1) sys.exit(1)
else: else:
try: try:
signal.pause() signal.pause()
except KeyboardInterrupt: except KeyboardInterrupt:
log.info('[linspector] program terminated by user!') logger.info('program terminated by user!')
if __name__ == '__main__': if __name__ == '__main__':

View file

@ -11,9 +11,10 @@ import os
# TODO: check for all required configuration options and set defaults if needed. do this only for # TODO: check for all required configuration options and set defaults if needed. do this only for
# options in the "linspector" section of linspector.ini. # options in the "linspector" section of linspector.ini.
class Configuration: class Configuration:
def __init__(self, configuration_path): def __init__(self, configuration_path, log):
self.__configuration = configparser.ConfigParser() self.__configuration = configparser.ConfigParser()
self.__configuration_path = configuration_path self.__configuration_path = configuration_path
self.__log = log
# print('[linspector] reading configuration file: ' + configuration_path + # print('[linspector] reading configuration file: ' + configuration_path +
# '/linspector.conf') # '/linspector.conf')