Middleware are classes that implement a
#call instance method. They hook into the request/response cycle.
def call(request_env) # do something with the request # request_env[:request_headers].merge!(...) @app.call(request_env).on_complete do |response_env| # do something with the response # response_env[:response_headers].merge!(...) end end
It’s important to do all processing of the response only in the
block. This enables middleware to work in parallel mode where requests are
env is a hash with symbol keys that contains info about the request and,
later, response. Some keys are:
# request phase :method - :get, :post, ... :url - URI for the current request; also contains GET parameters :body - POST parameters for :post/:put requests :request_headers # response phase :status - HTTP response status code, such as 200 :body - the response body :response_headers
There’s an easier way to write middleware, and it’s also the recommended one: make your middleware subclass
Faraday::Middleware already implements the
#call method for you and looks for two methods in your subclass:
#on_request is called when the request is being built and is given the
env representing the request.
#on_complete is called after the response has been received (that’s right, it already supports parallel mode!) and receives the
env of the response.
Do I need to override
For the majority of middleware, it’s not necessary to override the
#call method. You can instead use
However, in some cases you may need to wrap the call in a block, or work around it somehow (think of a begin-rescue, for example).
When that happens, then you can override
#call. When you do so, remember to call either
super to avoid breaking the middleware stack call!