lib/datadog/ci/transport/http.rb in datadog-ci-1.0.0.beta1 vs lib/datadog/ci/transport/http.rb in datadog-ci-1.0.0.beta2
- old
+ new
@@ -2,10 +2,11 @@
require "delegate"
require "datadog/core/transport/http/adapters/net"
require "datadog/core/transport/http/env"
require "datadog/core/transport/request"
+require "socket"
require_relative "gzip"
require_relative "../ext/transport"
module Datadog
@@ -18,20 +19,22 @@
:ssl,
:timeout,
:compress
DEFAULT_TIMEOUT = 30
+ MAX_RETRIES = 3
+ INITIAL_BACKOFF = 1
def initialize(host:, timeout: DEFAULT_TIMEOUT, port: nil, ssl: true, compress: false)
@host = host
@port = port
@timeout = timeout
@ssl = ssl.nil? ? true : ssl
@compress = compress.nil? ? false : compress
end
- def request(path:, payload:, headers:, verb: "post")
+ def request(path:, payload:, headers:, verb: "post", retries: MAX_RETRIES, backoff: INITIAL_BACKOFF)
if compress
headers[Ext::Transport::HEADER_CONTENT_ENCODING] = Ext::Transport::CONTENT_ENCODING_GZIP
payload = Gzip.compress(payload)
end
@@ -39,22 +42,39 @@
"Sending #{verb} request: host=#{host}; port=#{port}; ssl_enabled=#{ssl}; " \
"compression_enabled=#{compress}; path=#{path}; payload_size=#{payload.size}"
end
response = ResponseDecorator.new(
- adapter.call(
- build_env(path: path, payload: payload, headers: headers, verb: verb)
- )
+ perform_http_call(path: path, payload: payload, headers: headers, verb: verb, retries: retries, backoff: backoff)
)
Datadog.logger.debug do
"Received server response: #{response.inspect}"
end
response
end
private
+
+ def perform_http_call(path:, payload:, headers:, verb:, retries: MAX_RETRIES, backoff: INITIAL_BACKOFF)
+ adapter.call(
+ build_env(path: path, payload: payload, headers: headers, verb: verb)
+ )
+ rescue Timeout::Error, Errno::EINVAL, Errno::ECONNRESET, EOFError, SocketError, Net::HTTPBadResponse => e
+ Datadog.logger.debug("Failed to send request with #{e} (#{e.message})")
+
+ if retries.positive?
+ sleep(backoff)
+
+ perform_http_call(
+ path: path, payload: payload, headers: headers, verb: verb, retries: retries - 1, backoff: backoff * 2
+ )
+ else
+ Datadog.logger.error("Failed to send request after #{MAX_RETRIES} retries")
+ raise e
+ end
+ end
def build_env(path:, payload:, headers:, verb:)
env = Datadog::Core::Transport::HTTP::Env.new(
Datadog::Core::Transport::Request.new
)