Swoole\Coroutine::cancel

4.x is outdated, please check the latest version 22.x


Latest version: pecl install openswoole-22.1.2

Declaration

<?php Swoole\Coroutine::cancel(int $cid): bool

Parameters

cid

Coroutine ID, the coroutine ID you want to cancel/terminate. You cannot cancel the current coroutine.

Return

Returns true if the coroutine was successfully cancelled and false if there was a problem, use swoole_last_error() to see what went wrong.

Experimental feature, not recommended for production use

Description

Cancel the execution (terminate) of a coroutine based on a coroutine ID. You can get the ID of a coroutine with Coroutine::getCid(), this allows you to then cancel that coroutine but you can't cancel (terminate) the current coroutine you are in.

Coroutine cancel error codes (get with swoole_last_error()):

SWOOLE_ERROR_CO_CANNOT_CANCEL
SWOOLE_ERROR_CO_NOT_EXISTS
SWOOLE_ERROR_CO_CANCELED

You can use Swoole\Coroutine::isCanceled() to check if a coroutine has been cancelled.

Since v4.7.0


Examples

You should not cancel the current coroutine or non-existing coroutines.

<?php
use Swoole\Coroutine;
use function Swoole\Coroutine\run;

Co\run(function()
{
    assert(Coroutine::cancel(Coroutine::getCid()) === false);
    assert(swoole_last_error() === SWOOLE_ERROR_CO_CANNOT_CANCEL);

    assert(Coroutine::cancel(999) === false);
    assert(swoole_last_error() === SWOOLE_ERROR_CO_NOT_EXISTS);
});

Cancel a coroutine after Co::suspend/Co::yield

<?php
use Swoole\Coroutine;
use Swoole\Coroutine\System;
use function Swoole\Coroutine\run;
use function Swoole\Coroutine\go;

Co\run(function()
{
    $cid = Coroutine::getCid();

    go(function() use ($cid)
    {
        System::usleep(2000);
        assert(Coroutine::cancel($cid) === true);
    });

    $retval = Coroutine::suspend();
    echo "Done\n";
    assert($retval === false);
    assert(swoole_last_error() === SWOOLE_ERROR_CO_CANCELED);
});

<?php
use Swoole\Coroutine;
use Swoole\Event;
use Swoole\Coroutine\System;
use function Swoole\Coroutine\run;

Co\run(function()
{
    $cid = Coroutine::getCid();

    Event::defer(function() use ($cid)
    {
        assert(Coroutine::cancel($cid) === true);
    });

    $retval = System::gethostbyname('openswoole.com');
    echo "Done\n";
    assert($retval === false);
    assert(swoole_last_error() === SWOOLE_ERROR_AIO_CANCELED);
});

Last updated on August 31, 2022