Search code examples
mongodbreactjsmeteorreact-nativeddp

React Native Meteor subscription breaks if subdocument added


Overview (Simplified)

I am running a Meteor server with a publication which is parameterised by ID:

Meteor.publish('documents.byId', function(documentId) {
  ...
  return Documents.find({documentId});
});

The Documents collection (name changed) has a SimpleScema attached to it. The schema for this document contains a field which is an array of subdocuments.

Documents.schema = new SimpleSchema({
  ...
  subdocuments: {
    label: 'Sub Documents',
    type: [SubDocumentSchema],
    defaultValue: [],
    optional: true
  }
  ...
});

Documents.attachSchema(Documents.schema);

I then have a container on the client side in the usual way with a subscription:

...
var handle = Meteor.subscribe('documents.byId', documentId);
... 
var document = Meteor.collection('documents').findOne();
...    

Problem Description

On the react-native-meteor client, the subscription data is only received properly by the client if there are no subdocuments in the array. As soon as a subdocument is added, when I try to re-subscribe from react-native, the list becomes empty. Interestingly if I already subscribed, it still notices changes to the document, but once I reload the app it can't find it any more.

On the server I have checked that the documents are found by logging, but on the client when I do Meteor.collections('documents).findOne() it is empty unless the subdocument field is empty.

On the web client for the meteor server, if I subscribe to a document by ID everything is fine, no matter how many subdocuments there are.

Question

I suspect this is either some kind of simple typo-style mistake, or an issue with react-native-meteor itself. Can anybody else recreate this? I have been stuck on it for a while - my only guess is that maybe the native version isn't happy with the schema somehow?

[Edit] Versions

React-Native version: 0.39.2

Meteor version: 1.4.2.3

[Update]

Whilst searching around and stepping through the react-meteor-native code to see what it is doing, I found that one time the data actually came back! So this is probably some kind of timing issue?

[Update 2]

If I filter out the subdocument array on the server side, the native client starts working again:

return Documents.find({documentId}, {
  fields: {'subdocuments': 0}
}

Maybe react-native-meteor doesn't like something about the subdoc format/schema...

[Update 3]

I experimentally removed the "id" field from the subdocument array and now everything is working fine. So it is a problem with having a field of type Meteor.Collection.ObjectID in the subdocument array...


Solution

  • After much experimentation, I worked out that react-native-meteor was misbehaving due to the way I was populating my _id field for the subdocument.

    Originally, I had been setting the ID to:

    var _id = new Meteor.Collection.ObjectID();
    

    But once I realised this was causing issues, I used the string version instead:

    var _id = new Meteor.Collection.ObjectID().valueOf();
    

    And now the native client is behaving. I'm not sure if this counts as a workaround or if I was doing something wrong in the first place... the field in my schema has its type set to type: Meteor.Collection.ObjectID but it seems to be happy with both the string and the object.