From 908b9fe10f0b8a929765a2f6008c9944ba13446e Mon Sep 17 00:00:00 2001 From: Jacob Coffee Date: Sun, 25 Jan 2026 12:16:40 -0600 Subject: [PATCH 1/3] noninvasive cabotge support --- Dockerfile | 8 ++++++++ bedevere/__main__.py | 26 +++++++++++++++++++++++--- 2 files changed, 31 insertions(+), 3 deletions(-) create mode 100644 Dockerfile diff --git a/Dockerfile b/Dockerfile new file mode 100644 index 00000000..5e8bc033 --- /dev/null +++ b/Dockerfile @@ -0,0 +1,8 @@ +FROM python:3.11-slim + +WORKDIR /app +COPY requirements.txt . +RUN pip install --no-cache-dir -r requirements.txt +COPY bedevere bedevere + +CMD ["python", "-m", "bedevere"] diff --git a/bedevere/__main__.py b/bedevere/__main__.py index 4bb678e8..04baff40 100644 --- a/bedevere/__main__.py +++ b/bedevere/__main__.py @@ -68,10 +68,30 @@ async def repo_installation_added(event, gh, *args, **kwargs): ) +async def health_check(request): + """Health check endpoint for container orchestration.""" + return web.Response(status=200, text="OK") + + if __name__ == "__main__": # pragma: no cover app = web.Application() app.router.add_post("/", main) + app.router.add_get("/health", health_check) + + socket_path = os.environ.get("SOCKET_PATH") port = os.environ.get("PORT") - if port is not None: - port = int(port) - web.run_app(app, port=port) + + if socket_path: + + async def run_with_socket(): + runner = web.AppRunner(app) + await runner.setup() + site = web.UnixSite(runner, path=socket_path) + await site.start() + await asyncio.Event().wait() + + asyncio.run(run_with_socket()) + else: + if port is not None: + port = int(port) + web.run_app(app, port=port) From 8267c58a391f5a748013567dc4cf4a90aa73eeab Mon Sep 17 00:00:00 2001 From: Jacob Coffee Date: Sun, 25 Jan 2026 12:18:51 -0600 Subject: [PATCH 2/3] simpler --- bedevere/__main__.py | 20 ++++---------------- 1 file changed, 4 insertions(+), 16 deletions(-) diff --git a/bedevere/__main__.py b/bedevere/__main__.py index 04baff40..aef92940 100644 --- a/bedevere/__main__.py +++ b/bedevere/__main__.py @@ -78,20 +78,8 @@ async def health_check(request): app.router.add_post("/", main) app.router.add_get("/health", health_check) - socket_path = os.environ.get("SOCKET_PATH") - port = os.environ.get("PORT") - - if socket_path: - - async def run_with_socket(): - runner = web.AppRunner(app) - await runner.setup() - site = web.UnixSite(runner, path=socket_path) - await site.start() - await asyncio.Event().wait() - - asyncio.run(run_with_socket()) + if os.path.isdir("/var/run/cabotage"): + web.run_app(app, path="/var/run/cabotage/cabotage.sock") else: - if port is not None: - port = int(port) - web.run_app(app, port=port) + port = os.environ.get("PORT") + web.run_app(app, port=int(port) if port else None) From 28b2a47827b4354d13e6cf7b265c3e0aa6fcf95c Mon Sep 17 00:00:00 2001 From: Jacob Coffee Date: Sun, 25 Jan 2026 12:24:03 -0600 Subject: [PATCH 3/3] Add test for health_check endpoint Co-Authored-By: Claude Opus 4.5 --- tests/test___main__.py | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/tests/test___main__.py b/tests/test___main__.py index 397d1339..e9e628fa 100644 --- a/tests/test___main__.py +++ b/tests/test___main__.py @@ -13,6 +13,15 @@ } +async def test_health_check(aiohttp_client): + app = web.Application() + app.router.add_get("/health", main.health_check) + client = await aiohttp_client(app) + response = await client.get("/health") + assert response.status == 200 + assert await response.text() == "OK" + + async def test_ping(aiohttp_client): app = web.Application() app.router.add_post("/", main.main)