From 0d6ecce4155833d7ce8ff714e4132f1bf6cf160c Mon Sep 17 00:00:00 2001 From: Walter Oggioni Date: Wed, 15 Jul 2026 14:10:48 +0000 Subject: [PATCH] Restored simple RSGI support on KayaApp instances --- example/hello.py | 1 - packages/kaya-core/src/kaya/core/_app.py | 21 +++++++++++++++++- packages/kaya-rsgi/README.md | 2 +- packages/kaya-rsgi/src/kaya/rsgi/__init__.py | 3 +-- packages/kaya-rsgi/src/kaya/rsgi/_rsgi.py | 23 -------------------- 5 files changed, 22 insertions(+), 28 deletions(-) diff --git a/example/hello.py b/example/hello.py index 5ceb9ee..86308e9 100644 --- a/example/hello.py +++ b/example/hello.py @@ -3,7 +3,6 @@ from typing import List app = KayaApp() - @app.GET('/hello') @app.GET('/hello2') async def handle_request(ctx: HttpContext) -> None: diff --git a/packages/kaya-core/src/kaya/core/_app.py b/packages/kaya-core/src/kaya/core/_app.py index 3292241..0602671 100644 --- a/packages/kaya-core/src/kaya/core/_app.py +++ b/packages/kaya-core/src/kaya/core/_app.py @@ -2,7 +2,7 @@ from abc import ABC, abstractmethod from asyncio import Queue, AbstractEventLoop from asyncio import get_running_loop from logging import getLogger -from typing import Callable, Awaitable, Any, Mapping, Sequence, Optional, Unpack, Tuple, cast +from typing import Callable, Awaitable, Any, Mapping, Sequence, Optional, Tuple, cast from pwo import Maybe, AsyncQueueIterator from ._http_context import HttpContext from ._http_method import HttpMethod @@ -12,6 +12,7 @@ from ._websocket import WebSocket from ._asgi import AsgiContext, AsgiWebSocket from ._tree import Tree from ._types.asgi import LifespanScope, HTTPScope as ASGIHTTPScope, WebSocketScope as ASGIWebSocketScope +from typing_extensions import Unpack log = getLogger(__name__) @@ -69,6 +70,22 @@ class AbstractKayaApp(ABC): async def handle_websocket(self, ws: WebSocket) -> None: raise NotImplementedError() + def __rsgi_init__(self, loop: AbstractEventLoop) -> None: + self.setup(loop) + + def __rsgi_del__(self, loop: AbstractEventLoop) -> None: + self.shutdown(loop) + + async def __rsgi__(self, scope: Any, protocol: Any) -> None: + try: + from kaya.rsgi import RsgiContext, RsgiWebSocket + except ImportError as exc: + raise RuntimeError("RSGI support requires kaya-rsgi to be installed") from exc + if scope.proto == 'ws': + await self.handle_websocket(RsgiWebSocket(scope, protocol)) + else: + await self.handle_request(RsgiContext(scope, protocol)) + class KayaApp(AbstractKayaApp): _tree: Tree @@ -145,3 +162,5 @@ class KayaApp(AbstractKayaApp): def PATCH(self, path: str, recursive: bool = False) -> Callable[[HttpHandler], HttpHandler]: return self.route(path, (HttpMethod.PATCH,), recursive) + + diff --git a/packages/kaya-rsgi/README.md b/packages/kaya-rsgi/README.md index f9f34f2..b66dc9a 100644 --- a/packages/kaya-rsgi/README.md +++ b/packages/kaya-rsgi/README.md @@ -2,4 +2,4 @@ RSGI/Granian integration for the Kaya web framework. -Provides `RsgiContext`, `RsgiWebSocket`, and `RsgiApplication` to run Kaya apps on Granian's RSGI protocol. +Provides `RsgiContext`, `RsgiWebSocket` to run Kaya apps on Granian's RSGI protocol. diff --git a/packages/kaya-rsgi/src/kaya/rsgi/__init__.py b/packages/kaya-rsgi/src/kaya/rsgi/__init__.py index 0b230f2..8d5217e 100644 --- a/packages/kaya-rsgi/src/kaya/rsgi/__init__.py +++ b/packages/kaya-rsgi/src/kaya/rsgi/__init__.py @@ -1,9 +1,8 @@ -from ._rsgi import RsgiApplication, RsgiContext, RsgiWebSocket +from ._rsgi import RsgiContext, RsgiWebSocket from ._types import HTTPScope, WebSocketScope __all__ = [ - 'RsgiApplication', 'RsgiContext', 'RsgiWebSocket', 'HTTPScope', diff --git a/packages/kaya-rsgi/src/kaya/rsgi/_rsgi.py b/packages/kaya-rsgi/src/kaya/rsgi/_rsgi.py index 3222b17..2595fdd 100644 --- a/packages/kaya-rsgi/src/kaya/rsgi/_rsgi.py +++ b/packages/kaya-rsgi/src/kaya/rsgi/_rsgi.py @@ -175,26 +175,3 @@ class RsgiWebSocket(WebSocket): if message.kind == 'close': raise StopAsyncIteration return message - - -class RsgiApplication: - _app: AbstractKayaApp - - def __init__(self, app: AbstractKayaApp) -> None: - self._app = app - - def __rsgi_init__(self, loop: Any) -> None: - self._app.setup(loop) - - def __rsgi_del__(self, loop: Any) -> None: - self._app.shutdown(loop) - - async def __rsgi__(self, - scope: RSGIHTTPScope | RSGIWebsocketScope, - protocol: RSGIHTTPProtocol | RSGIWebsocketProtocol) -> None: - if scope.proto == 'ws': - ws = RsgiWebSocket(scope, protocol) # type: ignore[arg-type] - await self._app.handle_websocket(ws) - else: - ctx = RsgiContext(scope, protocol) # type: ignore[arg-type] - await self._app.handle_request(ctx)