Firebase database called multiple times


#1

I am using Ionic3 with AngularFire2 to interact with Firebase Database.

I have the following code:

ts

createMessage(chatItem: any, messageText: string): Promise<firebase.database.ThenableReference> {
    let offsetRef: firebase.database.Reference = firebase.database().ref(".info/serverTimeOffset");
    return new Promise<firebase.database.ThenableReference>((resolve) => {
        offsetRef.on("value", (snap: firebase.database.DataSnapshot) => {
            var offset = snap.val();
            var negativeTimestamp = (new Date().getTime() + offset) * -1;

            chatItem.readByReceiver = false;
            if (chatItem && !chatItem.$key && chatItem.key) {
                chatItem.$key = chatItem.key;
            }
            this.updateChat(chatItem);

            let ref: firebase.database.ThenableReference = this.af.database.list('/message').push({
                chatId: chatItem.$key,
                memberId1: this.me.uid,
                memberId2: this.you.uid,
                username: this.me.displayName,
                message_text: messageText,
                timestamp: firebase.database.ServerValue.TIMESTAMP,
                negativtimestamp: negativeTimestamp,
                readByReceiver: false
            });
            resolve(ref);
        });
    });
}

This works fine, and writes a message to the Firebase database. However, I noticed after a message was sent, and created in the database, about 20 min later an new but identical message was created again. After placing a debug statement in the code, and waiting for it to trigger again, I noticed that the following line is causing the code to execute more than once:

offsetRef.on("value", (snap: firebase.database.DataSnapshot) => {
    // breakpoint getting executed more than once here
});

I would expect it only to be executed only once for each call to the function. offsetRef.on is behaving like an observable I think.

Question

What’s the best way to ensure that the code is only executed once?

Thank you.


#2

offsetRef.once(“value”).then((snapshot) => {
// cod will be executed once here
});