0

次のコードがあり、node.js を使用してターンテーブル ボットを作成しようとしています。このコードは、ユーザーが「q+」と入力したときに、それがまだキューにないこと、まだ DJ していないことを確認する必要があり、これら 2 つの要件を満たしている場合はそれらをキューに追加することを示しています。上記の最初の 2 つの基準のいずれかを満たさない場合は、ユーザーに伝え、キューに触れないでください。

私の問題は「isCurrentDJ(userId)」です。その関数を介して userId を渡すと、関数は正しい答えを返します。ただし、答えが「true」であり、 isCurrentDJ(userId) 関数内の console.log() 関数がそのことを証明している場合でも、関数は常に「false」を返します。

私は最も js に精通しているわけではないので、これは可変スコープの問題である可能性があります。しかし、私は本当に確信が持てず、何時間も苦労してきました! どんな助けでも大歓迎です。ありがとう!

// When someone speaks, listen to see if it is one of the q commands
bot.on('speak', function (data) {
var name = data.name;
var text = data.text;
var userId = data.userid;

// q+ :: Add to Queue
if (text.match(/^q\+$/)) {

  //Index is the position in the queue that this person's name is found.
  //If its not found, -1 is returned.
  var index = queue.indexOf(name);

  //Function to determine if the user is currently a DJ
    function isCurrentDJ(user_id, callback){
      bot.roomInfo(false, function (data) {
        var djList = data.room.metadata.djs;
        for (i = 0; i < djList.length; i++){
          if (djList[i] == user_id){
            console.log('recognized as a DJ'); //Consistently printed!
            callback(true);
          }
        }
        callback(false);
      });
    }


  isCurrentDJ(userId, function(isDJ) {
    //If the user is already in the queue
    if(index > -1){
      //Tell them they are already in there
      bot.speak('You are already on the list');
    } else if(isDJ){
      //Otherwise if they are already a DJ tell them that
      bot.speak('You are already a DJ, '+name);
    }else{
      //Otherise if they are not in the queue add user to end of queue
      queue.push(name);
      //Tell them about it and the updated q
      bot.speak(name+' has been added to queue.');
    }
  });

}
4

2 に答える 2

1

あなたの問題は、それbot.roomInfoが非同期関数であることです。

呼び出すと、すぐに返されますが、currDJまだ false です。しばらくすると、コールバック ( function(data) {...) が呼び出されます。node.js の API のほとんどは非同期であるため、コードがブロックされることはありません。

コードを書き直す方法は次のとおりです。

// When someone speaks, listen to see if it is one of the q commands
bot.on('speak', function (data) {
   var name = data.name;
   var text = data.text;
   var userId = data.userid;

   // q+ :: Add to Queue
  if (text.match(/^q\+$/)) {

  //Index is the position in the queue that this person's name is found.
  //If its not found, -1 is returned.
  var index = queue.indexOf(name);

  //Function to determine if the user is currently a DJ
    function testCurrentDJ(user_id, cb){

      bot.roomInfo(false, function (data) {
        var djList = data.room.metadata.djs;
        for (i = 0; i < djList.length; i++){
          if (djList[i] == user_id){
            console.log('recognized as a DJ'); //Consistently printed!
            return cb(true);
          }
        }

        cb(false);
      });
    }

  //If the user is already in the queue
  if(index > -1){
    //Tell them they are already in there
    bot.speak('You are already on the list');
    return;
  }

  testCurrentDJ(userId, function(isDJ) {
      //Otherwise if they are already a DJ tell them that
      if(isDJ) {
        bot.speak('You are already a DJ, '+name);
      } else {
       //Otherise if they are not in the queue add user to end of queue
       queue.push(name);
       //Tell them about it and the updated q
       bot.speak(name+' has been added to queue. Is Current DJ? '+isDJ);
  }

    })
}

基本的な考え方を示すためにコードを更新しました。node.js の API では、通常、コールバックの最初の引数はエラー オブジェクトであり、すべてがうまくいった場合は null になります。

于 2012-08-06T00:20:23.523 に答える
0

bot.roomInfoおそらく非同期関数ですか?その場合、の値はcurrDJtrueに設定されますが、すでに返しているため遅すぎます。currDJそのコールバックが呼び出されるまで、の値を操作することはできません。

非同期関数の概念にどの程度精通していますか?

于 2012-08-06T00:10:55.720 に答える