Ad

If() Block Changing The Meteor Data Received

- 1 answer

OK. I am speechless. I encountered this weird behavior like two days ago and I can't really tell what is going on.

In my code I have:

character: Characters.find({
    'user._id': Meteor.userId(),
    'gameId': this.props.gameId
}).fetch(),

It is inside the getMeteorData function (I use Meteor with React), mixin [ReactMeteorData] is also present.

Now in the componentWillMount() function I have this piece of code. What I want to do is to check if there is a character inside created by this user and in this game.

componentDidMount: function() {
    console.log(this.data.character);
}

It returns [Class] with the character I was looking for. Great! So now I add this piece of code and it looks like this:

componentDidMount: function() {
    console.log(this.data.character);

    if (this.data.character.length > 0) {
        console.log('yay!');
    } else {
        console.log('nay...');
    }
}

So that's a normal, unsuspicious if(). Guess what I get from that first console.log(): []. WHY? Why is it that this if is changing what I get from my DB?!

Ad

Answer

The problem was that subscriptions were not ready when I tried to use them. What I did is rewrite the way subscriptions are made. I moved it from the router (so no subscriptions there) to the component itself. Like this:

data = {}
subs = {}

subs.something = Meteor.subscribe("something", argument);

if (subs.something.ready()) {
    data.something = Somethings.find({}).fetch();
    // the same query I use in publish method but with .fetch()
    // because otherwise Meteor throws a warning
}

This is the code that goes to the getMeteorData function. And then inside the render() I can use those subscriptions like this:

render: function() {
    return(
        <p>{this.data.something ? this.data.something.property : 'Loading...'}</p>
    );
}

And then it works perfectly fine. I had rewritten all of my components to use this way of doing things and now I have NO problems with subscriptions whatsoever. It also feels more "componentish" and "reactish" as everything including subscriptions is included in the parent component and the relevant data is being passed to children via props. No need to look for code and subscription methods in the router.

Ad
source: stackoverflow.com
Ad