2

for 루프에서 비동기 호출에 문제가 있습니다. 비동기 호출이 완료되기 전에 루프가 계속됩니다. 나는이 언어에 익숙하지 않고 콜백을 파악하려고 노력하고있다. 자체 호출 함수, 약속 및 제한 시간을 시도했지만 여전히 의도 한대로 작동하는 흐름을 가져올 수 없습니다.For 루프에서 비동기 호출 시퀀스 - 자바 스크립트

프로파일 객체가 메시지 배열로 푸시되기 전에 firebase에 대한 호출을 완료하고 싶습니다.

// returns the chats for that profile 
Chat.allChatsByUser(uid).$loaded() 
.then(function(data) {  
    for (var i = 0; i < data.length; i++) { 
    // self calling function for async callback handling 
    // this ensures that the async call is run for every iteration in the loop 
    (function(i) { 
     var item = data[i]; 
     // function to arrange users and chats fom newest to oldest 
     // for each matched user. item.$id = uid    
     Auth.getProfile(item.$id).$loaded() 
     .then(function(profile) { 
     // first function handles success 
     if (typeof profile === 'object') { 
       if(chat.keyOrder == 'true') { 

       // get last chat from firebase 
       // WANT THIS COMPLETE BEFORE CONTINUING      
       ref.child('chatting').child('messages').child(chat.chatId).on("value", function(data) { 
       profile.lastChat = data.child('lastMsg').val(); 
       }); 

      // pushes chatting users profile into the array 
      chat.messages.push(profile);  

     } else { 
       // invalid response 
       return $q.reject(profile); 
     } 
}, function(profile) { 
    // promise rejected 
    console.log('error', error);}); 
// i argument as closure 
})(i); 
} 

감사합니다. 실제로 두 개의 별도 일을하려는 것처럼

덕분에, 노엘

+0

당신이'chat.messages.push (프로파일)을 포함 해봤;''값 '이벤트 핸들러 내에서? – guest271314

+0

Spot on. 그것은 그것을 고쳤다. 보고 반응하는 시간을내어 주셔서 감사합니다 :-) 너무 단순하지만 몇 시간 동안 내 머리를 두 드렸습니다! –

답변

1

그래서 당신이 당신의 루프가 비동기 호출이 완료 될 때까지 계속하지하려면, 하나, 소리가 난다. 임 꽤 es6과 함께 이것을 할 멋진 방법이 있지만 es6을 사용하지 않는 것이 틀림 없습니다. 왜 루프가 기다리고 있는지 잘 모르겠다. 그래서 while 루프를 사용하여 즉석에서했습니다. 둘째로 "프로파일 객체가 메시지 배열에 푸시되기 전에 firebase에 대한 호출이 완료되기를 원합니다." 첫 번째 주석에서 언급 한대로 이벤트 핸들러 value 안에 푸시 콜을 넣으면됩니다.

// returns the chats for that profile 
Chat.allChatsByUser(uid).$loaded() 
    .then(function(data) { 
      var i = 0; 
      var inProgress = false; 
      while (i < data.length) { 
       // self calling function for async callback handling 
       // this ensures that the async call is run for every iteration in the loop 

       // wait until last iteration has completed 
       while(inProgress); 

       // the function is about to begin 
       inProgess = true; 
       (function(i) { 
         // increment i here 
         var item = data[i++]; 
         // function to arrange users and chats fom newest to oldest 
         // for each matched user. item.$id = uid    
         Auth.getProfile(item.$id).$loaded() 
          .then(function(profile) { 
            // first function handles success 
            if (typeof profile === 'object') { 
             if (chat.keyOrder == 'true') { 

              // get last chat from firebase 
              // WANT THIS COMPLETE BEFORE CONTINUING      
              ref.child('chatting').child('messages').child(chat.chatId).on("value", function(data) { 
               profile.lastChat = data.child('lastMsg').val(); 

               // wait until event 
               // pushes chatting users profile into the array 
               chat.messages.push(profile); 

               // allow next iteration to continue 
               inProgess = false; 
              }); 
             } else { 
              // invalid response 
              return $q.reject(profile); 
             } 
            }, 
            function(profile) { 
             // promise rejected END script 
             return console.log('error', error); 
            }); 
           // i argument as closure 
          })(i); 
       } 
+0

안녕 다니엘. 친구에게 답변 해 주셔서 감사합니다. 유사한 데이터 흐름을 수행 할 때이 형식을 사용하겠습니다. 순차 코딩 백그라운드에서 온 것처럼 비동기 프로그래밍에 익숙해 지려고 노력했습니다. 값 이벤트 처리기에 넣는 것이 트릭을 만들었습니다. 고마워. –

+0

문제는 없지만 대답 선택을 고려해보십시오. –

1

내가 .ALL 방법을 이런 식으로 뭔가 함께 갈 수있는 방법이라고 생각 chat.messages.push(profile) 핸들러

ref.child('chatting').child('messages').child(chat.chatId) 
.on("value", function(data) { 
    profile.lastChat = data.child('lastMsg').val(); 
    // pushes chatting users profile into the array 
    chat.messages.push(profile); 
}); 
0

value 내에 포함합니다. 예를 들면 :

function loadMeetings(city,state) { 

    return ref.child('states').child(state).child(city).once('value').then(function(snapshot) { 
    var reads = []; 
    snapshot.forEach(function(childSnapshot) { 
     var id = childSnapshot.key(); 
     var promise = ref.child('meetings').child(id).once('value').then(function(snap) { 
      return snap.val(); 
     }, function(error) { 
      // The Promise was rejected. 
      console.error(error); 
     }); 
     reads.push(promise); 
    }); 
    return Promise.all(reads); 
    }, function(error) { 
     // The Promise was rejected. 
     console.error(error); 
    }).then(function(values) { 
     //for each snapshot do something 
    }); 
} 
0

값 이벤트 핸들러 내에서 배열에 푸시 :

ref.child('chatting').child('messages').child(chat.chatId) 
.on("value", function(data) { 
    profile.lastChat = data.child('lastMsg').val(); 

    // pushes chatting users profile into the array 
    chat.messages.push(profile); 
}); 
관련 문제