Rolf B: dynamische Module node

Beitrag lesen

Hallo effel,

okay. Es gibt zwei Ansätze.

Erstens: Alles, was hinter func2() passieren muss, kommt mit in die Callback-Funktion, die Du an then übergibst.

func1();
import("./func2a.js")
.then(function(modul2) {
   modul2.func2a();
   func3();
}

Nachteilig ist hier, dass Du einiges an Code doppeln müsstest. Wenn Du für func2() mehrere Varianten hast, dann kopierst Du func3() - oder vielleicht auch noch mehr Code - in jede der Callback-Funktionen.

Aber ich schrieb ja, dass then selbst ein Promise zurückgibt. Es erfüllt sich, wenn der then-Callback fertig ist. Und wenn Du Code dieser Art hast, kannst Du dieses Promise nutzen. Du kannst in jedem Zweig dieses Promise speichern - immer in der gleichen Variablem - und dann den Rest von der Erfüllung dieses Promises abhängig machen:

func1();
let func2Promise;
if (...) {
   func2Promise = 
      import("./func2a.js")
      .then(function(modula) { modula.func2a(); }
else if (...) {
   func2Promise =
      import("./func2b.js")
      .then(function(modulb) { modulb.func2b(); }
}

func2Promise.then(function() {
   func3();
}

Rein hypothetisch kannst Du, wenn Du mehrere unabhängige Codeteile hast, auch mehrere Importe auslösen, für jeden einen .then-Handler vorsehen und vom jedem then-Handler das Promise speichern. Und dann verwendest Du Promise.all(), um den Moment abzuwarten, wo sich alle diese Promises erfüllen. Grob skizziert sieht das so aus:

const thenA = 
   import("./func_a.js")
   .then(function(modulA) { modulA.funcA(); }
const thenB = 
   import("./func_b.js")
   .then(function(modulB) { return modulB.funcB(); }
const thenC = 
   import("./func_c.js")
   .then(function(modulC) { return modulC.funcC(); }

Promise.all( [ thenA, thenB, thenC ])
.then(function(ergebnis) {
   ... code, der laufen soll, wenn funcA, funcB und und funcC fertig sind
}

Du kannst in den Callback-Funktionen von then einen Wert zurückgeben. Dieser Rückgabewert ist dann der Wert des von then gelieferten Promises und wird an den Callback für DESSEN then verwendet.

Im Falle von Promise.all ist es so, dass Du ein Array von Promises übergibst und Promise.all darauf wartet, dass sich alle erfüllen. Die Ergebniswerte dieser Promises werden in einem Array gesammelt und an den then-Handler übergeben.

D.h. der then von Promise.all bekommt ein Array mit 3 Einträgen.

Index 0: Rückgabewert des then-Callbacks von Modul A. Da dort kein return steht, ist das undefined
Index 1: Rückgabewert des then-Callbacks von Modul B. Dort steht ein return, d.h. du findest auf Index 1 den Rückgabewert von funcB().
Index 2: Das gleiche, für Modul C.

In welcher Reihenfolge funcA, funcB und funcC ablaufen, weißt Du nicht. Das hängt davon ab, wie schnell die Module geladen werden konnten. Sie laufen definitiv nicht gleichzeitig, sondern nacheinander - nur die Reihenfolge ist undefiniert. Gleichzeitig erfolgt aber - soweit möglich - das Laden des Programmcodes für diese Module, denn das Betriebssystem kann sowas parallelisieren. Deshalb kann man sowas nur machen, wenn diese Funktionen voneinander unabhängig sind. Aber über das Promise.all bekommst Du einen Synchronisierungspunkt, an dem Du weißt, dass alle drei fertig sind, und kannst über den Rückgabewert des then-Callbacks auch Daten einsammeln. Dieser Rückgabewert kann ja durchaus komplex sein: ein Objekt, ein Array, ein Array aus Objekten - das kann riesig werden.

Man kann mit Promises komplexe Ablaufszenarien konstruieren. Wenn man weiß, wie die Dinger ticken...

Rolf

--
sumpsi - posui - obstruxi