2016-10-12 4 views
-1

Ich habe eine Promise, aber es funktioniert nicht so, wie ich will, weil der Async-Aufruf nicht beendet ist, wenn ich versuche, die Daten zu verwenden.Javascript Promise Anti-Muster

Ich habe here Promise ant-Muster gesucht, und ich bin sicher, das ist meine Lösung. Da ich jedoch bei Javascript schwach bin, habe ich Schwierigkeiten, ihren Vorschlag umzusetzen. Wenn jemand helfen kann, würde ich es begrüßen.

Mein Code:

private findLocalChatsWithLastMessageForChat(): Promise<Mongo.Collection<Chat>> { 
    let promise: Promise<Mongo.Collection<Chat>> = new Promise<Mongo.Collection<Chat>>(resolve => { 
     let localChatCollection: Mongo.Collection<Chat> = new Mongo.Collection<Chat>(null); 
     for (let i: number = 0; i < this.chatsStorageService.chats.length; i++) { 
     let chat: Chat = this.chatsStorageService.chats[i]; 
     let findLastMessageForChatPromise: Promise<Message> = this.chatsStorageService.findLastMessageForChat(chat); 
     findLastMessageForChatPromise.then((data) => { 
      let message: Message = data; 
      chat.lastMessage = message; 
      chat.lastMessageCreatedAt = message.createdAt; 
      localChatCollection.insert(chat); 
     }); 
     } 
     resolve(localChatCollection); 
    }); 
    return promise; 
    } 

Wie Sie sehen können, das Versprechen kehrt zur aufrufenden Funktion, bevor die this.chatsStorageService.findLastMessageForChat Versprechen fertig sind.

here Lesen, bietet diese Lösung:

function workMyCollection(arr) { 
    return q.all(arr.map(function(item) { 
     return doSomethingAsync(item); 
    }));  
} 

Aber ich weiß nicht, wie mein Typoskript Code zu ändern.

Dank

Antwort

1

Das Problem hier ist Ihre resolve(localChatCollection) die Ihre Promise Lösung wird für frühere Versprechen ohne zu warten.

Sie müssen alle Ihre Versprechen in einem Array speichern und warten sie alle vor der Auflösung.

Beachten Sie, dass ich TypeScript nicht übersetze Ich lasse Sie übersetzen, wenn ich mich in der Syntax irre.

private findLocalChatsWithLastMessageForChat(): Promise<Mongo.Collection<Chat>> { 
    let promise: Promise<Mongo.Collection<Chat>> = new Promise<Mongo.Collection<Chat>>(resolve => { 
     let localChatCollection: Mongo.Collection<Chat> = new Mongo.Collection<Chat>(null); 

     // ----------------- 
     // ARRAY OF PROMISES 
     let promises: Array<Promise> = []; 
     // ----------------- 

     for (let i: number = 0; i < this.chatsStorageService.chats.length; i++) { 
     let chat: Chat = this.chatsStorageService.chats[i]; 
     let findLastMessageForChatPromise: Promise<Message> = this.chatsStorageService.findLastMessageForChat(chat); 

     // ----------------- 
     // PUSH ALL YOUR PROMISES IN promises ARRAY 
     promises.push(findLastMessageForChatPromise); 
     // ----------------- 

     // Binding 'chat' in order to don't loose it. 
     findLastMessageForChatPromise.then(function (_chat, data) { 
      let message: Message = data; 
      _chat.lastMessage = message; 
      _chat.lastMessageCreatedAt = message.createdAt; 
      localChatCollection.insert(_chat); 
     }.bind(null, chat)); 
     } 

     // ----------------- 
     // WAIT FOR ALL PROMISES BEFORE RESOLVING 
     Promise.all(promises).then(function() {resolve(localChatCollection);}); 
     // ----------------- 

    }); 
    return promise; 
    } 
+0

Vielen Dank. Ich werde es versuchen – Richard

+0

Brummen es wird ein Problem mit Ihrer 'chat' Variable geben. Ich werde meine Antwort aktualisieren –

+0

getan;) 'Chat' wird in Ordnung sein jetzt –