Way to order data fetched by .data() firebase

Viewed 59

I am trying to build a little website that shows all fields in a certain document. The problem is: the order of the fetched fields changes with each refresh. Is there a way to prevent that?

I fetch the data using:

const snapshot = await getDocs(collection(db, currentUser.uid))
console.log(snapshot[0].data())

^ I am using this getDocs()-system, because I need the other docs ids for another tasks in case you wonder

EDIT: Here is the structure of my database: enter image description here

In this case the snapshot[0].data() would sometimes be {field1 : "", field2 : ""} and sometimes be {field2: "", field1: ""}

1 Answers

I don't think the root problem of this cause is related to Firebase's data method. Objects in JS do not have a specific order, and therefore the entries might be printed in different orders each time you refresh a page. In order for you to show the fields in the same order each time you fetch the data, you can either use a Map or an array.

If you just want to show each field of the document to the user, you can sort the entries of the object that is returned by the data() method on a document and store it in an array:

const snapshot = await getDocs(collection(db, currentUser.uid))
const unsortedData = snapshot.docs[0].data()
const sortedData = Object.entries(unsortedData).sort(([keyA], [keyB]) => keyA.localeCompare(keyB))

If you want to keep the sweet O(1) access time for objects and want to have the fields sorted, you can create a Map from the Array. Map stores its entries sorted based on the order they were added.

const snapshot = await getDocs(collection(db, currentUser.uid))
const unsortedData = snapshot.docs[0].data()
const sortedData = Object.entries(test).sort(([keyA], [keyB]) => keyA.localeCompare(keyB))
const sortedMap = new Map(sortedData)

If you then want to render the Map again you could do:

Array.from(sortedMap).map(([key, value]) => { /* render the items here */ })
Related