Open rlipscombe opened 5 months ago
I've been wracking my brains for ways to wrap cowboy_router:compile
or the cowboy_router
middleware, or to wrap the individual handlers, but I can't come up with anything that doesn't feel like a hack.
After some thought, I've come up with the following, which doesn't require any cowboy changes:
Handler
with a tuple, {Handler, HandlerOpts}
HandlerOpts
with HandlerMetadata
.Add a middleware that goes in between cowboy_router
and cowboy_handler
that does this:
execute(Req, Env = #{handler := {Handler, HandlerOpts}, handler_opts := Metadata}) ->
Env2 = Env#{handler => Handler, handler_opts => HandlerOpts, handler_metadata => Metadata},
{ok, Req, Env2}.
Getting handler_metadata
into user_data
where the metrics callback can see it is left as an exercise for the reader.
One question that occasionally arises at work is "how do we attach telemetry labels to a cowboy route?". We'd like to be able to attach arbitrary metadata to a route, and have it available in the
cowboy_metrics_h
callback.Ideally, it would be an extra element in the route tuple, something like this:
...and would be picked up by the
cowboy_router
middleware and put in the env along withhandler
andhandler_opts
.(to avoid ambiguity, if you wanted this, you'd have to explicitly specify constraints, possibly empty -- or maybe
{Handler, Opts}
would need to be a tuple in this case).Does this seem like a good idea? Is there another way to do it right now?