2017-03-02 10 views
1

だから私はこれをやっていると思ったが、私はそうは思わない。クエリの結果をthen()の関数に渡そうとしています。私はconsole.log()の2つの機能の中から結果をログに記録しています。最初の人は結果を吐き出す必要があります。 2番目のものは私にundefinedを与えています。私は何が間違っているのか分かりません。ノードJsのpromiseでresolve()にSQLクエリの結果が渡されない

var dbConnect =() => new Promise(
     (res, rej) => { 

      var connection = mysql.createPool(Config.mariaDBCred); 

      connection.getConnection((err, connection) => { 

       if(err) return rej(err); 
       return res(connection); 

      }); 


     } 
    ); 

    var dbQuery = (connection, queryString, paramArray) => new Promise(
     (res, rej) => { 

      var sql = mysql.format(queryString, paramArray); 

      connection.query(sql, 
       (err, results, fields) => { 

        connection.release(); 

        console.log(results); //THIS DISPLAYS RESULTS FROM THE QUERY CORRECTLY 
        if(err) return rej(err); 
        return res(results, fields); 

       } 
      ); 

     } 
    ); 


    //CHECK IF EMAIL EXISTS 
    module.exports.doesEmailExist = (email, callback) => { 

     dbConnect().then(
      (connection) => { 
       dbQuery(
        connection, 
        'SELECT `id`, `password_hash` FROM `users` WHERE email = ?', 
        [email] 
       ) 
      } 
     ).then(
      (results, fields) => { 
       console.log(results); //THIS DISPLAY UNDEFINED 
       if(results.length > 0) return callback(true, results); 
       return callback(false, "Email does not exist."); 
      } 
     ).catch(
      (reason) => { 
       console.log(reason); 
       return callback(false, "Internal Error"); 
      } 
     ); 

    } 
+0

待ち時間...最初の 'then()'の中に2番目の'then() 'を入れる必要がありますか?しかし、そうであれば、どうすれば2つのキャッチを避けることができますか? – user2287474

+0

ではありませんが、これは最初の 'then'が正しく動作していないことを意味します。クエリーからバックティックを削除しようとします。'(ユーザからのID、パスワード...) ' – Taki

+0

@Takiは残念ながら動作しませんでした。 – user2287474

答えて

1

私は、以下の編集はあなたの問題をすべて解決するかどうかわからないんだけど、Promise APIに関してであなたの問題の観点から、彼らは正しい方向にあなたを導く必要があります。

最初に、dbQuery関数では、約束事の中で1つの値しか解決できないため、オブジェクトを解決します。

第2に、約束を守るには、約束を返さなければなりません。最初のthenハンドラでは、PromisedbQuerydbConnectの後)から返信していませんでした。

最後に、以前に使用された複数のパラメータではなく、単一の解決オブジェクトで処理するように2番目のthenハンドラを変更しました。以前はすべてが機能していましたが、resultsが定義されていましたが、fieldsは定義されていませんでした。このような場合は、ArrayまたはObjectを解決することをおすすめします。 es6を使用している場合は、オブジェクト/配列の非構造化が容易になります。

別のメモ。プロミスを使用している場合は、doesEmailExist関数で実装されているコールバックパターンを削除することを検討してください。より一貫性があり、特定のエラーの場合をターゲットにしない限り、catchハンドラをラップする必要はありません。思考の糧。

var dbConnect =() => new Promise(
    (res, rej) => { 

     var connection = mysql.createPool(Config.mariaDBCred); 

     connection.getConnection((err, connection) => { 

      if(err) return rej(err); 
      return res(connection); 

     }); 


    } 
); 

var dbQuery = (connection, queryString, paramArray) => new Promise(
    (res, rej) => { 

     var sql = mysql.format(queryString, paramArray); 

     connection.query(sql, 
      (err, results, fields) => { 

       connection.release(); 

       console.log(results); //THIS DISPLAYS RESULTS FROM THE QUERY CORRECTLY 
       if(err) return rej(err); 
       // return res(results, fields); NOPE, can only resolve one argu 
       return res({ results: results, fields: fields }) // resolve an object 

      } 
     ); 

    } 
); 


//CHECK IF EMAIL EXISTS 
module.exports.doesEmailExist = (email, callback) => { 

    dbConnect().then(
     (connection) => { 
      // Return the promise from `dbQuery` call 
      return dbQuery(
       connection, 
       'SELECT `id`, `password_hash` FROM `users` WHERE email = ?', 
       [email] 
      ) 
     } 
    ).then(
     (response) => { 
      // Can only resolve one argument 
      var results = response.results; 
      var fields = response.fields; 
      console.log(results); //THIS DISPLAY UNDEFINED 
      if(results.length > 0) return callback(true, results); 
      return callback(false, "Email does not exist."); 
     } 
    ).catch(
     (reason) => { 
      console.log(reason); 
      return callback(false, "Internal Error"); 
     } 
    ); 

} 
+0

この洞察には十分に感謝することはできません。私は本当に約束の概念を理解しようとしています。私は 'callback()'を取り除き、すべてをPromisesに変換したいと思っています。一度に1つのステップでそれをやります。今すぐこれを試してみよう。 – user2287474

+1

よろしくお願いします!一度あなたがそれのハングアップを取得した場合、コールバックに戻って、できない場合はイベントに戻りません!特にes7の 'async/await'機能を考慮してください。 – Nindaff

+0

それは間違いなくその問題を解決しました。どうもありがとうございます。今は、なぜdoesEmailExist()を呼び出す関数が、ユーザが存在しても実行を続ける理由を理解する必要があります。笑。 – user2287474

関連する問題