Wednesday, 12 April 2017

Firebase functions transaction. parent node or individual child nodes?

I am trying to determine if my transaction pattern is correct. as i understand, you should limit updates to child nodes, so i've tried to follow that general rule.

/functions/index.js

//not rate limited
//writes:
// - board.posts+1
// - thread.replies+1
// - thread.pages+1 if page count should change Math.ceil(thread.replies+1/POSTS_PER_PAGE)=pages
exports.newPost2 = require('./lib/new-post-2')(functions,firebase,rootRef,POSTS_PER_PAGE);

/functions/lib/new-post-2.js

module.exports = function(functions,firebase,rootRef,POSTS_PER_PAGE){

    return functions.database.ref('/posts/{forum}/{board}/{thread}/{post}').onWrite(function(event){

        // Only edit data when it is first created.
        if (event.data.previous.exists()) {
            return;
        }
        // Exit when the data is deleted.
        if (!event.data.exists()) {
            return;
        }

        var params = event.params;
        var forum = params.forum;
        var board = params.board;
        var thread = params.thread;
        var post = params.post;

        //first increment the replies node of the thread.
        rootRef.child('threads').child(forum).child(board).child(thread).child('replies').transaction(function(data) {

            return data + 1;//increment reply count for thread. 

        }).then(function(snapshot){
            //now, our snapshot should contain the updated value of replies.
            var replies = snapshot.val();

            //update the page count of the thread
            rootRef.child('threads').child(forum).child(board).child(thread).child('pages').transaction(function(data) {
                return Math.ceil(replies+1/POSTS_PER_PAGE);//replies is always +1 because OP of thread doesnt count as a reply.
            });

            //update the posts count for the board. this field is also updated by another firebase cloud function, when a thread is created
            rootRef.child('forums').child(forum).child('boards').child(board).child('posts').transaction(function(data){
                return data + 1;//increment post count for the board.
            });
        }); 

    });
};

I'm worried about possibly racing while updating page count of thread and post count of board after the initial reply field is incremented on thread. I'm wondering if there is a safer way i can restructure this to update all 3 fields within the first transaction, if its possible.



via r3wt

No comments:

Post a Comment