protected function handleErrorResponses(
        ResponseInterface $response,
        RequestInterface $request,
        CommandInterface $command,
        Operation $operation
    ) {
        $errors = $operation->getErrorResponses();

        // We iterate through each errors in service description. If the descriptor contains both a phrase and
        // status code, there must be an exact match of both. Otherwise, a match of status code is enough
        $bestException = null;

        foreach ($errors as $error) {
            $code = (int) $error['code'];

            if ($response->getStatusCode() !== $code) {
                continue;
            }

            if (isset($error['phrase']) && ! ($error['phrase'] === $response->getReasonPhrase())) {
                continue;
            }

            $bestException = $error['class'];

            // If there is an exact match of phrase + code, then we cannot find a more specialized exception in
            // the array, so we can break early instead of iterating the remaining ones
            if (isset($error['phrase'])) {
                break;
            }
        }

        if (null !== $bestException) {
            throw new $bestException($response->getReasonPhrase(), $command, null, $request, $response);
        }

        // If we reach here, no exception could be match from descriptor, and Guzzle exception will propagate if
        // option "http_errors" is set to true, which is the default setting.
    }