zerodahero / laravel-workflow

Use the Symfony Workflow component in Laravel
MIT License
197 stars 37 forks source link

Multiple dispatching (3 times exactly) of a same event #54

Closed babak271 closed 2 years ago

babak271 commented 2 years ago

I am facing multiple dispatching (3 times exactly) of a same event when using workflow_apply() method.

I'm using version 3.3.3 and here is the config of my workflow.

use App\Constants\UserTypes;
use App\Models\Factor;

'factor_wf'  => [
        'type'           => 'state_machine',
        'marking_store'  => [
            'type'     => 'single_state',
            'property' => 'status',
        ],
        'supports'       => [Factor::class],
        'places'         => ['open', 'submit'],
        'initial_places' => ['open'],
        'transitions'    => [
            'to_submit_by_State'   => [
                'from'     => 'open',
                'to'       => 'submit',
                'metadata' => [
                    'permission' => UserTypes::getWorkflowPermission(UserTypes::State),
                ],
            ],
    ]
]

Here is the subscriber.

use ZeroDaHero\LaravelWorkflow\Events\CompletedEvent;

class FactorWorkflowSubscriber
{
    public function onCompleted(CompletedEvent $event)
    {
        if ($event->getWorkflowName() == 'factor_wf') {
            (new HandleFactorWorkflow($event->getOriginalEvent()))->handle();
        }
    }

    public function subscribe($events)
    {
        return [
            CompletedEvent::class => 'onCompleted',
        ];
    }
}

Note that when I use workflow.completed instead of CompleteEvent namespace, it resolves and I don't get repetitive dispatching.

This issue is a continuation of this.

zerodahero commented 2 years ago

Hi, thanks for the detailed info on this! It's been a busy start of the year, but I'm hoping to take a closer look into this soon. Thanks for your patience.

prog-24 commented 2 years ago

It's not really 3 of the same events, they are actually 3 different events.

The first one is the event wrapped with the package class The second one is the event for that specific workflow The final one is the event for that specific workflow, for that specific transition. You can simply block all other events in the onGuard event or better yet, target the specific event that you want. I hope this makes sense, happy to explain more.

babak271 commented 2 years ago

It's not really 3 of the same events, they are actually 3 different events.

The first one is the event wrapped with the package class The second one is the event for that specific workflow The final one is the event for that specific workflow, for that specific transition. You can simply block all other events in the onGuard event or better yet, target the specific event that you want. I hope this makes sense, happy to explain more.

Thank you for your explanation, but still I don't understand why it behaves differently in below two subscriptions cases:

public function subscribe($events)
{
    return [
        CompletedEvent::class => 'onCompleted',
    ];
}

And

public function subscribe($events)
{
    return [
        'workflow.completed' => 'onCompleted',
    ];
}
klimenttoshkov commented 2 years ago

These are 2 different events.

On 24 Jan 2022, at 15:09, Babak @.***> wrote:

It's not really 3 of the same events, they are actually 3 different events.

The first one is the event wrapped with the package class The second one is the event for that specific workflow The final one is the event for that specific workflow, for that specific transition. You can simply block all other events in the onGuard event or better yet, target the specific event that you want. I hope this makes sense, happy to explain more.

Thank you for your explanation, but still I don't understand why it behaves differently in below two subscriptions cases:

public function subscribe($events) { return [ CompletedEvent::class => 'onCompleted', ]; } And

public function subscribe($events) { return [ 'workflow.completed' => 'onCompleted', ]; } — Reply to this email directly, view it on GitHub https://github.com/zerodahero/laravel-workflow/issues/54#issuecomment-1020083393, or unsubscribe https://github.com/notifications/unsubscribe-auth/AOIQGVPCAD4GA6BVNJ2ZZM3UXVFR7ANCNFSM5KXOTYPQ. Triage notifications on the go with GitHub Mobile for iOS https://apps.apple.com/app/apple-store/id1477376905?ct=notification-email&mt=8&pt=524675 or Android https://play.google.com/store/apps/details?id=com.github.android&referrer=utm_campaign%3Dnotification-email%26utm_medium%3Demail%26utm_source%3Dgithub. You are receiving this because you are subscribed to this thread.

zerodahero commented 2 years ago

@babak271 , yeah, we're not fully Symfony-style nor fully Laravel-style on the events here in order to preserve both types of events. The original (upstream) version of this package only emitted the Laravel-style event, which isn't nearly as flexible as the Symfony-style events are. The Laravel-style event should be dispatched once per workflow event, and the Symfony events will be dispatched as per the component. In most simple use-cases you can pick one or the other (if it's really simple, just use the Laravel event), but if you've got a more complex workflow or eventing around that, you probably want to switch entirely to Symfony events.