Возвращение массива, завершенного из array.push внутри foreb-базы firebase - PullRequest
0 голосов
/ 26 июня 2018

В данный момент у меня плохое время с nodejs (v6.14.0), потому что я сделал почтовый запрос, который должен выполнить некоторую работу, пока не вернет действительный ответ. Проблема в том, что я получаю пустой массив в качестве ответа (если я перезапущу запрос более одного раза, ответ будет действительным), я исследовал и должен управлять тем, как выполняются и возвращаются обещания, но я не вижу, что мне нужно чтобы сделать, потому что я вижу это немного сложнее, чем примеры, которые я нашел, мне нужен более глубокий совет или руководство, пожалуйста. Это мой код:

ru.post('/route', (request, response) => {
let rBody = request.body;
let weekDay = getDay(rBody.date);  // Return day => "Monday"
let cRef = adminDb.database().ref('/fields/');
return cRef.orderByChild('field_size').equalTo(rBody.type).once('value').then((snap) => {
    let arrResult = new Array;
    snap.forEach(fields => {
        infoField = fields.val();
        let idFi = infoField.id_fi;
        let idCen = infoField.id_cen;
        let id_rsvp = idFi + "_" + rBody.date + "_" + idCen;
        let id_rsvp2 = idFi + "_" + rBody.date + "_" + idCen + "_" + rBody.hour;
        let resRef = adminDb.database().ref('/rsvp/' + id_rsvp + '/' + id_rsvp2);
        resRef.on('value', snap => {
            if (snap.val() === null) {
                if (infoField.act === "true") {
                    let cenRef = adminDb.database().ref('/cen/' + idCen);
                    cenRef.on('value', snap => {
                        let infoCen = snap.val();
                        if (infoCen.act === "true") {
                            values = infoField.ft;
                            daySelected = weekDay;
                            dayCheck = values[daySelected];
                            hourSelected = rBody.hour;
                            hourCheck = dayCheck[hourSelected];
                            if (hourCheck !== "" && hourCheck !== "0") {
                                infoField.lat = infoCen.lat;
                                infoField.lon = infoCen.long;
                                if (rBody.lat !== undefined && rBody.long !== undefined) {
                                    infoField.dGet = true;
                                } else {
                                    infoField.dGet = false;
                                }
                                infoField.address = infoCen.address;
                                uRef = adminDb.database().ref('/users/');
                                uRef.child(rBody.userid).child('/fav/').orderByChild('id_fi').equalTo(idFi).on('value', snap => {
                                    if (snap.exists() === true) {
                                        infoField.fav = true
                                    } else {
                                        infoField.fav = false
                                    }
                                    arrResult.push(infoField); //how to get this arrResult (completed) to use on the next .then() on first try?
                                })
                            }
                        }
                    })
                }
            }
        })
    })
    return arrResult;
}).then((res) => {
    console.log("check",res);
    return response.status(200).json(res); // Fist response is [], if it a new request with the same values it works...
}).catch(err => {
    return response.status(err.status >= 100 && err.status < 600 ? err.code : 500).send(err.message);
})});

Результирующий массив должен выглядеть примерно так при первой попытке:

[{
//Values from first snapshot return (infoField) plus:
lat: infoCen.lat,
lon: infoCen.long,
dGet: true/false,
address: infoCen.address,
fav: true/false,
}]

Я получаю это только после второго запуска, сначала он остается пустым []

1 Ответ

0 голосов
/ 26 июня 2018

Я сделал некоторые изменения в вашем коде, вы не правильно обрабатываете обещания:

ru.post('/route', (request, response) => {
  let rBody = request.body;
  let weekDay = getDay(rBody.date); // Return day => "Monday"
  let cRef = adminDb.database().ref('/fields/');
  return cRef.orderByChild('field_size').equalTo(rBody.type).once('value').then((snapshot) => {
    let arrResult = [];
    snapshot.forEach(fields => {
      let infoField = fields.val();
      let idFi = infoField.id_fi;
      let idCen = infoField.id_cen;
      let id_rsvp = idFi + "_" + rBody.date + "_" + idCen;
      let id_rsvp2 = idFi + "_" + rBody.date + "_" + idCen + "_" + rBody.hour;
      let resRef = adminDb.database().ref('/rsvp/' + id_rsvp + '/' + id_rsvp2);
      return resRef.on('value', snap => {
        if (snap.val() === null) {
          if (infoField.act === "true") {
            let cenRef = adminDb.database().ref('/cen/' + idCen);
            return cenRef.on('value', snap => {
              let infoCen = snap.val();
              if (infoCen.act === "true") {
                let values = infoField.ft;
                let daySelected = weekDay;
                let dayCheck = values[daySelected];
                let hourSelected = rBody.hour;
                let hourCheck = dayCheck[hourSelected];
                if (hourCheck !== "" && hourCheck !== "0") {
                  arrResult.push(adminDb.database().ref('/fields/' + fields.key + '/lat').set(infoCen.lat));
                  arrResult.push(adminDb.database().ref('/fields/' + fields.key + '/lon').set(infoCen.long));
                  if (rBody.lat !== undefined && rBody.long !== undefined) {
                    arrResult.push(adminDb.database().ref('/fields/' + fields.key + '/dGet').set(true));
                  } else {
                    arrResult.push(adminDb.database().ref('/fields/' + fields.key + '/distanciaGet').set(false));
                  }
                  arrResult.push(adminDb.database().ref('/fields/' + fields.key + '/address').set(infoCen.address));
                  const uRef = adminDb.database().ref('/users/');
                  uRef.child(rBody.userid).child('/fav/').orderByChild('id_fi').equalTo(idFi).on('value', snap => {
                    if (snap.exists() === true) {
                      arrResult.push(adminDb.database().ref('/fields/' + fields.key + '/fav').set(true));
                    } else {
                      arrResult.push(adminDb.database().ref('/fields/' + fields.key + '/fav').set(false));
                    }
                  });
                }
              }
            });
          }
        }
      });
    });
    return Promise.all(arrResult);
  }).then((res) => {
    console.log("check", res);
    return response.status(200).json(res); // Fist response is [], if it a new request with the same values it works...
  }).catch(err => {
    return response.status(err.status >= 100 && err.status < 600 ? err.code : 500).send(err.message);
  });
});
...