Skip to content

Commit 0092250

Browse files
authored
Enable structured logging for FastStream broker logs (#131)
* Add FastStream example with Redis integration * Add force flag to docker cleanup and configure structlog for FastStream broker * Add TestApp context manager and debug output to foreign logs test * Refactor logging configuration for FastStream application and brokers * Remove unused imports and simplify app creation in faststream example * Remove unused TestApp import and simplify test setup * Add typing imports and finalize application variable
1 parent 3264255 commit 0092250

File tree

3 files changed

+66
-1
lines changed

3 files changed

+66
-1
lines changed

Justfile

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,3 +22,9 @@ publish:
2222
uv version $GITHUB_REF_NAME
2323
uv build
2424
uv publish --token $PYPI_TOKEN
25+
26+
run-faststream-example *args:
27+
#!/bin/bash
28+
trap 'echo; docker rm -f microbootstrap-redis' EXIT
29+
docker run --name microbootstrap-redis -p 6379:6379 -d redis
30+
uv run examples/faststream_app.py

examples/faststream_app.py

Lines changed: 49 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,49 @@
1+
from __future__ import annotations
2+
import typing
3+
from typing import TYPE_CHECKING
4+
5+
from faststream.redis import RedisBroker
6+
7+
from microbootstrap.bootstrappers.faststream import FastStreamBootstrapper
8+
from microbootstrap.config.faststream import FastStreamConfig
9+
from microbootstrap.granian_server import create_granian_server
10+
from microbootstrap.settings import FastStreamSettings
11+
12+
13+
if TYPE_CHECKING:
14+
from faststream.asgi import AsgiFastStream
15+
16+
17+
class Settings(FastStreamSettings): ...
18+
19+
20+
settings: typing.Final = Settings()
21+
22+
23+
def create_app() -> AsgiFastStream:
24+
broker = RedisBroker()
25+
26+
@broker.subscriber("first")
27+
@broker.publisher("second")
28+
def _(message: str) -> str:
29+
print(message) # noqa: T201
30+
return "Hi from first handler!"
31+
32+
@broker.subscriber("second")
33+
def _(message: str) -> None:
34+
print(message) # noqa: T201
35+
36+
application: typing.Final = (
37+
FastStreamBootstrapper(settings).configure_application(FastStreamConfig(broker=broker)).bootstrap()
38+
)
39+
40+
@application.after_startup
41+
async def send_first_message() -> None:
42+
await broker.connect()
43+
await broker.publish("Hi from startup!", "first")
44+
45+
return application
46+
47+
48+
if __name__ == "__main__":
49+
create_granian_server("examples.faststream_app:create_app", settings, factory=True).serve()

microbootstrap/bootstrappers/faststream.py

Lines changed: 11 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55
import prometheus_client
66
import structlog
77
import typing_extensions
8+
from faststream._internal.logger.logger_proxy import RealLoggerObject
89
from faststream.asgi import AsgiFastStream, AsgiResponse
910
from faststream.asgi import get as handle_get
1011
from faststream.specification import AsyncAPI
@@ -71,10 +72,19 @@ def get_config_type(cls) -> type[FastStreamOpentelemetryConfig]:
7172
return FastStreamOpentelemetryConfig
7273

7374

75+
faststream_app_logger: typing.Final = structlog.get_logger("microbootstrap.faststream.app")
76+
faststream_broker_logger: typing.Final = structlog.get_logger("microbootstrap.faststream.broker")
77+
78+
7479
@FastStreamBootstrapper.use_instrument()
7580
class FastStreamLoggingInstrument(LoggingInstrument):
7681
def bootstrap_before(self) -> dict[str, typing.Any]:
77-
return {"logger": structlog.get_logger("microbootstrap-faststream")}
82+
return {"logger": faststream_app_logger}
83+
84+
def bootstrap_after(self, application: AsgiFastStream) -> AsgiFastStream: # type: ignore[override]
85+
for one_broker in application.brokers:
86+
one_broker.config.broker_config.logger.logger = RealLoggerObject(faststream_broker_logger)
87+
return application
7888

7989

8090
@FastStreamBootstrapper.use_instrument()

0 commit comments

Comments
 (0)