TaskSet::joinNext

(PHP 8.6+, True Async 1.0)

public TaskSet::joinNext(): Async\Future

Gibt ein Future zurück, das mit dem Ergebnis des ersten abgeschlossenen Tasks aufgelöst wird — egal ob erfolgreich oder fehlgeschlagen. Wenn der Task mit einem Fehler abgeschlossen wurde, wird das Future mit dieser Exception abgelehnt.

Nach der Auslieferung des Ergebnisses wird der Eintrag automatisch aus dem Set entfernt, und count() verringert sich um 1.

Die verbleibenden Tasks laufen weiter.

Wenn bereits ein abgeschlossener Task existiert, wird das Future sofort aufgelöst.

Das zurückgegebene Future unterstützt ein Cancellation-Token über await(?Completable $cancellation).

Rückgabewert

Async\Future — ein zukünftiges Ergebnis des ersten abgeschlossenen Tasks. Rufen Sie ->await() auf, um den Wert zu erhalten.

Fehler

Beispiele

Beispiel #1 Sequentielle Ergebnisverarbeitung

<?php

use Async\TaskSet;

spawn(function() {
    $set = new TaskSet();

    $set->spawn(fn() => fetchUser(1));
    $set->spawn(fn() => fetchUser(2));
    $set->spawn(fn() => fetchUser(3));

    echo "vorher: count=" . $set->count() . "\n"; // 3

    $first = $set->joinNext()->await();
    echo "nach erstem: count=" . $set->count() . "\n"; // 2

    $second = $set->joinNext()->await();
    echo "nach zweitem: count=" . $set->count() . "\n"; // 1
});

Beispiel #2 Verarbeitungsschleife

<?php

use Async\TaskSet;

spawn(function() {
    $set = new TaskSet(concurrency: 5);

    foreach ($urls as $url) {
        $set->spawn(fn() => httpClient()->get($url)->getBody());
    }
    $set->seal();

    while ($set->count() > 0) {
        try {
            $body = $set->joinNext()->await();
            processResponse($body);
        } catch (\Throwable $e) {
            log("Fehler: {$e->getMessage()}");
        }
    }
});

Beispiel #3 Mit Timeout

<?php

use Async\TaskSet;

spawn(function() {
    $set = new TaskSet();

    $set->spawn(fn() => slowApi()->fetchReport());
    $set->spawn(fn() => anotherApi()->fetchStats());

    try {
        $result = $set->joinNext()->await(Async\timeout(5.0));
    } catch (Async\TimeoutException) {
        echo "Kein Task innerhalb von 5 Sekunden abgeschlossen\n";
    }
});

Siehe auch