Должен ли я вызвать XMLHttpRequest async в рамках обещания? [Дубликат]

1

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

mwe будет:

call(arg) {
    return new Promise(resolve => {
        let xhr = new XMLHttpRequest();
        xhr.open('GET', 'http://localhost:8080?' + arg.name, false);
        xhr.send();
        resolve({body: {result: xhr.responseText}});
    });
}
  • 3
    Нет, это не хорошо. Помимо некоторых специальных инструментов, JavaScript является однопоточным, и вы будете заставлять пользовательский интерфейс зависать как обычно в обещании, если вы используете синхронный XHR, так же, как если бы вы делали это в прослушивателе событий, setTimeout ,….
  • 3
    Примечание: если вы хотите ajax с поддержкой обещаний, просто используйте fetch .
Теги:
xmlhttprequest
promise

1 ответ

2
Лучший ответ

Должен ли я вызвать XMLHttpRequest async в рамках обещания?

Да, асинхронный (не синхронный).

Из-за асинхронного характера обещания я всегда предполагал, что синхронизация XMLHttpRequest - это хорошо...

Это не так по нескольким причинам:

  1. Асинхронный не такой как в другом потоке. Вы все еще блокируете основной поток пользовательского интерфейса.

  2. Функция выполнения обещания (функция, которую вы передаете new Promise) в любом случае выполняется синхронно. Таким образом, ваш call не будет возвращен, пока не завершится вызов ajax, потому что это синхронный вызов.

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

Единственное, что обещания делают асинхронными, это вызовы then, catch и, finally обработчиков. Смотрите комментарии и результаты в этом фрагменте для деталей:

// The promise executor is called *synchronously*.
// This outputs 1, 2, 3, not 1, 3, 2:
console.log(1);
new Promise(resolve => {
  console.log(2);
  resolve();
});
console.log(3);

// 'then', 'catch', and 'inally' handlers are called asynchronously, even if
// the promise is already settled (because it would be chaotic to call them
// synchronously *sometimes* [because the promise is already settled when you
// call 'then'/'catch/'finally'] but not *other* times [because it isn't
// settled yet when you call 'then'/'catch/'finally']).
// This outputs A, B, C, not A, C, B
console.log("A");
Promise.resolve().then(() => console.log("C"));
console.log("B");

Не делайте синхронный AJAX, просто нет веских причин для 2019 года.


Примечание: если вы хотите ajax с поддержкой обещаний, используйте fetch.

  • 0
    Хорошо, это имеет смысл, я сделаю это тогда. Я постараюсь выяснить, fetch часть. Поскольку я должен вернуть обещание, я могу кормить API.
  • 0
    @magu_ - fetch возвращает обещание. Вы, вероятно, захотите обернуть его, хотя, поскольку у API raw fetch есть удивительная «особенность» (это ссылка на пост об этом в моем анемичном небольшом блоге) . XMLHttpRequest также не уйдет в ближайшее время, так что вы можете просто изменить свой false на true и не беспокоиться о fetch пока что. Удачного кодирования!
Показать ещё 1 комментарий

Ещё вопросы

Сообщество Overcoder
Наверх
Меню