For me Tesla.Middlewear.Logger
is great for debugging as you can log the whole request/response. I believe the architecture of Req makes this difficult as there is no way to hook into the entire communication cycle.
I also find that the Tesla Middlewear model is simpler than Req’s, which requires more boilerplate and is a bit harder to get your head around, at least that was my impression from writing equivalent middlewear for both clients:
Tesla:
def call(%Tesla.Env{method: :get, url: url} = env, next, options) do
timeout = Keyword.get(options || [], :debounce_timeout)
case Boing.debounce(url, timeout) do
:ok -> Tesla.run(env, next)
{:error, debounced: ^url} -> {:error, debounced: url}
end
end
Req:
defmodule DebouncedException do
defexception [:url]
@impl Exception
def message(%__MODULE__{url: url}), do: "Debounced: #{url}"
end
def attach(%Req.Request{} = request, options \\ []) do
request
|> Req.Request.register_options([:debounce_timeout])
|> Req.Request.merge_options(options)
|> Req.Request.append_request_steps(debounce: &debounce_step/1)
end
defp debounce_step(%Req.Request{method: :get, url: url} = request) do
timeout = request.options[:debounce_timeout]
case Boing.debounce(URI.to_string(url), timeout) do
:ok -> request
{:error, debounced: url} -> {request, DebouncedException.exception(url: url)}
end
end