lib/httpx/plugins/retries.rb in httpx-0.17.0 vs lib/httpx/plugins/retries.rb in httpx-0.18.0
- old
+ new
@@ -20,13 +20,20 @@
TLSError,
TimeoutError,
Parser::Error,
Errno::EINVAL,
Errno::ETIMEDOUT].freeze
+ DEFAULT_JITTER = ->(interval) { interval * (0.5 * (1 + rand)) }
- def self.extra_options(options)
- options.merge(max_retries: MAX_RETRIES)
+ if ENV.key?("HTTPX_NO_JITTER")
+ def self.extra_options(options)
+ options.merge(max_retries: MAX_RETRIES)
+ end
+ else
+ def self.extra_options(options)
+ options.merge(max_retries: MAX_RETRIES, retry_jitter: DEFAULT_JITTER)
+ end
end
module OptionsMethods
def option_retry_after(value)
# return early if callable
@@ -36,10 +43,17 @@
end
value
end
+ def option_retry_jitter(value)
+ # return early if callable
+ raise TypeError, ":retry_jitter must be callable" unless value.respond_to?(:call)
+
+ value
+ end
+
def option_max_retries(value)
num = Integer(value)
raise TypeError, ":max_retries must be positive" unless num.positive?
num
@@ -85,13 +99,18 @@
retry_after = options.retry_after
retry_after = retry_after.call(request, response) if retry_after.respond_to?(:call)
if retry_after
+ # apply jitter
+ if (jitter = request.options.retry_jitter)
+ retry_after = jitter.call(retry_after)
+ end
+ retry_start = Utils.now
log { "retrying after #{retry_after} secs..." }
pool.after(retry_after) do
- log { "retrying!!" }
+ log { "retrying (elapsed time: #{Utils.elapsed_time(retry_start)})!!" }
connection = find_connection(request, connections, options)
connection.send(request)
end
else
connection = find_connection(request, connections, options)