Как я могу отклонить обещание, возвращаемое функцией async / await?
например, первоначально
foo(id: string): Promise<A> {
return new Promise((resolve, reject) => {
someAsyncPromise().then((value)=>resolve(200)).catch((err)=>reject(400))
});
}
Перевести на async / await
async foo(id: string): Promise<A> {
try{
await someAsyncPromise();
return 200;
} catch(error) {//here goes if someAsyncPromise() rejected}
return 400; //this will result in a resolved promise.
});
}
Итак, как я мог должным образом отклонить это обещание в этом случае?
Promise
конструктора антипаттерна ! Даже первый фрагмент должен был быть написанfoo(id: string): Promise<A> { return someAsyncPromise().then(()=>{ return 200; }, ()=>{ throw 400; }); }
Ответы:
Лучше всего , чтобы
throw
наError
упаковку значения, что приводит к отклоненному обещанию сError
обертыванием значения:Вы также можете просто
throw
указать значение, но тогда нет информации о трассировке стека:Либо верните отклоненное обещание с
Error
переносом значения, но это не идиоматично:(Или просто
return Promise.reject(400);
, но опять же, тогда нет никакой контекстной информации.)(В вашем случае, поскольку вы используете,
TypeScript
иfoo
значение retrn равноPromise<A>
, вы бы использовалиreturn Promise.reject<A>(400 /*or error*/);
)В
async
/await
ситуации это последнее, вероятно, немного семантическое несоответствие, но оно работает.Если вы бросаться
Error
, что играет хорошо с чем - нибудь , потребляющим своимfoo
результатом «с сawait
синтаксисом:источник
throw
это лучше, чемPromise.reject()
IMO. Лиthrow 400
это другой вопрос. В OP это отклоняет 400, и мы можем утверждать, что это должно отклонитьError
вместо этого.async
функциях нетresolve
илиreject
функции. Естьreturn
иthrow
, которые являются идиоматическими способами разрешить и отклонитьasync
обещание функции.new
делает это явным. Также обратите внимание, что вы не можете оставить это, если у вас естьError
подкласс (class MyError extends Error
), так что ...Вероятно, следует также упомянуть, что вы можете просто связать
catch()
функцию после вызова асинхронной операции, потому что внутри все еще возвращается обещание.Таким образом, вы можете избежать
try/catch
синтаксиса, если он вам не нравится.источник
async
функцию, я выбрасываю исключение, а затем ловко ловлю его,.catch()
как если бы я вернулсяPromise.reject
или вызвалreject
. Мне это нравится!await
сбои в одной программе. Если для каждогоawait
не нужны особые случаи, я не понимаю, почему вы хотели бы поймать их таким образом. Просто мне скромное мнение.await
сбой отдельно, но мне также нужно было работать с платформой на основе Promise, которая отклоняла обещания при ошибке.${host}/user/permissions/repositories_wrong_url/
, accessToken , accessTokenSecret) .catch (err => {logger.error ('Невозможно получить разрешения для репозитория', err); обратный вызов (err);})await
ключевое слово.Вы можете создать функцию- оболочку, которая принимает обещание и возвращает массив с данными, если ошибки нет, и ошибку, если произошла ошибка.
Используйте это так в ES7 и в асинхронной функции:
источник
Лучшим способом написания асинхронной функции было бы возвращение ожидающего обещания с самого начала и последующая обработка как отклонений, так и разрешений в обратном вызове обещания, а не просто выдача отклоненного обещания по ошибке. Пример:
Затем вы просто цепляете методы на возвращенном обещании:
Источник - этот урок:
https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Promise
источник
У меня есть предложение правильно обрабатывать отклонения в новом подходе, не имея нескольких блоков try-catch.
Откуда должна быть импортирована функция to.ts :
Кредиты отправляются Диме Гроссману по следующей ссылке .
источник
let [err]=
если только проверка на ошибки.Это не ответ на вопрос @TJ Краудера. Просто комментарий, отвечающий на комментарий «И на самом деле, если исключение будет преобразовано в отклонение, я не уверен, действительно ли я обеспокоен, если это ошибка. Мои причины для выдачи только ошибки, вероятно, не применимы. "
если ваш код использует
async
/await
, то все равно рекомендуется отклонятьError
вместо400
:источник
Я знаю, что это старый вопрос, но я просто наткнулся на поток, и здесь, похоже, существует связь между ошибками и отклонением, что противоречит (во многих случаях, по крайней мере) часто повторяемого совета не использовать обработку исключений для иметь дело с ожидаемыми случаями. Чтобы проиллюстрировать: если асинхронный метод пытается аутентифицировать пользователя и аутентификация не удалась, это отклонение (один из двух ожидаемых случаев), а не ошибка (например, если API аутентификации был недоступен).
Чтобы убедиться, что я не просто раскалывал волосы, я провел тест производительности трех разных подходов к этому, используя этот код:
Некоторые вещи, которые там есть, включены из-за моей неуверенности в отношении интерпретатора Javascript (мне нравится проходить только одну кроличью нору за раз); например, я включил
doSomething
функцию и назначил ее возврат,dummyValue
чтобы гарантировать, что условные блоки не будут оптимизированы.Мои результаты были:
Я знаю, что есть много случаев, когда не стоит искать небольшие оптимизации, но в более крупных системах эти вещи могут иметь большое совокупное значение, и это довольно резкое сравнение.
ТАК ... хотя я думаю, что подход принятого ответа является обоснованным в тех случаях, когда вы ожидаете обработки непредсказуемых ошибок в рамках асинхронной функции, в тех случаях, когда отклонение просто означает «вам придется пойти с планом B (или C или D…) «Я думаю, что я предпочел бы отказаться от использования пользовательского объекта ответа.
источник