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

Я пытаюсь сделать запрос и вернуть его результат обратно в основную область, но он либо возвращает undefined, либо обещание, хотя обещание уже выполнено.

const getLastMessage = fetch("/history?id="+getChatID())
  .then((response) => response.json())
  .then((messages) => {
    return messages[messages.length-1]['id']
    // returns correct result
  })

const getLastFetched = async () => {
  lastMessage = await getLastMessage
  // sets lastMessage to correct value
};

let lastMessage = getLastFetched()
console.log(lastMessage)
// undefined

Если я заставлю getLastFetched вернуть данные lastMessage, он вернет объект обещания. Я пробовал то же самое ранее, и это сработало?

0
walker 25 Ноя 2022 в 21:28
Хм, другие ответы не охватывают это? Вы просто не можете ожидать, что асинхронная операция будет каким-то образом синхронной.
 – 
Nick
25 Ноя 2022 в 21:30
2
Я уверен, что то же самое раньше не работало.
 – 
xehpuk
25 Ноя 2022 в 21:31

2 ответа

Предполагая, что вы запускаете код в асинхронном блоке, вы должны добавить await перед getLastFetched(). Кроме того, это вернет пустое обещание, потому что getLastFetched ничего не возвращает. Таким образом, даже если будет объявлено последнее сообщение, идентификатор не имеет значения, потому что во время журнала консоли он пуст. И последнее: lastMessage должен быть объявлен перед getLastFetched.

const getLastMessage = fetch("/history?id="+getChatID())
  .then((response) => response.json())
  .then((messages) => {
    return messages[messages.length-1]['id']
    // returns correct result
  })

let lastMessage;

const getLastFetched = async () => {
  lastMessage = await getLastMessage
  // sets lastMessage to correct value
};

await getLastFetched()
console.log(lastMessage)

Вот как это будет работать внутри асинхронного блока IIFE:

(async () => {
  const getLastMessage = fetch("/history?id="+getChatID())
    .then((response) => response.json())
    .then((messages) => messages[messages.length-1].id);

  let lastMessage;

  const getLastFetched = async () => {
    lastMessage = await getLastMessage
    // sets lastMessage to correct value
  };
    
  await getLastFetched()

  console.log(lastMessage);
})();
0
TwistedOwl 25 Ноя 2022 в 21:45

Вы не можете ожидать, что последнее сообщение будет ничем иным, как неопределенным по двум причинам. Эта часть не идет асинхронно, только внутри getLastFetched. И вы ничего не возвращаете в этой функции.

Я также не стал бы смешивать и сочетать await и .then. Это был бы один из способов решить эту проблему:

(async () => {
  const getLastMessage = async () => {
    const request = await fetch("/history?id="+getChatID());
    const data = request.body;
    return data[data.length-1]['id']
  };

  const getLastFetched = async () => {
    lastMessage = await getLastMessage();
    return lastMessage;
  };

  let lastMessage = await getLastFetched();
  console.log(lastMessage);
})();
0
MalwareMoon 25 Ноя 2022 в 22:06