Gernar
JavaScript: асинхронность

Рядом с какими функциями можно писать await

Разбор вопроса «Рядом с какими функциями можно писать await» для Frontend Developer: что проверяет интервьюер, ключевые тезисы, практические примеры и частые ошибки.

Вопрос

Рядом с какими функциями можно писать await

Профессия

Frontend Developer

Что хочет услышать интервьюер

Интервьюер хочет убедиться, что кандидат понимает связь между async/await и Promise, знает синтаксические ограничения и может привести примеры использования await в реальных сценариях.

Ключевые тезисы

  • await можно использовать только внутри функций, объявленных с async. Это ключевое правило JavaScript.
  • await работает с любыми функциями, которые возвращают Promise. Если функция не возвращает Promise, она будет автоматически обёрнута в resolved Promise.
  • Примеры: асинхронные функции (fetch, setTimeout с обёрткой в Promise), методы API, возвращающие Promise, или любые пользовательские async-функции.

Подробный ответ

Ключевое правило JavaScript гласит, что ключевое слово await можно использовать только внутри функций, объявленных с async. Это связано с тем, что await ожидает завершения Promise, и только асинхронные функции могут корректно обрабатывать такие операции. Если попытаться использовать await вне функции с async, это вызовет синтаксическую ошибку. await работает с любыми функциями, которые возвращают Promise. Если функция не возвращает Promise, она будет автоматически обёрнута в resolved Promise, что позволяет использовать await даже с синхронными функциями, хотя это не является распространённой практикой. Примеры функций, с которыми можно использовать await, включают асинхронные операции, такие как fetch, setTimeout (с обёрткой в Promise), методы API, возвращающие Promise, или любые пользовательские async-функции. Использование await внутри цикла возможно, но это может повлиять на производительность, особенно если операции выполняются последовательно. Для оптимизации можно использовать методы, такие как Promise.all, для параллельного выполнения асинхронных задач. Ошибки при использовании await обрабатываются с помощью блоков try/catch, что позволяет корректно обрабатывать исключения в асинхронном коде.

Практические примеры

Пример 1

Пример использования await с функцией fetch:

async function fetchData() {
  try {
    const response = await fetch('https://api.example.com/data');
    const data = await response.json();
    console.log(data);
  } catch (error) {
    console.error('Ошибка при загрузке данных:', error);
  }
}

Пример 2

Пример использования await внутри цикла:

async function processArray(array) {
  for (const item of array) {
    const result = await someAsyncFunction(item);
    console.log(result);
  }
}

Пример 3

Пример использования await с Promise.all для параллельного выполнения задач:

async function processMultipleTasks(tasks) {
  const results = await Promise.all(tasks.map(task => someAsyncFunction(task)));
  console.log(results);
}

Частые ошибки

  • Использование await вне функции с async, что приводит к синтаксической ошибке.
  • Неиспользование try/catch для обработки ошибок, что может привести к незамеченным исключениям в асинхронном коде.
  • Использование await внутри цикла без учёта влияния на производительность, что может замедлить выполнение кода.

Связанные темы

  • Promise и его методы (then, catch, finally)
  • Асинхронные функции и ключевое слово async
  • Обработка ошибок в асинхронном коде с помощью try/catch
  • Оптимизация производительности асинхронных операций с помощью Promise.all

Follow-up вопросы

Что произойдёт, если использовать await вне async-функции?

Уровень: basic

Это вызовет синтаксическую ошибку, так как await можно использовать только внутри функций, объявленных с async.

Можно ли использовать await с функциями, которые возвращают не Promise?

Уровень: intermediate

Да, можно. Если функция возвращает не Promise, JavaScript автоматически обернёт результат в resolved Promise.

Как работает await с методами, которые возвращают Promise, например, fetch?

Уровень: intermediate

await приостанавливает выполнение кода до тех пор, пока Promise не будет разрешён (resolved или rejected). Например, await fetch() вернёт результат, когда запрос завершится.

Можно ли использовать await внутри цикла? Если да, как это повлияет на производительность?

Уровень: advanced

Да, можно, но это может привести к снижению производительности, если цикл выполняет асинхронные операции последовательно. В таких случаях лучше использовать Promise.all для параллельного выполнения.

Как обрабатываются ошибки при использовании await?

Уровень: intermediate

Ошибки можно обрабатывать с помощью try/catch. Если Promise завершится с ошибкой, выполнение перейдёт в блок catch.

Содержание