Зміна тривалості очікування волейболу


191

Я використовую нову рамку Volley для Android, щоб зробити запит на свій сервер. Але це час очікування, перш ніж отримати відповідь, хоча він реагує.

Я спробував додати цей код:

HttpConnectionParams.setConnectionTimeout(httpParams, 5000);
HttpConnectionParams.setSoTimeout(httpParams, timeoutMs);

в HttpClientStackрамках Воллі з іншим цілим числом (50000), але воно все-таки закінчується до 50 секунд.

Чи є спосіб змінити час очікування на довге значення?



21
@AdamStelmaszczyk - це не буде дублікатом, оскільки йдеться про конкретні деталі в рамках Воллі. Посилання на питання SO щодо використання HttpClientкласу.
Майкл Банзон

Відповіді:


359

Див. Request.setRetryPolicy()І конструктор для DefaultRetryPolicy, напр

JsonObjectRequest myRequest = new JsonObjectRequest(Method.GET,
        url, null,
        new Response.Listener<JSONObject>() {

            @Override
            public void onResponse(JSONObject response) {
                Log.d(TAG, response.toString());
            }
        }, new Response.ErrorListener() {

            @Override
            public void onErrorResponse(VolleyError error) {
                Log.d(TAG, "Error: " + error.getMessage());
            }
});

myRequest.setRetryPolicy(new DefaultRetryPolicy(
        MY_SOCKET_TIMEOUT_MS, 
        DefaultRetryPolicy.DEFAULT_MAX_RETRIES, 
        DefaultRetryPolicy.DEFAULT_BACKOFF_MULT));

Ви також знаєте, як встановити пріоритет запиту?
Маркус

2
@Markus замінює Request.getPriority (), щоб повернути щось, крім 'нормального'. ImageRequest робить це. ПРИМІТКА. Ви повинні задавати це питання окремим запитанням про так.
larham1

1
Це саме те, що я шукав, щоб запобігти відхилення Воллі мого запиту, який займає 15 секунд. - Дякую!
слот

Я щойно додав це для запитів POST, щоб вимкнути повторний час у режимі очікування. Неймовірно неправильно, що розробники Google вирішили встановити повторну політику для запитів POST. Вирішили мою проблему. Дякую.
Proverbio

1
@ Roon13 дивіться щойно доданий конструктор зразкового запиту.
larham1

226

Для обробки Android Volley Timeout потрібно використовувати RetryPolicy

RetryPolicy

  • Volley пропонує простий спосіб реалізувати RetryPolicy для ваших запитів.
  • Volley встановлює Socket & ConnectionTImeout за замовчуванням на 5 секунд для всіх запитів.

RetryPolicy це інтерфейс, у якому вам потрібно реалізувати свою логіку того, як ви хочете повторити певний запит, коли відбудеться час очікування.

Він стосується цих трьох параметрів

  • Тайм-аут - Вказує час очікування розетки в мілісах за кожну спробу.
  • Кількість спроб - кількість спроб повторного спроби.
  • Back Off Multiplier - множник, який використовується для визначення експоненціального часу, встановленого для розетки для кожної спроби повторної спроби.

Для екс. Якщо RetryPolicy створено з цими значеннями

Час очікування - 3000 мс, кількість спроб повтору - 2, множник відключення - 2,0

Спроба 1:

  • time = time + (час * Back Multiplier);
  • час = 3000 + 6000 = 9000мс
  • Socket Timeout = час;
  • Запит відправлений із розеткою з розеткою 9 сек

Повторна спроба 2:

  • time = time + (час * Back Multiplier);
  • час = 9000 + 18000 = 27000мс
  • Socket Timeout = час;
  • Запит відправлений з розеткою з розеткою 27 сек

Отже, наприкінці спроби 2 спроби повторно, якщо все-таки відбудеться час вимкнення Socket, Воллі закине TimeoutErrorваш обробник відповіді на помилку інтерфейсу.

//Set a retry policy in case of SocketTimeout & ConnectionTimeout Exceptions. 
//Volley does retry for you if you have specified the policy.
jsonObjRequest.setRetryPolicy(new DefaultRetryPolicy(5000, 
                DefaultRetryPolicy.DEFAULT_MAX_RETRIES, 
                DefaultRetryPolicy.DEFAULT_BACKOFF_MULT));

Дякуємо за детальну відповідь про те, що RetryPolicyреально робить реалізація.
dbm

5
Приємна відповідь @Yakiv Mospan. Але у вашому прикладі час першої спроби 0 + (3000 * 2) замість 3000 + (3000 * 2). А другий 6000 + (3000 * 2).
13KZ

13 КЗ, я вважаю, що ви все ще помиляєтесь щодо розрахунків часу, дивіться мою редагування та підтверджуйте проти джерела залпу
Protongun

1
Просто нагадування для людей , що використовують це: завжди використовувати new DefaultRetryPolicy(і переконайтеся , що ніколи не використовувати повторно в RetryPolicyоб'єкт, а об'єкт посилається через весь процес запиту та збільшення повторів додають в протягом того ж значення об'єкта тайм - аут, що робить ваші майбутні інтервали часу запиту рости нескінченно
IG Pascual

як відбувається таймаут рукостискання підключення?
GMsoF

23

Просто щоб сприяти моєму підходу. Як уже відповіли, RetryPolicyце шлях. Але якщо вам потрібна політика, яка відрізняється від стандартної для всіх ваших запитів, ви можете встановити її в базовому класі запиту, тому вам не потрібно встановлювати політику для всіх примірників ваших запитів.

Щось на зразок цього:

public class BaseRequest<T> extends Request<T> {

    public BaseRequest(int method, String url, Response.ErrorListener listener) {
        super(method, url, listener);
        setRetryPolicy(getMyOwnDefaultRetryPolicy());
    }
}

У моєму випадку у мене є GsonRequest, який поширюється на цей BaseRequest, тому я не ризикую забути встановити політику для конкретного запиту, і ви все одно можете її замінити, якщо цього вимагає певний запит.


1
Це має працювати правильно? setRetryPolicy (новий DefaultRetryPolicy (1000, DefaultRetryPolicy.DEFAULT_MAX_RETRIES, DefaultRetryPolicy.DEFAULT_BACKOFF_MULT));
LOG_TAG

12
/**
 * @param request
 * @param <T>
 */
public <T> void addToRequestQueue(Request<T> request) {

    request.setRetryPolicy(new DefaultRetryPolicy(
            MY_SOCKET_TIMEOUT_MS,
            DefaultRetryPolicy.DEFAULT_MAX_RETRIES,
            DefaultRetryPolicy.DEFAULT_BACKOFF_MULT));

    getRequestQueue().add(request);
}

7
req.setRetryPolicy(new DefaultRetryPolicy(
    MY_SOCKET_TIMEOUT_MS, 
    DefaultRetryPolicy.DEFAULT_MAX_RETRIES, 
    DefaultRetryPolicy.DEFAULT_BACKOFF_MULT));

Ви можете встановити MY_SOCKET_TIMEOUT_MSяк 100. Все, що ви хочете встановити для цього, - це в мілісекундах. DEFAULT_MAX_RETRIESможе бути 0, за замовчуванням - 1.


4
int MY_SOCKET_TIMEOUT_MS=500;

 stringRequest.setRetryPolicy(new DefaultRetryPolicy(
                MY_SOCKET_TIMEOUT_MS,
                DefaultRetryPolicy.DEFAULT_MAX_RETRIES,
                DefaultRetryPolicy.DEFAULT_BACKOFF_MULT));

3

Ще один спосіб зробити це у користувацькому JsonObjectRequest:

@Override
public RetryPolicy getRetryPolicy() {
    // here you can write a custom retry policy and return it
    return super.getRetryPolicy();
}

Джерело: Приклад Android Volley


2

Альтернативне рішення, якщо всі вищезазначені рішення не працюють для вас

За замовчуванням Volley встановив тайм-аут однаково і для, setConnectionTimeout()і setReadTimeout()за значенням від RetryPolicy. У моєму випадку, Volleyвикид виключення таймауту для великих фрагментів даних див:

com.android.volley.toolbox.HurlStack.openConnection(). 

Моє рішення - створити клас, який поширюється HttpStackна мою власну setReadTimeout()політику. Потім використовуйте його, коли створюється RequestQueueтак:

Volley.newRequestQueue(mContext.getApplicationContext(), new MyHurlStack())

1

Я в кінцевому підсумку додав метод setCurrentTimeout(int timeout)до RetryPolicyі його реалізація в DefaultRetryPolicy.

Потім я додав setCurrentTimeout(int timeout)класу "Запит" і зателефонував.

Це, здається, робить свою роботу.

Вибачте за мою лінь, до речі, і ура за відкритий код.

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.