class Async::HTTP::Internet
def self.instance
def self.instance ::Thread.current.async_http_internet_instance ||= self.new end
def call(verb, url, *arguments, **options, &block)
@parameter headers [Hash | Protocol::HTTP::Headers] The headers to send with the request.
@parameter url [String] The URL to request, e.g. `https://www.codeotaku.com`.
@parameter method [String] The request method, e.g. `GET`.
If you provide non-frozen headers, they may be mutated.
Make a request to the internet with the given `method` and `url`.
def call(verb, url, *arguments, **options, &block) endpoint = Endpoint[url] client = self.client_for(endpoint) options[:authority] ||= endpoint.authority options[:scheme] ||= endpoint.scheme request = ::Protocol::HTTP::Request[verb, endpoint.path, *arguments, **options] response = client.call(request) return response unless block_given? begin yield response ensure response.close end end
def client_for(endpoint)
def client_for(endpoint) key = host_key(endpoint) @clients.fetch(key) do @clients[key] = self.make_client(endpoint) end end
def close
def close # The order of operations here is to avoid a race condition between iterating over clients (#close may yield) and creating new clients. clients = @clients.values @clients.clear clients.each(&:close) end
def host_key(endpoint)
def host_key(endpoint) url = endpoint.url.dup url.path = "" url.fragment = nil url.query = nil return url end
def initialize(**options)
def initialize(**options) @clients = Hash.new @options = options end
def make_client(endpoint)
def make_client(endpoint) ::Protocol::HTTP::AcceptEncoding.new( Client.new(endpoint, **@options) ) end