2017-01-07 2 views
0

mongoose를 사용하여 mongoDB 데이터베이스의 레코드로 배열을 채우려고합니다. 기록을 채우려 할 때. 그것은 함수 밖에서 빈 배열을 보여줍니다. 아래는 코드입니다.mongoose를 사용하여 NodeJs에서 빈 배열을 반환

var saveMessageToVariable = function(){ 
    var records = []; 
    var spark_ids = []; 
    var obj = new Object(); 
    Message.find().distinct("spark_id").exec(function(err,data) { 
     data.forEach(function (id) { 
      if(id != null) 
      spark_ids.push(id); 
     }); 
     // console.log(spark_ids.length); 
     spark_ids.forEach(function(spark_id){ 
       Message.findOne({"spark_id":spark_id}).sort({"date":-1}).exec(function(err,data){ 
        obj.spark_id = data.spark_id; 
        obj.meesage = data.message; 
        obj.date = data.date; 
        obj.message_id = data._id; 
        records.push(obj); 
    }); 
     }); 


    }); 

console.log(records); 

} 

이 스크립트를 실행하면 로그에 빈 배열이 표시됩니다. 이 문제를 어떻게 해결합니까?

답변

0

그것은 비동기 호출이고 즉시 데이터가 다음 행으로 데이터베이스 제어 교대에서 가져온이므로 초기 값을 출력으로,이 같은 콜백 사용을 선호 :

function(spark_id,callback){ 
       Message.findOne({"spark_id":spark_id}).sort({"date":-1}).exec(function(err,data){ 
        obj.spark_id = data.spark_id; 
        obj.meesage = data.message; 
        obj.date = data.date; 
        obj.message_id = data._id; 
        callback(obj); 

    }); 
} 

function(obj) 
{ 
records.push(obj); 
} 

당신에게 다른 두를 이것에 대한 접근 방법 :

1) try 및 catch 블록을 사용하십시오.

2) async 및 await 키워드를 사용하십시오.

건배!

내가 moongoose과 많은 경험이없는
0

하지만 according to the docs it supports promises since Version 4.

다음이 작동합니다 :

//I assume you'll need this more often 
function notNull(value){ return value != null; } 

//returns a promise of the records-Array 
var saveMessageToVariable = function(){ 

    //returns a promise of a formated message 
    function getMessage(spark_id){ 
     return Message.findOne({ spark_id }) 
      .sort({ date: -1 }) 
      //.exec() 
      .then(formatMessage) 
    } 

    function formatMessage(msg){ 
     return { 
      spark_id: msg.spark_id, 
      message: msg.message, 
      date:  msg.date, 
      message_id: msg._id 
     } 
    } 

    return Message.find() 
     .distinct("spark_id") 
     //.exec() 
     .then(function(ids){ 
      //waits for all findOnes to complete, then returns an Array 
      return Promise.all(
       ids.filter(notNull).map(getMessage) 
      )); 
} 

이 코드 여부를 exec() 필요 어떠했는지 나는 확실하지 않다. 그걸 확인해야 해.

//usage 
saveMessageToVariable.then(function(records){ 
    console.log(records); 
}) 

btw. saveMessageToVariable은이 기능이하는 것을 전혀 반영하지 않습니다. 더 나은 이름을 선택해야합니다.

관련 문제