2013-05-09 4 views
3

Я пытаюсь допросить, имеет ли какой-либо из клиентов в комнате определенное свойство, связанное с ними. Асинхронный характер метода socket.io get вызывает у меня проблемы. Я видел библиотеку async, которая выглядит так, как будто это может быть то, что мне нужно, но мне трудно понять, как применить это к этой ситуации.Работа с socket.io async get/set calls

Вот как я хочу, чтобы функция работала, предполагая, что get не был асинхронным;

/** 
* 
**/ 
socket.on('disconnect', function(data) { 
    socket.get('room', function(err, room) { 
    if(!roomHasProperty(room)) { 
     io.sockets.in(room).emit('status', { message: 'property-disconnect' }); 
    } 
    }); 
}); 

/** 
* 
**/ 
var roomClients = function(room) { 
    var _clients = io.sockets.clients(room); 
    return _clients; 
} 

/** 
* 
**/ 
var roomHasProperty = function(room) { 
    // get a list of clients in the room 
    var _clients = roomClients(room); 
    // build up an array of tasks to be completed 
    var tasks = []; 
    // loop through each socket in the room 
    for(key in _clients) { 
    var _socket = _clients[key]; 
    // grab the type from the sockets data store and check for a control type 
    _socket.get('type', function (err, type) { 
     // ah crap, you already went ahead without me!? 
     if(type == 'property') { 
      // found a the property type we were looking for 
      return true; 
     } 
    }); 
    } 
    // didn't find a control type 
    return false; 
} 

Есть ли лучший способ сделать это?

+0

Помимо проблемы с асинхронным доступом, я только что заметил, что возвращаю true в обратном вызове, а не в родительский метод. Дурак. –

ответ

0

Считаете ли вы использование библиотеки обещаний? Это упрощает работу с асинхронными функциями. Если вы должны были использовать Q, вы можете сделать это: (извините, я не могу проверить код прямо сейчас, но я уверен, что он должен работать практически без изменений)

var roomHasProperty = function(room) { 
    // Create the deferred object 
    var deferred = Q.defer(); 
    // get a list of clients in the room 
    var _clients = roomClients(room); 
    // array of promises to check 
    var promises = []; 

    // This function will be used to ask each client for the property 
    var checkClientProperty = function (client) { 
    var deferred = Q.defer(); 
    // grab the type from the sockets data store and check for a control type 
    client.get('type', function (err, type) { 
     // ah crap, you already went ahead without me!? 
     if(type == 'property') { 
     // found a the property type we were looking for 
     deferred.resolve(true); 
     } else { 
     // property wasn't found 
     deferred.resolve(false); 
     } 
    }); 
    return deferred.promise; 
    } 
    // loop through each socket in the room 
    for(key in _clients) { 
    promises.push(checkClientProperty(_clients[key])); 
    } 
    Q.all(promises).then(function (results) { 
    deferred.resolve(results.indexOf(true) > -1); 
    }) 
    // didn't find a control type 
    return deferred.promise; 
} 

Вы можете использовать это примерно так:

checkClientProperty(client).then(function (result) { 
    if (result) { 
    console.dir('the property was found'); 
    } else { 
    console.dir('the property was not found'); 
    } 
}); 
Смежные вопросы