0

This code is assigning the value of 'temps' to this.messages for some reason that I do not understand, any help would be appreciated. I know the issue lies within the below chunk of code as removing the .sort section changes the output order of this.messages.

this.currentMessageSubject.subscribe(()=> {
  console.log('Refreshing messages')
  if (this.conversationId) {
    firebase.firestore().collectionGroup('conv').where("parentMessageId", "==", this.conversationId).get().then(async (querySnapshot) => {
      let temps: FirebaseMessages;
      let tempsMsgs = new Map();
      temps = this.messages;
      temps.messages = []
      
      querySnapshot.forEach((newConvo) => {
        const thing = { id: newConvo.id, ...newConvo.data() } as FirebaseMessage;
  
        if (!tempsMsgs.has(thing.id)) {
          tempsMsgs.set(thing.id, thing)
          temps.messages.push(thing);
        }
        
      })
      temps.messages.sort(function(a,b){
        return a.timestamp.seconds - b.timestamp.seconds;
      });
      temps.messages = temps.messages.filter((message) => {
        if (message.id) {
          return true;
        }
        
        return false;
      })
    })
  }
})
Jakob B
  • 19
  • 1

2 Answers2

1

If you assign a non-primitive value to a variable (i.e. object), it will be passed by reference.

So, in your case this line:

temps = this.messages;

assigns the same object that is in your this.messages to your temps variable. So, editing temps will actually edit the this.messages as well, since both are pointing to the same object.

You will have to clone your object, and assign the clone to your temps variable. Regarding cloning - there are multiple good answers about cloning object on SO, so I will not cover that here since we don't know the structure of the messages.

TotallyNewb
  • 3,884
  • 1
  • 11
  • 16
0

When doing temps = this.messages;, the reference is passed to temps.

You need to clone this object in another way (notice the change line 7) :

this.currentMessageSubject.subscribe(()=> {
  console.log('Refreshing messages')
  if (this.conversationId) {
    firebase.firestore().collectionGroup('conv').where("parentMessageId", "==", this.conversationId).get().then(async (querySnapshot) => {
      let temps: FirebaseMessages;
      let tempsMsgs = new Map();
      temps = {...this.messages};
      temps.messages = []
      
      querySnapshot.forEach((newConvo) => {
        const thing = { id: newConvo.id, ...newConvo.data() } as FirebaseMessage;
  
        if (!tempsMsgs.has(thing.id)) {
          tempsMsgs.set(thing.id, thing)
          temps.messages.push(thing);
        }
        
      })
      temps.messages.sort(function(a,b){
        return a.timestamp.seconds - b.timestamp.seconds;
      });
      temps.messages = temps.messages.filter((message) => {
        if (message.id) {
          return true;
        }
        
        return false;
      })
    })
  }
})

You can refer to this topic to learn more about this : What is the most efficient way to deep clone an object in JavaScript?

Alex Mougenet
  • 213
  • 3
  • 20