2012-04-11 9 views
22

¿Por qué este código muestra "0"? ¿No debería devolver "1"?Meteor: uso de la colección en el inicio del cliente

Messages = new Meteor.Collection("messages"); 

if (Meteor.is_client) { 
    Meteor.startup(function() {  
     alert(Messages.find().count()); 
    }); 
} 

if (Meteor.is_server) { 
    Meteor.startup(function() { 
     Messages.insert({text: "server says hello"}); 
    }); 
} 

Si hago el "Messages.find(). Count()", más adelante, se devuelve 1.

+2

concurrencia, bienvenido a la misma. – Raynos

+1

@Raynos No parece un problema de concurrencia. Sucede cada vez que se ejecuta el controlador de arranque del cliente. – pomber

+0

Es un problema de concurrencia, el problema es que ejecuta dos cosas al mismo tiempo una en el servidor y otra en el cliente. y usted espera que el servidor uno termine mágicamente primero – Raynos

Respuesta

37

Por defecto, cuando un cliente se pone en marcha Meteor, se conecta al servidor y suscribe documentos en cualquier Meteor.Collection que haya definido. Esto lleva tiempo, ya que siempre hay cierta demora en establecer la conexión del servidor y la recepción de documentos.

Meteor.startup() en el cliente es muy similar a $() en jQuery - ejecuta su argumento una vez que el cliente DOM está listo. Hace no espere que las colecciones de su cliente reciban todos sus documentos del servidor. Así que la forma en que escribió el código, la llamada a find() se ejecutará siempre demasiado pronto y volver 0.

Si quieres que esperar para ejecutar código hasta después de una colección primero se descarga desde el servidor, es necesario utilizar Meteor.subscribe() a suscribirse explícitamente a una colección. subscribe() toma una devolución de llamada que se ejecutará cuando el conjunto inicial de documentos esté en el cliente.

Ver:

meteor-publish y meteor-subscribe

+9

Me encantaría ver un ejemplo de código de cómo hacer esto. –

+0

Al usar 'Meteor.subscribe()' ¿tengo que desactivar de alguna manera el comportamiento predeterminado de "suscribirse a todos los documentos de una colección"? – bijan

+3

@bijan (o para otros que tengan la misma pregunta), sí, necesita eliminar el paquete de autopublish: $ meteor remover autopublish. – jtblin

0

sólo para seguir con un ejemplo de código de cómo saber cuándo una colección está listo para usar en el cliente.

Como @debergalis descrito, se debe utilizar el enfoque Meteor.subscribe - se acepta un par de devoluciones de llamada, sobre todo onReady

Por ejemplo:

if(Meteor.isClient){ 

    Meteor.subscribe("myCollection", { 

     onReady: function(){ 

      // do stuff with my collection 

     } 

    }); 

} 
Cuestiones relacionadas