remove aiohttp by quart

This commit is contained in:
Stefan Allius
2025-04-15 18:15:59 +02:00
parent 5452b8efc2
commit 8bf8c2e85d
3 changed files with 32 additions and 65 deletions

View File

@@ -1,4 +1,4 @@
aiomqtt==2.3.2 aiomqtt==2.3.2
schema==0.7.7 schema==0.7.7
aiocron==2.1 aiocron==2.1
aiohttp==3.11.16 quart==0.20

View File

@@ -96,8 +96,8 @@ class Proxy():
Infos.new_stat_data[key] = False Infos.new_stat_data[key] = False
@classmethod @classmethod
def class_close(cls, loop) -> None: # pragma: no cover async def class_close(cls, loop) -> None: # pragma: no cover
logging.debug('Proxy.class_close') logging.debug('Proxy.class_close')
logging.info('Close MQTT Task') logging.info('Close MQTT Task')
loop.run_until_complete(cls.mqtt.close()) await cls.mqtt.close()
cls.mqtt = None cls.mqtt = None

View File

@@ -1,11 +1,10 @@
import logging import logging
import asyncio import asyncio
import logging.handlers import logging.handlers
import signal
import os import os
import argparse import argparse
from asyncio import StreamReader, StreamWriter from asyncio import StreamReader, StreamWriter
from aiohttp import web from quart import Quart, Response
from logging import config # noqa F401 from logging import config # noqa F401
from proxy import Proxy from proxy import Proxy
from inverter_ifc import InverterIfc from inverter_ifc import InverterIfc
@@ -18,28 +17,29 @@ from cnf.config_read_toml import ConfigReadToml
from cnf.config_read_json import ConfigReadJson from cnf.config_read_json import ConfigReadJson
from modbus_tcp import ModbusTcp from modbus_tcp import ModbusTcp
routes = web.RouteTableDef()
proxy_is_up = False proxy_is_up = False
app = Quart(__name__)
@routes.get('/')
async def hello(request):
return web.Response(text="Hello, world")
@routes.get('/-/ready') @app.route('/')
async def ready(request): async def hello():
return Response(response="Hello, world")
@app.route('/-/ready')
async def ready():
if proxy_is_up: if proxy_is_up:
status = 200 status = 200
text = 'Is ready' text = 'Is ready'
else: else:
status = 503 status = 503
text = 'Not ready' text = 'Not ready'
return web.Response(status=status, text=text) return Response(status=status, response=text)
@routes.get('/-/healthy') @app.route('/-/healthy')
async def healthy(request): async def healthy():
if proxy_is_up: if proxy_is_up:
# logging.info('web reqeust healthy()') # logging.info('web reqeust healthy()')
@@ -47,32 +47,11 @@ async def healthy(request):
try: try:
res = inverter.healthy() res = inverter.healthy()
if not res: if not res:
return web.Response(status=503, text="I have a problem") return Response(status=503, response="I have a problem")
except Exception as err: except Exception as err:
logging.info(f'Exception:{err}') logging.info(f'Exception:{err}')
return web.Response(status=200, text="I'm fine") return Response(status=200, response="I'm fine")
async def webserver(addr, port):
'''coro running our webserver'''
app = web.Application()
app.add_routes(routes)
runner = web.AppRunner(app)
await runner.setup()
site = web.TCPSite(runner, addr, port)
await site.start()
logging.info(f'HTTP server listen on port: {port}')
try:
# Normal interaction with aiohttp
while True:
await asyncio.sleep(3600) # sleep forever
except asyncio.CancelledError:
logging.info('HTTP server cancelled')
await runner.cleanup()
logging.debug('HTTP cleanup done')
async def handle_client(reader: StreamReader, writer: StreamWriter, inv_class): async def handle_client(reader: StreamReader, writer: StreamWriter, inv_class):
@@ -82,10 +61,12 @@ async def handle_client(reader: StreamReader, writer: StreamWriter, inv_class):
await inv.local.ifc.server_loop() await inv.local.ifc.server_loop()
async def handle_shutdown(loop, web_task): @app.after_serving
async def handle_shutdown():
'''Close all TCP connections and stop the event loop''' '''Close all TCP connections and stop the event loop'''
logging.info('Shutdown due to SIGTERM') logging.info('Shutdown due to SIGTERM')
loop = asyncio.get_event_loop()
global proxy_is_up global proxy_is_up
proxy_is_up = False proxy_is_up = False
@@ -97,24 +78,16 @@ async def handle_shutdown(loop, web_task):
logging.info('Proxy disconnecting done') logging.info('Proxy disconnecting done')
#
# second, cancel the web server
#
web_task.cancel()
await web_task
# #
# now cancel all remaining (pending) tasks # now cancel all remaining (pending) tasks
# #
pending = asyncio.all_tasks() for task in asyncio.all_tasks():
for task in pending: if task == asyncio.current_task():
continue
task.cancel() task.cancel()
logging.info('Proxy cancelling done')
# await Proxy.class_close(loop)
# at last, start a coro for stopping the loop
#
logging.debug("Stop event loop")
loop.stop()
def get_log_level() -> int | None: def get_log_level() -> int | None:
@@ -214,27 +187,21 @@ def main(): # pragma: no cover
loop.create_task(asyncio.start_server(lambda r, w, i=inv_class: loop.create_task(asyncio.start_server(lambda r, w, i=inv_class:
handle_client(r, w, i), handle_client(r, w, i),
'0.0.0.0', port)) '0.0.0.0', port))
web_task = loop.create_task(webserver('0.0.0.0', 8127))
#
# Register some UNIX Signal handler for a gracefully server shutdown
# on Docker restart and stop
#
for signame in ('SIGINT', 'SIGTERM'):
loop.add_signal_handler(getattr(signal, signame),
lambda loop=loop: asyncio.create_task(
handle_shutdown(loop, web_task)))
loop.set_debug(log_level == logging.DEBUG) loop.set_debug(log_level == logging.DEBUG)
try: try:
global proxy_is_up global proxy_is_up
proxy_is_up = True proxy_is_up = True
loop.run_forever() logging.info("Start Quart")
app.run(host='0.0.0.0', port=8127, use_reloader=False, loop=loop)
logging.info("Quart stopped")
except KeyboardInterrupt: except KeyboardInterrupt:
pass pass
except asyncio.exceptions.CancelledError:
logging.info("Quart cancelled")
finally: finally:
logging.info("Event loop is stopped")
Proxy.class_close(loop)
logging.debug('Close event loop') logging.debug('Close event loop')
loop.close() loop.close()
logging.info(f'Finally, exit Server "{serv_name}"') logging.info(f'Finally, exit Server "{serv_name}"')