Как разрешить внешнюю асинхронную функцию из внутренней функции

Как разрешить внешнюю асинхронную функцию askIfUserIsAMinor с логическим значением, указывающим второстепенный статус пользователя (истина / ложь) после того, как пользователь ответил на приглашение диалогового окна? Например:

async function askIfUserIsAMinor() {
  let dialogButtons = [
    {
      text: "Yes",
      onPress: () => {
        // I want to return 'false' on the outer async function 
      }
    }, 
    {
      text: "No",
      onPress: () => {
        // I want to return 'true' on the outer async function 
      }
    }
  ];
  dialog.prompt("Are you above the age of 18?", dialogButtons);
}

let userIsAMinor = await askIfUserIsAMinor();
if (userIsAMinor) {
  // let user proceed
} else {
  // show something else
}

Да, есть много других способов решить эту проблему без async / await, но мой вариант использования намного сложнее, чем этот, это просто упрощенный сценарий. В ES6 это можно решить, если askIfUserIsAMinor вернет обещание и внутренние onPress функции будут вызывать resolve во внешнем обещании.


person Geoffrey Goh    schedule 24.12.2015    source источник
comment
вы используете await неправильно ... Я ожидал увидеть return await dialog.prompt(... - хотя, не зная, какой диалог или код dialog.prompt вообще выглядит, трудно сказать   -  person Jaromanda X    schedule 24.12.2015
comment
Я расширил комментарий   -  person Jaromanda X    schedule 24.12.2015
comment
Допустим, диалог подобен библиотечному методу, который показывает подсказку и при нажатии вызывает присоединенные функции к каждой кнопке. Мы не можем изменить dialog.prompt на await-способный async function.   -  person Geoffrey Goh    schedule 24.12.2015
comment
как вообще используется dialog.prompt? например, он возвращает обещание или есть параметр обратного вызова? другими словами, уберите async / await - как работает dialog.prompt?   -  person Jaromanda X    schedule 24.12.2015
comment
Полностью основан на обратном вызове, он не возвращает обещание, обратные вызовы для каждой кнопки привязаны к onPress.   -  person Geoffrey Goh    schedule 24.12.2015


Ответы (1)


Этот код на самом деле работает правильно - обещайте диалог.

function askIfUserIsAMinor() {
    return new Promise(function(resolve) {
        let dialogButtons = [{
            text: "Yes",
            onPress: () => resolve(true)
        }, {
            text: "No",
            onPress: () => resolve(false)
        }];
        dialog.prompt("Are you above the age of 18?", dialogButtons);
    });
}
async function testMinor() {
    let userIsAMinor = await askIfUserIsAMinor();
    if (userIsAMinor) {
      // let user proceed
    } else {
      // show something else
    }
}

or

async function askIfUserIsAMinor() {
    let userIsAMinor = await new Promise(function(resolve) {
        let dialogButtons = [{
            text: "Yes",
            onPress: () => resolve(true)
        }, {
            text: "No",
            onPress: () => resolve(false)
        }];
        dialog.prompt("Are you above the age of 18?", dialogButtons);
    });
    if (userIsAMinor) {
      // let user proceed
    } else {
      // show something else
    }
}
askIfUserIsAMinor();
person Jaromanda X    schedule 24.12.2015
comment
Это работает? Честно говоря, я догадался, основываясь на моем ограниченном чтении ES2016 / ES7 - все еще догоняя ES2015 / ES6 - person Jaromanda X; 24.12.2015
comment
Теоретически должно. Сейчас тестирую. Просто немного раздражает то, что ES7 async / await предполагается использовать в качестве улучшения по сравнению с обещаниями ES6, но мы должны возвращаться к обещаниям всякий раз, когда появляются более сложные сценарии, такие как эти. - person Geoffrey Goh; 24.12.2015
comment
@GeoffreyGoh - отредактировал ответ - вышеперечисленное должно работать, но, возможно, не совсем так, как вы хотите - person Jaromanda X; 24.12.2015