#javascript #promise #es6-promise
#javascript #обещание #es6-обещание
Вопрос:
Я довольно новичок в javascript и пытаюсь преобразовать приведенный ниже код в асинхронную функцию. Насколько я понимаю, асинхронная функция всегда возвращает обещание.
// working code
export const getUser = (req: Express.Request, res: Express.Response) =>
new Promise((resolve, reject) => {
passport.authenticate('oauth-bearer', { session: false }, (err, user) => {
if (err) reject(err)
if (user) resolve(user)
else reject('Unauthorized')
})(req, res)
})
Это обещание используется с await
ключевым словом:
const user = await getUser(req, res)
Мои попытки до сих пор всегда возвращали «Функцию», а не разрешенное или отклоненное обещание:
// failing code
export const getUser = (req: Express.Request, res: Express.Response) =>
async () => {
return await passport.authenticate('oauth-bearer', { session: false }, (err, user) => {
if (err) throw err
if (user) return user
else throw 'Unauthorized'
})(req, res)
}
Спасибо, что указали, что я здесь делаю неправильно.
Комментарии:
1. Если
passport.authenticate
не возвращает обещание, значит, вы не можете.async
функции — это синтаксический сахар, связанный с обещаниями; если обещания нет, вы не можете использовать этот синтаксис.2.
passport.authenticate
действительно, это обычная функция. Но это вызывает обратный вызов. И я надеялся, что это можно было обернуть вasync
функцию. Поэтому мне не нужно использоватьnew Promise
синтаксис.3. Я не уверен, сработает ли это, но попробуйте await promisify(passport.authenticate)(… YOUR_PARAMS) и импортировать {promisify} = require(‘util’);
Ответ №1:
Вы получаете функцию вместо обещания, потому что new Promise
создает обещание немедленно, но async () => {}
создает обещание только при его вызове.
… но это наименьшая из ваших проблем.
async
функции — это инструменты для управления существующими обещаниями. Они не могут быть свободно взаимозаменяемы с конструктором promise.
passport.authenticate
не возвращает обещание, поэтому вы не можете использовать async
для управления им.
Комментарии:
1. Спасибо, первое предложение о том, когда оно было создано, многое прояснило. Так что в некотором смысле это можно сделать, но тогда с помощью IIFE. Что делает его менее читаемым. Тогда придерживайтесь значений по умолчанию.
2. IIFE не помогло бы: вы все равно не смогли бы контролировать, будет ли обещание разрешено или отклонено функцией обратного вызова, которую вы передаете
passport.authenticate
Ответ №2:
Как упоминалось выше, вы не можете использовать его здесь таким образом. Однако, в случае, если вам потребуется написать асинхронную функцию, это будет выглядеть следующим образом.
export const getUser = async (req: Express.Request, res: Express.Response) => {
return await functionThatReturnsAPromise()
}