bugfix> javascript > 投稿

だから私は現在これを持っています:

var item_id
try {
    item_id =
        await
            (async function () {
               // code
            })();
} catch (error) {
}

しかし、私は item_id を持つことをはるかに好むでしょう定数としてノードが私に約束の拒絶を処理することを要求するので、await値をconstに割り当てる最良の方法は何ですか

例えばエラー:

[0] (node:77118) UnhandledPromiseRejectionWarning: Unhandled promise rejection (rejection id: 1): TypeError: details[Symbol.iterator] is not a function
[0] (node:77118) [DEP0018] DeprecationWarning: Unhandled promise rejections are deprecated. In the future, promise rejections that are not handled will terminate the Node.js process with a non-zero exit code.

非同期コード

await
    (async function () {
        const query = `
            INSERT INTO item (list_id)
            SELECT 
                ?
            FROM
                list
            WHERE
                id = ?
                AND
                user_id = ?
            LIMIT 1;
        `
        const results =
            await
                doQuery({
                    inputs: [
                        list_id,
                        list_id,
                        req.session.user.id
                        // 10
                    ],
                    query,
                    error_message: "item create mysql error"
                })
        return results.insertId === 0 ? false : results.insertId
    })();

doQuery

function doQuery({ query, inputs, error_message, res = null }) {
    return (
        new Promise(function (resolve, reject) {
            db.query(query, inputs, function (err, results, fields) {
                if (err) {
                    console.trace(chalk.green(db.sql))
                    console.log()
                    handleError({ error: err, error_message, res })
                    reject(err)
                    return
                }
                resolve(results)
            })
        })
    )
}

handleError

function handleError({ error, message, res }) {
    console.trace(chalk.yellow(message))
    console.trace(chalk.red(error))
    console.log()
    if (res) {
        res.send({
            error: true,
            success: false,
        })
    }
}

回答 3 件
  • これはよく知られた問題であり、他の場所で議論されています。

    次のオプションがあります。

    item_id を宣言するだけ   let と  あなたがやったように外側のレベルで。それについて何も悪いことはありません。

    item_id でやりたいことに応じて 、 try/catch 内でそれを行う  ブロック、 const item_id; を宣言できるようにする   try の中 。

    本当に try/catch が必要であることを確認してください 。 async 内でエラーがスローされることを忘れないでください  functionは、関数によって返されるpromiseの拒否に自動的に変換されます。あなたはそれをキャッチする必要はありません(そして場合によってはそれを望んでいません)。代わりに、エラーをより高いレベルで処理します。 「約束の拒否を処理する必要がある」ノードは、それが発生した場所で処理する必要があるという意味ではありません。より高いレベルで処理できます。覚えておいてください ここでエラーを発生させると、非同期関数が「ハッピーパス」に戻り(再スローしない限り)、呼び出し元の関数はエラーが発生したことを知ることができなくなります。

    場合によっては、promiseと catch の使用に戻ると、コードが読みやすくなります。 のように

    .catch()
    
    

    または場合によっては

    const item_id_promise = async function () {}();
    item_id_promise.catch(...);
    
    

    しかし、実際にはあなたの質問は return (async function() { }()).catch(...) とは関係ありません 、 await 、または約束。それはブロック内の変数のブロックスコープについてです。この場合は async  ブロック。はい、 try  および const  ブロックスコープであり、そのため let にスコープされます  句。したがって、他のものと同様に、 try の外部で使用したい場合は  ブロックするには、それらを try の外側で宣言する必要があります  ブロック。または、 try の外でそれらを宣言したくない場合  ブロックして、それらを try の外部で使用することはできません  ブロックするので、可能であれば、その内部でのみ使用するように手配する必要があります。

  • 次のようなPromiseの機能を使用して、別のスコープで関数を定義できます。

    try
    
    

  • @torazaburoの提案に従ってください:

    async function foo(bar) {
        return new Promise((resolve, reject) => {
             if(bar === 'baz') {
                  resolve(bar); // Resolve this promise
             } else {
                  reject(); // Reject this promise
             }
        });
    }
    foo('baz').then(baz => {
        // Do something with 'baz', the result of the resolved promise
    }).catch(error => {
        // The promise is rejected, process an error here
    });
    
    
    const item_id = async function () { // code return 1337; // return your expected item id }(); item_id.catch(function (e) { console.error(e); });

あなたの答え