6 pièce(s) jointe(s)
[React/Redux/Firestore] Parcourir des collections stockées en arbre (tree)
Bonjour à tous,
J'essaie depuis plusieurs jours de parcourir ma BDD (Firestore) afin de rendre les éléments dans un Tree.
La parcours récursif dans Firestore fonctionne bien, cependant je n'arrive pas à stocker mon objet dans Redux une fois qu'il est fini d'être chargé.
Je comprends pourquoi mon rendu ne donne que le 1er niveau et pourquoi le length affiche 0 alors qu'il y a bien des objets dans la liste (lié au fait que les fonctions sont asynchrones et que la console affiche les objets en référence), mais je n'arrive pas à trouver la solution pour mettre l'objet complet c'est à dire avec toutes les sous collections dans mon store au bon moment.
Si quelqu'un à une idée, je suis preneur.
Merci
Un exemple de code parlera plus :
Un objet "play" est une feuille de l'arbre et un objet "category" est un nœud.
Ma base de données Firestore:
Pièce jointe 574276
Collection users:
Pièce jointe 574268
Sous collection plays (type = category)
Pièce jointe 574267
Sous collection plays (type = play)
Pièce jointe 574269
Fonctions de scrutation:
Code:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48
|
componentDidMount(){
// Mise à jour de l'authentification
this.authListener();
}
authListener = () => {
firebase.auth().onAuthStateChanged((user) => {
if(user){ // Si l'utilisateur est connecté
firebase.firestore().collection("users").doc(user.uid).get().then(snapshot => {
this.props.setUser(snapshot.data())
})
firebase.firestore().collection(`users/${user.uid}/plays`).onSnapshot(snapshot => { // Si l'utilisateur est connecté parcours du 1er noeud de la collection
let plays = []
snapshot.forEach(doc => {
if(doc.data().type === "play"){ // Si l'objet est "play" alors c'est une feuille de l'arbre
plays.push(doc.data())
}else if(doc.data().type === "category"){ // Si l'objet est "category" alors c'est un noeud de l'arbre
const cat = doc.data();
cat.plays = []
this.getAllPlaysForUser(cat.plays, `users/${user.uid}/plays/${doc.id}/plays`); // Récursivité avec en paramètre l'objet à mettre à jour et le path de la prochaine sous collection
plays.push(cat) // ajout du noeud au parent
}
})
console.log("plays", plays);
console.log("plays.length", plays.length);
this.props.setPlays(plays) // mise à jour du store mais n'est pas complet car les appels sont asynchrone
})
}else{
this.props.setPlays([]) // Vide le store si l'utilisateur n'est pas connecté
}
})
}
getAllPlaysForUser = (plays, path) => {
firebase.firestore().collection(path).onSnapshot(snapshot => { // Parcours des noeuds suivant
snapshot.forEach(doc => {
if(doc.data().type === "play"){ // Si l'objet est "play" alors c'est une feuille de l'arbre
plays.push(doc.data())
}else if(doc.data().type === "category"){ // Si l'objet est "category" alors c'est un noeud de l'arbre
const cat = doc.data();
cat.plays = []
this.getAllPlaysForUser(cat.plays, `${path}/${doc.id}/plays`);// Récursivité avec en paramètre l'objet à mettre à jour et le path de la prochaine sous collection
plays.push(cat) // ajout du noeud au parent
}
})
})
} |
Le résultat mais seulement du 1er niveau
Pièce jointe 574273
Mon log console lors du parcours de l'objet mis dans le store pour la construction de l'arbre:
Pièce jointe 574274