@param string $method
@param string $uri
@param mixed $body
@param array $query
@param array $headers
@param array $options

@return ResponseInterface

@throws ApiException
557365
public function send($method, $uri, $body = null, array $query = [], array $headers = [], array $options = [])
    {
        $options = $this->enhanceOptions($body, $query, $headers, $options);

        try {
            $this->lastResponse = $this->client->request($method, $uri, $options);
        } catch (GuzzleException $e) {
            throw new ApiException($e->getMessage(), $e->getCode());
        }

        $this->validateResponse($this->lastResponse);

        return $this->lastResponse;
    }
361837
public function request($method, $url, $body = null, $headers = [], $options = [])
    {
        if (is_array($url)) {
            if (count($url) > 1) {
                $uri = $url[0];
                unset($url[0]);
                $url = $uri . (strpos($uri, '?') !== false ? '&' : '?') . http_build_query($url);
            } else {
                $url = $url[0];
            }
        }

        if (preg_match('/^http(s)?:\/\//i', $url) !== 1) {
            throw new NotSupportedException(['only HTTP requests can be handled: `:url`', 'url' => $url]);
        }

        if (is_string($headers)) {
            $headers = [strpos($headers, '://') ? 'Referer' : 'User-Agent' => $headers];
        }

        if (isset($headers['-'])) {
            $headers['Referer'] = $headers['-'];
            unset($headers['-']);
        }

        if (isset($headers['Referer'])) {
            if (is_array($headers['Referer'])) {
                $referer = $headers['Referer'];
                if (isset($referer[0])) {
                    $str = $referer[0];
                    unset($referer[0]);
                } else {
                    $str = 'http://TRACK/';
                }
                $headers['Referer'] = $str . (strpos($str, '?') ? '&' : '?') . http_build_query($referer);
            } elseif (!strpos($options['Referer'], '://')) {
                $headers['Referer'] = 'http://TRACE/' . $headers['Referer'];
            }
        }

        if (!isset($headers['User-Agent'])) {
            $headers['User-Agent'] = self::USER_AGENT_IE;
        }

        if (is_int($options) || is_float($options)) {
            $options = ['timeout' => $options];
        }

        if (!isset($options['timeout'])) {
            $options['timeout'] = $this->_timeout;
        }

        if ($this->_proxy && !isset($options['proxy'])) {
            $options['proxy'] = $this->_proxy;
        }

        if ($this->_cafile && !isset($options['cafile'])) {
            $options['cafile'] = $this->_cafile;
        }

        $options['verify_peer'] = $this->_verify_peer;

        $request = new Request();
        $request->method = $method;
        $request->url = $url;
        $request->headers = $headers;
        $request->body = $body;
        $request->options = $options;

        $this->logger->debug($request, 'httpClient.request');

        $this->eventsManager->fireEvent('httpClient:beforeRequest', $this, $request);
        $response = $this->do_request($request);
        if (strpos($response->content_type, '/json') !== false && $json = json_decode($response->body, true)) {
            $response->body = $json;
        }
        $this->eventsManager->fireEvent('httpClient:afterRequest', $this, $response);
        $response->request = $request;
        $response->user_data = isset($options['user_data']) ? $options['user_data'] : null;

        $this->logger->debug($response, 'httpClient.response');

        if ($response->http_code === 429) {
            throw new TooManyRequestsException($response->url, $response);
        } elseif ($response->http_code === 403) {
            throw new ForbiddenException($response->url, $response);
        } elseif ($response->http_code === 401) {
            throw new UnauthorizedException($response->url, $response);
        }

        if ($response->http_code >= 500) {
            throw new ServiceUnavailableException(['service is unavailable: :http_code => `:url`',
                'http_code' => $response->http_code,
                'url' => $response->url], $response);
        }

        if ($response->http_code >= 400) {
            throw new BadRequestException(['bad request: :http_code => `:url`', 'http_code' => $response->http_code, 'url' => $response->url], $response);
        }

        return $response;
    }
1050736
protected function request($method, $url, array $options, $body = '')
	{
		$response = @file_get_contents($url, false, $this->createContext($method, $options, $body));
		if ($response === false)
		{
			return false;
		}

		$response = $this->decompress($response);
		if (!empty($options['returnHeaders']))
		{
			$response = implode("\r\n", $http_response_header) . "\r\n\r\n" . $response;
		}

		return $response;
	}
1325989
protected function makeRequest($method, $uri, $options)
    {
        $logger = $this->getLogger();

        try {
            $logger->info(sprintf('Making API %s request to %s', $method, $uri), [$options]);

            /** @var ResponseInterface $response */
            $response = $this->_doRequest($method, $uri, $options);

            $logger->debug('Response from HTTP call was status code:', [$response->getStatusCode()]);
            $logger->debug('Response JSON was:', [$response->getBody()]);

            return $response;
        } catch (\Exception $e) {
            throw $e; // Just rethrow for now
        }
    }
360934
private function sendRequest($method, $url, array $options = [])
    {
        $response = $this->httpClient->request((string)$method, $url, $options);

        return json_decode($response->getBody(), true);
    }
1086189
public function createRequest($method = RequestInterface::GET, $uri = null, $headers = null, $body = null)
        {

            $request = parent::createRequest($method, $uri, $headers, $body);
            // see http://snippets.webaware.com.au/howto/stop-turning-off-curlopt_ssl_verifypeer-and-fix-your-php-config/
            #$request->getCurlOptions()->set(CURLOPT_SSL_VERIFYPEER, false);

            // Add Zelift auth headers
            $hTimestamp = $this->getTimestamp();

            $baseSig = Keyring::getAppSecret() . '+' . Keyring::getConsumerKey() . '+' . $method . '+' . $request->getUrl() . '+' . $body . '+' . $hTimestamp;

            $sig = '$1$' . sha1($baseSig);
            $request->addHeader('X-Zelift-Application', Keyring::getAppKey());
            $request->addHeader('X-Zelift-Timestamp', $hTimestamp);
            $request->addHeader('X-Zelift-Consumer', Keyring::getConsumerKey());
            $request->addHeader('X-Zelift-Signature', $sig);

            return $request;
        }
1271332
protected function httpRequest($method, $uri, array $options = [])
    {
        if (null !== $this->proxy) {
            $options[RequestOptions::PROXY] = $this->proxy;
        }

        if (!isset($options[RequestOptions::HEADERS])) {
            $options[RequestOptions::HEADERS] = $this->getHttpHeaders();
        } else {
            $options[RequestOptions::HEADERS] = array_merge($this->getHttpHeaders(), $options[RequestOptions::HEADERS]);
        }

        if (!isset($options[RequestOptions::HTTP_ERRORS])) {
            $options[RequestOptions::HTTP_ERRORS] = false;
        }

        if (!isset($options[RequestOptions::ALLOW_REDIRECTS])) {
            $options[RequestOptions::ALLOW_REDIRECTS] = false;
        }

        if (!isset($options[RequestOptions::TIMEOUT]) && null !== $this->timeout) {
            $options[RequestOptions::TIMEOUT] = $this->timeout;
        }

        if (null !== $this->qps && null !== $this->lastRequestTime) {
            $lastInterval = floor((microtime(true) - $this->lastRequestTime) * 1000000);
            $timeout = ceil(1000000 / $this->qps);
            if ($lastInterval < $timeout) {
                usleep($timeout - $lastInterval);
            }
        }

        $response = $this->getHttpClient()->request($method, $uri, $options);
        $this->lastRequestTime = microtime(true);
        $this->history[] = [
            'method' => $method,
            'uri' => $uri,
            'time' => $this->lastRequestTime,
            'status' => $response->getStatusCode(),
        ];

        return $response;
    }
632572
public function invoke($uri, $method, array $headers = [])
    {
        $client   = new Client();
        $res      = $client->createRequest(strtoupper($method), url('/') . '/' . $uri, array_merge($headers, $this->getHeaders()));
        $response = $res->send();
        $types    = $response->getHeader('Content-Type')->toArray();
        $body     = $response->getBody(true);
        foreach ($types as $type) {
            if ($type == 'application/json' && function_exists('json_decode') and is_string($body)) {
                return json_decode($body);
            }
        }

        return $body;
    }
470451
public function request($url, $method = 'GET', $headers = [], $body = null, $options = [])
    {
        if (false === is_array($options)) {
            $options = [];
        }

        $request = $this->getGuzzleClient()->createRequest($method, $url, $options);

        $request->addHeaders($headers);
        $request->setBody($body);

        $response = $this->getGuzzleClient()->send($request);

        return [
            'code'    => $response->getStatusCode(),
            'headers' => $response->getHeaders(),
            'body'    => (string)$response->getBody(),
        ];
    }
1128559
public function send(string $method, string $url, array $options)
    {
        try {
            // Guzzle overwrites all query string values in the URI if queries are specified
            // in the 'query' option, so they need to be extracted first.
            $optionsPayload = $this->mergeOptions(
                ['query' => $this->parseQueryParams($url)],
                $options
            );

            $response = $this->buildClient()->request($method, $url, $optionsPayload);

            return $this->buildResponse($response);
        } catch (GuzzleException $exception) {
            // No "custom" exceptions, just rethrow whatever guzzle spits out.
            throw $exception;
        }
    }
1303010
private static function requestApi($method, $body=null, $id=null) {
        $uri = Params::ENDPOINT . '/orders';
        if ($method == "get" || $method == "put")
            $uri .= "/$id";

        $request = new HttpRequest($method, $uri, self::$useSSL, self::$additionalCurlOpts);
        $request->setBasicAuthorization(self::$key);
        if (!is_null($body)) $request->setBodyAsJson($body);

        $response = $request->send();
        $response->checkCurlResponse();
        $jsonBody = $response->getBodyAsJson();
        if (!$response->isOk() || is_null($jsonBody) || !self::isBodyStatusOk($jsonBody)) {
            $httpStatus = $response->getHttpStatus();
            throw Exceptions\KondutoException::buildFromHttpStatus($jsonBody, $httpStatus);
        }

        return $response;
    }
356983
public function createRequest($url, $method = 'GET', array $headers = [], $body = null)
    {
        $headers = array_merge($headers, ['User-Agent' => strval($this->userAgent)]);
        return new Request($method, $url, $headers, $body);
    }
723925
public function handle(string $method, $body = false, $uriAppend = false, array $queryParams = [])
    {
        $clientBuilder = new ClientBuilder();
        $url           = HttpHelper::setHttPortToUrl($this->client->getGatewayUrl(), false) . '/' . $this->resource->getVersion() . '/' . $this->resource->getURI();
        $client = $clientBuilder->setConnectionParams(['client' => ['headers' => $this->setAuthorization()]])
                                ->setHosts(['host' => $url])
                                ->build();

        try {

            $size = $queryParams['body']['size'] ?? 0;
            $from = $queryParams['body']['from'] ?? 0;

            $response = new ElasticSearchResponse($this->multi ? $client->msearch($queryParams) : $client->search($queryParams), $this->multi, $size, $from);
        } catch (\Exception $ex) {
            $error = json_decode($ex->getMessage());
            throw new \Exception($error->error->reason ?? $ex->getMessage());
        }

        return $response;
    }
1213833
public function rest($method, $url, $body = null, $headers = [], $options = [])
    {
        if (isset($headers['Content-Type']) && strpos($headers['Content-Type'], '/json') === false) {
            throw new InvalidValueException(['Content-Type of rest is not application/json: :content-type', 'content-type' => $headers['Content-Type']]);
        } else {
            $headers['Content-Type'] = 'application/json';
        }

        if (!isset($headers['X-Requested-With'])) {
            $headers['X-Requested-With'] = 'XMLHttpRequest';
        }

        if (!isset($headers['Accept'])) {
            $headers['Accept'] = 'application/json';
        }

        if (is_array($body)) {
            $body = json_encode($body, JSON_UNESCAPED_SLASHES | JSON_UNESCAPED_UNICODE);
        }

        $response = $this->request($method, $url, $body, $headers, $options);

        if (!is_array($response->body)) {
            if (strpos($response->content_type, '/json') === false) {
                throw new ContentTypeException(['content-type of response is not application/json: :content-type => `:url`',
                    'content-type' => $response->content_type,
                    'url' => $response->url],
                    $response);
            }

            throw new JsonDecodeException(['json decode failed: `:url`', 'url' => $response->url], $response);
        }

        return $response;
    }
410522
private function requestAPI($method, $url, array $options = [])
    {
        try {
            return $this->sendRequest((string)$method, (string)$url, $options);
        } catch (SessionWasExpiredException $e) {
            return $this->sendRequest((string)$method, (string)$url, $options);
        } catch (ClientException $e) {
            throw new BunqException($e);
        }
    }
659567
public function run(
        string $method,
        string $uri,
        array $headers,
        string $body
    ) {
        if ($this->router === null) {
            return;
        }

        try {
            $response = $this->router->run($method, $uri, $headers, $body);
            if ($response !== null) {
                $response->output();
            }
        } catch (RouterException $e) {
            $e->getResponse()->output();
        }
    }
963258
public function request(string $method, string $url, array $options = []): ResponseInterface
    {
        [$url, $options] = self::prepareRequest($method, $url, $options, $this->defaultOptions);
        $scheme = $url['scheme'];
        $authority = $url['authority'];
        $host = parse_url($authority, PHP_URL_HOST);
        $url = implode('', $url);

        if ($pushedResponse = $this->multi->pushedResponses[$url] ?? null) {
            unset($this->multi->pushedResponses[$url]);
            // Accept pushed responses only if their headers related to authentication match the request
            $expectedHeaders = [
                $options['headers']['authorization'] ?? null,
                $options['headers']['cookie'] ?? null,
                $options['headers']['x-requested-with'] ?? null,
                $options['headers']['range'] ?? null,
            ];

            if ('GET' === $method && $expectedHeaders === $pushedResponse->headers && !$options['body']) {
                $this->logger && $this->logger->debug(sprintf('Connecting request to pushed response: "%s %s"', $method, $url));

                // Reinitialize the pushed response with request's options
                $pushedResponse->response->__construct($this->multi, $url, $options, $this->logger);

                return $pushedResponse->response;
            }

            $this->logger && $this->logger->debug(sprintf('Rejecting pushed response for "%s": authorization headers don\'t match the request', $url));
        }

        $this->logger && $this->logger->info(sprintf('Request: "%s %s"', $method, $url));

        $curlopts = [
            CURLOPT_URL => $url,
            CURLOPT_USERAGENT => 'Symfony HttpClient/Curl',
            CURLOPT_TCP_NODELAY => true,
            CURLOPT_PROTOCOLS => CURLPROTO_HTTP | CURLPROTO_HTTPS,
            CURLOPT_REDIR_PROTOCOLS => CURLPROTO_HTTP | CURLPROTO_HTTPS,
            CURLOPT_FOLLOWLOCATION => true,
            CURLOPT_MAXREDIRS => 0 < $options['max_redirects'] ? $options['max_redirects'] : 0,
            CURLOPT_COOKIEFILE => '', // Keep track of cookies during redirects
            CURLOPT_CONNECTTIMEOUT_MS => 1000 * $options['timeout'],
            CURLOPT_PROXY => $options['proxy'],
            CURLOPT_NOPROXY => $options['no_proxy'] ?? $_SERVER['no_proxy'] ?? $_SERVER['NO_PROXY'] ?? '',
            CURLOPT_SSL_VERIFYPEER => $options['verify_peer'],
            CURLOPT_SSL_VERIFYHOST => $options['verify_host'] ? 2 : 0,
            CURLOPT_CAINFO => $options['cafile'],
            CURLOPT_CAPATH => $options['capath'],
            CURLOPT_SSL_CIPHER_LIST => $options['ciphers'],
            CURLOPT_SSLCERT => $options['local_cert'],
            CURLOPT_SSLKEY => $options['local_pk'],
            CURLOPT_KEYPASSWD => $options['passphrase'],
            CURLOPT_CERTINFO => $options['capture_peer_cert_chain'],
        ];

        if (!ZEND_THREAD_SAFE) {
            $curlopts[CURLOPT_DNS_USE_GLOBAL_CACHE] = false;
        }

        if (\defined('CURLOPT_HEADEROPT')) {
            $curlopts[CURLOPT_HEADEROPT] = CURLHEADER_SEPARATE;
        }

        // curl's resolve feature varies by host:port but ours varies by host only, let's handle this with our own DNS map
        if (isset($this->multi->dnsCache->hostnames[$host])) {
            $options['resolve'] += [$host => $this->multi->dnsCache->hostnames[$host]];
        }

        if ($options['resolve'] || $this->multi->dnsCache->evictions) {
            // First reset any old DNS cache entries then add the new ones
            $resolve = $this->multi->dnsCache->evictions;
            $this->multi->dnsCache->evictions = [];
            $port = parse_url($authority, PHP_URL_PORT) ?: ('http:' === $scheme ? 80 : 443);

            if ($resolve && 0x072a00 > curl_version()['version_number']) {
                // DNS cache removals require curl 7.42 or higher
                // On lower versions, we have to create a new multi handle
                curl_multi_close($this->multi->handle);
                $this->multi->handle = (new self())->multi->handle;
            }

            foreach ($options['resolve'] as $host => $ip) {
                $resolve[] = null === $ip ? "-$host:$port" : "$host:$port:$ip";
                $this->multi->dnsCache->hostnames[$host] = $ip;
                $this->multi->dnsCache->removals["-$host:$port"] = "-$host:$port";
            }

            $curlopts[CURLOPT_RESOLVE] = $resolve;
        }

        if (1.0 === (float) $options['http_version']) {
            $curlopts[CURLOPT_HTTP_VERSION] = CURL_HTTP_VERSION_1_0;
        } elseif (1.1 === (float) $options['http_version'] || 'https:' !== $scheme) {
            $curlopts[CURLOPT_HTTP_VERSION] = CURL_HTTP_VERSION_1_1;
        } elseif (CURL_VERSION_HTTP2 & curl_version()['features']) {
            $curlopts[CURLOPT_HTTP_VERSION] = CURL_HTTP_VERSION_2_0;
        }

        if ('POST' === $method) {
            // Use CURLOPT_POST to have browser-like POST-to-GET redirects for 301, 302 and 303
            $curlopts[CURLOPT_POST] = true;
        } else {
            $curlopts[CURLOPT_CUSTOMREQUEST] = $method;
        }

        if ('\\' !== \DIRECTORY_SEPARATOR && $options['timeout'] < 1) {
            $curlopts[CURLOPT_NOSIGNAL] = true;
        }

        if (!isset($options['headers']['accept-encoding'])) {
            $curlopts[CURLOPT_ENCODING] = ''; // Enable HTTP compression
        }

        foreach ($options['request_headers'] as $header) {
            if (':' === $header[-2] && \strlen($header) - 2 === strpos($header, ': ')) {
                // curl requires a special syntax to send empty headers
                $curlopts[CURLOPT_HTTPHEADER][] = substr_replace($header, ';', -2);
            } else {
                $curlopts[CURLOPT_HTTPHEADER][] = $header;
            }
        }

        // Prevent curl from sending its default Accept and Expect headers
        foreach (['accept', 'expect'] as $header) {
            if (!isset($options['headers'][$header])) {
                $curlopts[CURLOPT_HTTPHEADER][] = $header.':';
            }
        }

        if (!\is_string($body = $options['body'])) {
            if (\is_resource($body)) {
                $curlopts[CURLOPT_INFILE] = $body;
            } else {
                $eof = false;
                $buffer = '';
                $curlopts[CURLOPT_READFUNCTION] = static function ($ch, $fd, $length) use ($body, &$buffer, &$eof) {
                    return self::readRequestBody($length, $body, $buffer, $eof);
                };
            }

            if (isset($options['headers']['content-length'][0])) {
                $curlopts[CURLOPT_INFILESIZE] = $options['headers']['content-length'][0];
            } elseif (!isset($options['headers']['transfer-encoding'])) {
                $curlopts[CURLOPT_HTTPHEADER][] = 'Transfer-Encoding: chunked'; // Enable chunked request bodies
            }

            if ('POST' !== $method) {
                $curlopts[CURLOPT_UPLOAD] = true;
            }
        } elseif ('' !== $body) {
            $curlopts[CURLOPT_POSTFIELDS] = $body;
        }

        if ($options['peer_fingerprint']) {
            if (!isset($options['peer_fingerprint']['pin-sha256'])) {
                throw new TransportException(__CLASS__.' supports only "pin-sha256" fingerprints.');
            }

            $curlopts[CURLOPT_PINNEDPUBLICKEY] = 'sha256//'.implode(';sha256//', $options['peer_fingerprint']['pin-sha256']);
        }

        if ($options['bindto']) {
            $curlopts[file_exists($options['bindto']) ? CURLOPT_UNIX_SOCKET_PATH : CURLOPT_INTERFACE] = $options['bindto'];
        }

        $ch = curl_init();

        foreach ($curlopts as $opt => $value) {
            if (null !== $value && !curl_setopt($ch, $opt, $value) && CURLOPT_CERTINFO !== $opt) {
                $constants = array_filter(get_defined_constants(), static function ($v, $k) use ($opt) {
                    return $v === $opt && 'C' === $k[0] && (0 === strpos($k, 'CURLOPT_') || 0 === strpos($k, 'CURLINFO_'));
                }, ARRAY_FILTER_USE_BOTH);

                throw new TransportException(sprintf('Curl option "%s" is not supported.', key($constants) ?? $opt));
            }
        }

        return new CurlResponse($this->multi, $ch, $options, $this->logger, $method, self::createRedirectResolver($options, $host));
    }