Ошибка «407 Proxy Authentication Required» во время запроса на отдых Java иногда - PullRequest
0 голосов
/ 26 июня 2019

Я пытаюсь выполнить запрос REST на один из URL моего клиента, чтобы получить ответ с помощью прокси. В большинстве случаев я могу получить ответ, используя свой код. Но иногда, когда я пытаюсь отправить запрос, используя мойкод Я получаю ошибку «407 Proxy Authentication Required». Это случается редко, но как только я получаю эту ошибку, для каждого последовательного запроса я получаю ту же ошибку. Но когда я использую инструмент POSTMAN из Chrome, чтобы отправить тот же запрос, который был сгенерирован впо тому же URL-адресу я получу ответ. Но как только я получу ответ от POSTMAN, если я попытаюсь повторить свой код, я начну получать ответ не только с моей локальной машины, но и с других машин, на которых я запускаю код.Я очень смущен этой проблемой и не могу понять, почему происходит этот странный сценарий. Есть ли что-то, чего мне не хватает в моем коде. Пожалуйста, помогите мне, ребята. Я дал мой код ниже:

Код

public Map<String ,Object> ConnectRestService(MyRequest myRequest, String postURL, String httpProxy,int timeout int httpPort, Map<String ,Object> responseMap)
        throws KeyManagementException, UnrecoverableKeyException, NoSuchAlgorithmException, KeyStoreException, CustomException{

    MyResponse myResponse = new MyResponse();
    Map<String ,Object> responseReturnMap = new HashMap<>();
    String output = "";
    TrustStrategy acceptingTrustStrategy = new TrustStrategy() {

        @Override
        public boolean isTrusted(java.security.cert.X509Certificate[] chain, String authType)
                throws java.security.cert.CertificateException {
            // TODO Auto-generated method stub
            return true;
        }
    };

    SSLContext sslContext = SSLContexts.custom()
            .loadTrustMaterial(null, acceptingTrustStrategy)
            .build();


    SSLConnectionSocketFactory csf = new SSLConnectionSocketFactory(sslContext);
    HttpClient httpClient;
    httpClient = HttpClients.custom().setSSLSocketFactory(csf).setProxy(new HttpHost(httpProxy, httpPort)).build();

    HttpHeaders httpHeaders = new HttpHeaders();
    httpHeaders.add("Content-type", "text/xml");
    httpHeaders.add("Accept", "text/xml");
    httpHeaders.add("access-control-allow-origin", "*");
    httpHeaders.add("content-encoding", "UTF-8");
    HttpComponentsClientHttpRequestFactory requestFactory = new HttpComponentsClientHttpRequestFactory(httpClient);
    requestFactory.setConnectTimeout(timeout);


    try {
        RestTemplate restTemplate = new RestTemplate(requestFactory);
        HttpEntity<MyRequest> entity = new org.springframework.http.HttpEntity<MyRequest>(
                myRequest, httpHeaders);
        ResponseEntity<String> response = restTemplate.exchange(postURL, HttpMethod.POST, entity, String.class);


    } catch (Exception ex) {
        logger.error(ex.getMessage(), ex);
    }

    return responseReturnMap;
}

Пожалуйста, помогите мне выяснить, что мне здесь не хватает.

Ответы [ 5 ]

3 голосов
/ 03 июля 2019

В случае ошибки 407 полученный вами ответ должен содержать специальный заголовок Proxy-Authenticate.Этот заголовок скажет вам, какую аутентификацию ожидает прокси-сервер.

Что вам нужно сделать, это включить заголовок Proxy-Authorization в ваш запрос.Типичный синтаксис заголовка Proxy-Authorization - заголовок Proxy-Authorization:<type-of-authentication-scheme> <credentials-for-authentication-at-proxy-server>.

Proxy-Authenticate, который позволит вам узнать тип схемы аутентификации, которую вам нужно использовать.

0 голосов
/ 09 июля 2019

Пожалуйста, попробуйте немного очистить ваш код.Я думаю, что создание RestTemplate каждый раз создает давление на сборщик мусора, но также может привести к другим проблемам.Также вы возвращаете всегда пустую карту из вашего метода (возможно, очищая код во время отладки ...).

Чтобы решить вашу проблему, попробуйте проверить ваш стек tcp или стек tcp прокси-сервера (если есть)когда возникает проблема.Например, посмотрите на количество открытых соединений с помощью команды, подобной this :

ss -s

PS: Перезапуск клиентского приложения / сервера также помогает?Есть ли другие способы, как «заставить его работать снова» вместо использования почтальона?

0 голосов
/ 06 июля 2019

Я думаю, что вы пытаетесь получить к нему доступ с прокси-сервера . В этом случае вы должны добавить Proxy-Authorization в заголовок.

Попробуйте использовать этот фрагмент кода:

String data = "user:password"; // Here proxy user and password to be used.
String encodedValue = Base64.getEncoder().encodeToString(data.getBytes());
HttpHeaders httpHeaders = new HttpHeaders();
httpHeaders.add("Proxy-Authorization", "Basic " + encodedValue); // You need to add proxy-authorization in the header.

Прочитайте эту ссылку: Документация Mozilla для авторизации через прокси

0 голосов
/ 04 июля 2019

Глядя на ваш код, я заинтересовался этой строкой кода:

httpHeaders.add("access-control-allow-origin", "*");

Вместо использования звездочки вы можете попытаться указать происхождение источника, то есть, откуда должен исходить запрос. Браузеры, такие как chrome или firefox, могут не всегда вести себя корректно, если обнаружат, что источник отсутствует MAYBE из-за различий в доменах или из-за проблем с CORS.

Когда запрос отправляется, сетевой уровень пытается найти ресурс, и здесь кажется, что непростой заголовок вызывает проблему или сбивает с толку браузер. Браузер сначала отправляет запрос OPTIONS без данных [основное первое действие для запросов, чтобы увидеть, что должно быть обслужено, и, если он найден верным, перейти к реальному запросу], чтобы подтвердить, что сервер примет запрос на подходящий ответ.

Я думаю, что Content-Type не относится ни к одному из следующих типов: application / x-www-form-urlencoded, multipart / form-data или text / plain делает запрос непростым. Подробнее об этом здесь для непростых запросов .

Кроме того, было бы хорошо проверить, отправляет ли ваша Java-программа заголовок Proxy-Authorization. Проверьте заголовки сеанса TCP, чтобы увидеть, отсутствует ли он.

Другая часть, которую я, возможно, захочу протестировать, - это прокси-шаблон отдыха. Конечно, вам может потребоваться изменить его, как требуется для работы с SSL, но ниже приведен базовый пример с учетными данными для аутентификации.

 private final RestTemplate getProxiedRestTemplate() {
    RestTemplate r = null;
    if (isProxyActivated()) {
        HttpClientBuilder client = HttpClientBuilder.create();
        HttpComponentsClientHttpRequestFactory requestFactory = new HttpComponentsClientHttpRequestFactory();
        client.setProxy(new HttpHost("your ip", 8080 //or the port you want to use}
));
        if (withAuthentication()) {
            Credentials credentials = new UsernamePasswordCredentials(getProxyUsername(), getProxyPassword());
            AuthScope authScope = new AuthScope("your ip", 8080);
            CredentialsProvider credsProvider = new BasicCredentialsProvider();
            credsProvider.setCredentials(authScope, credentials);
            client.setDefaultCredentialsProvider(credsProvider);
        }
        requestFactory.setHttpClient(client.build());
        r = new RestTemplate(requestFactory);
    } else {
        r = new RestTemplate();
    }
    return r;
}

Я надеюсь, что этот пост окажется полезным или, по крайней мере, направит вас в более подходящем направлении, всего наилучшего.

0 голосов
/ 02 июля 2019

Из того, что я заметил, некоторые программы просто показывают всплывающее окно с запросом учетных данных в таких случаях. Много раз это окно идет «за» текущим окном, в котором вы работаете, и вы даже не замечаете, что запрашиваются учетные данные. Поэтому во многих случаях вы, как человек, даже не вводите учетные данные, поскольку (к сожалению) всплывающее окно отображается «позади» текущего рабочего окна.

Итак, в следующий раз, когда вы столкнетесь с такой проблемой, быстро проверьте, есть ли какие-либо собственные всплывающие окна, которые появились за сценой, и быстро введите свои учетные данные.

Теперь, еще одна вещь, которую я видел, это то, что некоторые инструменты командной строки (например, git и т. Д.) При повторном подключении к URL должны будут проходить через прокси-сервер, и эти инструменты иногда выполняют паршивую работу по управлению учетными данными. Для этого еще одним способом является «диспетчер учетных данных», который предоставляется в Windows. Просто зайдите туда и «добавьте» URL в диспетчер учетных данных и введите учетные данные там, закройте все окна командной строки и повторите попытку. На этот раз все должно работать нормально.

Существуют «разновидности» учетных данных, одна с «Доменным именем» (обычно, если вы находитесь за корпоративным прокси-сервером).

Пример. Ваш идентификатор входа Windows в корпоративной сети может быть просто «Deepak» или «DOMAINNAME \ Deepak», поэтому попробуйте ввести их как имя пользователя в «диспетчере учетных данных Windows»

Попробуйте это, и всего наилучшего.

https://support.microsoft.com/en-us/help/4026814/windows-accessing-credential-manager

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...