Symfony MessageHandler 计算消息被发送的次数

Posted

技术标签:

【中文标题】Symfony MessageHandler 计算消息被发送的次数【英文标题】:Symfony MessageHandler count how many times a message has been dispatched 【发布时间】:2020-07-19 12:15:23 【问题描述】:

我正在使用 Symfony Messenger,我想在处理程序中继续发送消息,直到它被发送多次。

我怎样才能跟踪它?

到目前为止,这是我的处理程序类的代码:

class RetryTestHandler implements MessageHandlerInterface

    /**
    * @var EntityManagerInterface
    */
    private $entityManager;
    /**
     * @var MessageBusInterface
     */
    private $bus;

    public function __construct(MessageBusInterface $bus, EntityManagerInterface $entityManager)
    
        $this->entityManager = $entityManager;
        $this->bus = $bus;
    

    public function __invoke(RetryTest $message)
    
        // TODO: Keep dispatching message until it has been dispatched 10 times?
        $this->bus->dispatch(new RetryTest("This is a test!"), [
            new DelayStamp(5000)
        ]);
    


【问题讨论】:

【参考方案1】:

要将元数据添加到您的消息中,you can use stamps。

您以后可以在自己的自定义中间件中使用它。

例如对于这个自定义的StampInterface 实现类:

class LoopCount implements StampInterface 


    private int $count; 

    public function __construct($count) 
        $this->count = $count;
    

    public function getCount(): int 
        return $this->count;
     

然后create your own middleware检查这个邮票并在处理后重新发送:

class ResendingMiddleware implements MiddlewareInterface

     private $bus;

     public function __construct(MessageBusInterface $bus) 
           $this->bus = $bus;
    

    public function handle(Envelope $envelope, StackInterface $stack): Envelope
    

        $envelope = $stack->next()->handle($envelope, $stack);

        if (null !== $stamp = $envelope->last(LoopCount::class)) 
            $count = $stamp->getCount();
         else 
            return $envelope;
        

        // Stop dispatching
        if ($count > 9) 
            return $envelope;
        

        $this->bus->dispatch(new RetryTest("Dit is een test"), [
            new DelayStamp(5000),
            new LoopCount($count + 1)
        ]);

        return $envelope;
    

如果处理超过 9 次,则不做任何事情消费该消息。

您还需要将中间件添加到配置中:

framework:
    messenger:
        buses:
            messenger.bus.default:
                middleware:
                    # service ids that implement Symfony\Component\Messenger\Middleware\MiddlewareInterface
                    - 'App\Middleware\ResendingMiddleware'

我写的很匆忙,目前无法测试,但是基础应该可以帮助您朝着正确的方向前进。测试和调试,你会得到它的工作。稍后我会回来尝试看看是否缺少任何东西

【讨论】:

感谢您的帮助,但我收到 HandlerException -> 调用未定义的方法 last()。我假设我需要使用信封,因为 last() 方法属于信封? 但是你知道是什么导致了这个错误吗?是不是因为我没有消息作为__invoke方法的参数? 好的,为此编写了一个快速中间件。没有经过全面测试,抱歉;工作中的麻烦,我需要回到那个问题上。但是您应该能够使用以上内容来完成项目。如果您发现错误,请不要犹豫提出修改建议。 那么在中间件handle()方法中我只需要在count超过9的时候返回信封吗?但是返回类型是信封所以我得到一个错误:handle() 的返回值必须是信封的一个实例,没有返回,因为我只在 if 语句中返回信封(超过 9 次检查)。跨度> 我忘了在最后加上return语句。正如我所说,我写的很匆忙,没有测试它。但是在这和文档之间,您应该能够完成实施。也许今天下午我就能正常运行并测试它。

以上是关于Symfony MessageHandler 计算消息被发送的次数的主要内容,如果未能解决你的问题,请参考以下文章

NSQ vb.net MessageHandler

Senparc.Weixin.MP SDK 微信公众平台开发教程(十九):MessageHandler 的未知类型消息处理

端点没有适配器;您的端点是不是使用 @Endpoint 进行了注释,或者它是不是实现了受支持的接口,例如 MessageHandler 或 PayloadEndpoint?

如何计算按多个日期分组的行(在 Symfony 中)?

Symfony2 Doctrine 错误:无法计算使用 HAVING 子句的查询。使用输出步行器进行分页

symfony 中的子查询