Asynchronous Handling

Asynchronous PHP

Asynchronous

Ecotone does allow for easy change endpoint to be running synchronously or asynchronously according to current running process.

In order to run Endpoint asynchronously we need to mark it as Asynchronous.

#[Asynchronous("orders")]
#[CommandHandler("order.place", "place_order_endpoint")
public function placeOrder(PlaceOrderCommand $command) : void
{
// do something with $command
}
#[Asynchronous("orders")]
#[EventHandler(endpointId: "place_order_endpoint")
public function when(OrderWasPlaced $event) : void
{
// do something with $command
}

We need to add endpointId on our endpoint's annotation, in this case in CommandHandler. Asynchronous has channel name defined as orders we need to register such channel. In order to do it, we need to use one of the Modules, that provides pollable channels. At this moment following modules with pollable channels are available:

Currently available Message Channels are integrated with great library enqueue.

Symfony
Laravel
Lite
Symfony
bin/console ecotone:list
+--------------------+
| Endpoint Names |
+--------------------+
| orders |
+--------------------+
Laravel
artisan ecotone:list
+--------------------+
| Endpoint Names |
+--------------------+
| orders |
+--------------------+
Lite
$consumers = $messagingSystem->list()

After setting up Pollable Channel we can run the endpoint:

Symfony
Laravel
Lite
Symfony
bin/console ecotone:run orders -vvv
Laravel
artisan ecotone:run orders -vvv
Lite
$messagingSystem->runAsynchronouslyRunningEndpoint("orders");

Asynchronous Class

You may put Asynchronous on the class, level so all the endpoints within a class will becomes asynchronous.

Query Handler

Query Handler endpoints are never registered as asynchronous.

Multiple Asynchronous Endpoints

Using single asynchronous channel we may register multiple endpoints. This allow for registering single asynchronous channel for whole Aggregate or group of related Command Handlers, that should be done in order.

Polling Metadata for Asynchronous

As asynchronous channel can have multiple endpoints, we can't define Polling Metadata on the specific Endpoint. That's why we need to make use of Application Context Configuration. Application Context Configurationis configuration done on PHP Level.

class Configuration
{
#[ServiceContext]
public function registerAsyncChannelPollingMetadata() : array
{
return [
PollingMetadata::create("orders")
->setErrorChannelName(self::ERROR_CHANNEL)
];
}
}

@Extension - Marks method that extends Ecotone with specific configuration. Can return object or array of configurations. Configuration can be done for specific environment.

class Configuration
{
#[Extension]
#[Environment(["test"])
public function registerAsyncChannelPollingMetadata() : array
{
return [
PollingMetadata::create("orders")
->setExecutionTimeLimitInMilliseconds(1)
->setHandledMessageLimit(1)
];
}
}

Intercepting asynchronous endpoint

All asynchronous endpoints are marked with special annotationEcotone\Messaging\Annotation\PollableEndpoint If you want to intercept all polling endpoints you should make use of annotation related point cut. Ecotone\Messaging\Annotation\PollableEndpoint