Inside your useEffect you're calling setMessages for each child node in the results. Things will be much faster, if you only call setMessages once after processing all child nodes:

useEffect(() => {
  onValue(dbMessage, (snapshot) => {
    let data = [];
    snapshot.forEach((childSnapshot) => {
      const messageData = childSnapshot.val();
      data.push(messageData);
    });
    console.log(data);
    setMessages(data);
  });
}, []);