2017-10-24 3 views
2

Könnten Sie mir bitte helfen, Javascirpt async hell zu verstehen?JS Grunddesign, wenn ich natürlich Sync-Code habe, aber ich muss ein paar asynchrone Funktionen aufrufen

Ich denke, ich vermisse etwas Wichtiges ☹ Die Sache ist, dass js Beispiele und die meisten Antworten im Internet nur einen Teil des Codes betreffen - ein kleiner Ausschnitt. Aber Anwendungen sind viel komplizierter.

Ich werde es nicht direkt in JS schreiben, da ich mehr an dem Design und daran interessiert bin, es richtig zu schreiben.

diese Funktionen in meiner Anwendung Stellen Sie sich vor:

InsertTestData(); 
SelectDataFromDB_1(‘USERS’); 
SelectDataFromDB_2(‘USER_CARS’,’USERS’); 
FillCollections(‘USER’,’USER_CARS’); 
DoTheWork(); 
DeleteData(); 

ich für die Funktionen keine Beschreibung nicht vorsah, aber ich denke, es basiert auf Namen offensichtlich. Sie müssen in diesem gehen SPEZIFISCHE BESTELLUNG. Stellen Sie sich vor, dass ich eine Auswahl in die Datenbank ausführen muss, um BENUTZER zu erhalten, und dann muss ich eine Auswahl ausführen, um USER_CARS für diese BENUTZER zu erhalten. Also muss es wirklich in dieser Reihenfolge sein (beachte dasselbe für andere Funktionen). Die Sache ist, dass 6 mal Node/Mysql, die async ist, aber ich brauche Ergebnisse in bestimmten Reihenfolge aufrufen müssen. Wie kann ich das RICHTIG machen?

Das könnte funktionieren: /* nicht gültigen Code ich die Idee präsentieren wollen und halten Sie sie kurz */

InsertTestData(
Mysql.query(select, data, function(err,success) 
{ 
SelectDataFromDB_1(‘USERS’); -- in that asyn function I will call the next procedure 
} 
)); 

SelectDataFromDB_1 (
Mysql.query(select, data, function(err,success) 
{ 
SelectDataFromDB_2(‘USERS’); -- in that asyn function I will call the next procedure 
} 
)); 

SelectDataFromDB_2 (
Mysql.query(select, data, function(err,success) 
{ 
FillCollections (‘USERS’); -- in that asyn function I will call the next procedure 
} 
)); 

etc ..

ich es „leicht“ Kette kann aber das sieht als ein Chaos. Ich meine wirklich Chaos. Ich kann einige Scheduler/timmers verwenden, um zu planen und zu testen, ob der vorherige Vorgang abgeschlossen ist) Beide sind Chaos.

Also, was ist der richtige Weg, dies zu tun;

Danke, AZOR

+3

Das Chaos du rede eine Rückruf Hölle genannt wird, und in der Tat ist es ein schlechtes trainieren. Es gibt mehrere Möglichkeiten, dies zu lösen. Werfen Sie einen Blick auf [async/await] (https://hackernoon.com/6-reasons-why-javascripts-async-await-blows-promoes-away-tutorial-c7ec10518dd9). Es ist eine neue Syntax, die fast so aussieht, als würde man asynchronen Code schreiben, als ob es synchron wäre. –

Antwort

0

Wenn Sie eine aktuelle Version von Knoten verwenden, können Sie ES2017 die Verwendung async/await syntax Synchron aussehende Code zu haben, die wirklich asynchron ist.

Zuerst Sie eine Version von Mysql.query benötigen, die ein Versprechen gibt, die sich leicht mit util.promisify getan wird:

const util = require('util'); 
// ... 
const query = util.promisify(Mysql.query); 

Dann wickeln Sie den Code in einer async Funktion und verwenden await:

(async() => { 
    try { 
     await InsertTestData(); 
     await SelectDataFromDB_1(‘USERS’); 
     await SelectDataFromDB_2(‘USER_CARS’,’USERS’); 
     await FillCollections(‘USER’,’USER_CARS’); 
     await DoTheWork(); 
     await DeleteData(); 
    } catch (e) { 
     // Handle the fact an error occurred... 
    } 
})(); 

... wo Ihre Funktionen sind async Funktionen, zB:

async InsertTestData() { 
    await query("INSERT INTO ..."); 
} 

Beachten Sie die try/catch in der async Wrapper, ist es wichtig, Fehler zu behandeln, denn andernfalls, wenn ein Fehler auftritt, erhalten Sie eine unbehandelte Ablehnung Nachricht (und zukünftige Versionen von Node kann den Prozess gut beenden). (Warum "unbehandelte Ablehnungen"? Weil async Funktionen syntaktischer Zucker für Versprechen sind; eine async Funktion gibt ein Versprechen zurück.) Sie können tun, dass entweder mit den try/catch gezeigt, oder stellvertretenden .catch auf dem Ergebnis des Aufrufs es mit:

(async() => { 
    await InsertTestData(); 
    // ... 
})().catch(e => { 
    // Handle the fact an error occurred 
}); 
Verwandte Themen