Ko-routinen

Ko-routinen sind leichtergewichtige, benutzerdefinierte Nebenläufigkeitsmechanismen, die eine Multitaskingweiterleitung innerhalb eines Prozesses ermöglichen. Sie ermöglichen den Wechsel zwischen Ko-routinen durch manuelles Steuern von Anhalten und Wiederherstellen, wodurch die Kosten für Prozesskontextwechsel vermieden werden. Workerman bietet eine allgemeine Ko-routinen-Schnittstelle, die automatisch mit den Swoole/Swow/Fiber-Treibern kompatibel ist.

Hinweis
Diese Funktion erfordert workerman>=5.1.0

Achtung

  • Ko-routinen unterstützen nur die Treiber Swoole, Swow, Fiber.
  • Bei Verwendung des Fiber-Treiber muss composer require revolt/event-loop installiert werden.
  • Der Swoole- oder Swow-Treiber kann PHP-blockierende Funktionen automatisch in Ko-routinen umwandeln, wodurch der ursprüngliche synchronisierte Code asynchron ausgeführt wird.
  • Der Fiber-Treiber kann jedoch nicht wie Swoole und Swow automatisch in Ko-routinen umgewandelt werden; wenn er auf von PHP bereitgestellte blockierende Funktionen trifft, blockiert er den gesamten Prozess und es findet kein Ko-routinenwechsel statt.
  • Wenn der Swoole, Swow oder Fiber-Treiber verwendet wird, erstellt workerman bei jeder Ausführung der Rückrufe onWorkerStart, onMessage, onConnect, onClose usw. automatisch eine Ko-routine zur Ausführung.
  • Verschiedene Ko-routinen-Treiber können verschiedenen workern mit $worker->eventLoop=xxx; zugewiesen werden.
<?php
use Workerman\Connection\TcpConnection;
use Workerman\Coroutine;
use Workerman\Events\Swoole;
use Workerman\Events\Fiber;
use Workerman\Protocols\Http\Request;
use Workerman\Worker;
require_once __DIR__ . '/vendor/autoload.php';

$worker1 = new Worker('http://0.0.0.0:8001');
$worker1->eventLoop = Swoole::class; // Verwenden Sie Swoole-Ko-routinen
$worker1->onMessage = function (TcpConnection $connection, Request $request) {
    Coroutine::create(function () {
        echo file_get_contents("http://www.example.com/event/notify");
    });
    $connection->send('ok');
};

$worker2 = new Worker('http://0.0.0.0:8001');
$worker2->eventLoop = Fiber::class; // Verwenden Sie die integrierten Fiber-Ko-routinen
$worker2->onMessage = function (TcpConnection $connection, Request $request) {
    Coroutine::create(function () {
        echo file_get_contents("http://www.example.com/event/notify");
    });
    $connection->send('ok');
};

Worker::runAll();

Schnittstelle für Ko-routinen

interface CoroutineInterface
{

    /**
     * Erstellen Sie eine Ko-routine und führen Sie sie sofort aus
     */
    public static function create(callable $callable, ...$data): CoroutineInterface;

    /**
     * Starten Sie die Ko-routine
     */
    public function start(mixed ...$args): mixed;

    /**
     * Setzen Sie die Ko-routine fort
     */
    public function resume(mixed ...$args): mixed;

    /**
     * Holen Sie sich die Ko-routine-ID
     */
    public function id(): int;

    /**
     * Setzen Sie den Rückruf zur Zerstörung der Ko-routine
     */
    public static function defer(callable $callable): void;

    /**
     * Pausieren Sie die aktuelle Ko-routine
     */
    public static function suspend(mixed $value = null): mixed;

    /**
     * Holen Sie sich die aktuelle Ko-routine
     */
    public static function getCurrent(): CoroutineInterface|Fiber|SwowCoroutine|static;

    /**
     * Überprüfen Sie, ob es sich um eine Ko-routine-Umgebung handelt
     */
    public static function isCoroutine(): bool;

}

Über Ko-routinen

Vorteile

Die größte Wirkung der Einführung von Ko-routinen in PHP besteht darin, dass asynchroner Code mit einem synchronen Ansatz geschrieben werden kann, wodurch die „Callback-Hölle“ vermieden und die Lesbarkeit sowie Wartbarkeit des Codes verbessert werden.
Ko-routinen können die Elastizität von I/O-intensiven Geschäften erheblich steigern und mit weniger Prozessen einen größeren Durchsatz bieten.

Nachteile

Die Einführung von Ko-routinen erfordert jedoch, dass Entwickler ständig auf Probleme wie globale Variablenverunreinigungen, Ressourcenwettbewerb und die Umgestaltung von Drittanbieterbibliotheken achten. Dies erhöht die Entwicklungs- und Wartungskosten und belastet das geistige Wohlbefinden erheblich.

Die Einführung von Ko-routinen bringt zusätzliche Kosten für die Erstellung, Planung, Zerstörung und den Verbindungs-Pool von Ko-routinen mit sich.
Aus umfangreichen Belastungstests zeigt sich, dass bei vollem CPU-Auslastung die maximale Leistung mit Ko-routinen im Vergleich zu blockierendem I/O um etwa 10 % - 20 % abnimmt.