def retriable_rest_request(method, url, req_body, headers)
rest_request = Chef::REST::RESTRequest.new(method, url, req_body, headers)
Chef::Log.debug("Sending HTTP Request via #{method} to #{url.host}:#{url.port}#{rest_request.path}")
http_attempts = 0
begin
http_attempts += 1
res = yield rest_request
rescue Errno::ECONNREFUSED
if http_retry_count - http_attempts + 1 > 0
Chef::Log.error("Connection refused connecting to #{url.host}:#{url.port} for #{rest_request.path}, retry #{http_attempts}/#{http_retry_count}")
sleep(http_retry_delay)
retry
end
raise Errno::ECONNREFUSED, "Connection refused connecting to #{url.host}:#{url.port} for #{rest_request.path}, giving up"
rescue Timeout::Error
if http_retry_count - http_attempts + 1 > 0
Chef::Log.error("Timeout connecting to #{url.host}:#{url.port} for #{rest_request.path}, retry #{http_attempts}/#{http_retry_count}")
sleep(http_retry_delay)
retry
end
raise Timeout::Error, "Timeout connecting to #{url.host}:#{url.port} for #{rest_request.path}, giving up"
rescue Net::HTTPServerException
if res.kind_of?(Net::HTTPForbidden)
if http_retry_count - http_attempts + 1 > 0
Chef::Log.error("Received 403 Forbidden against #{url.host}:#{url.port} for #{rest_request.path}, retry #{http_attempts}/#{http_retry_count}")
sleep(http_retry_delay)
retry
end
end
raise
end
end