mcpField
B
bitrix-events

bitrix-events

github.com/bxmaximum开发47290 次安装2 周前更新
代码仓库

关于 bitrix-events

面向 Bitrix 开发者的事件处理指南,涵盖 D7 与旧版事件的发布、注册和处理。重点说明如何根据分发方式匹配处理器签名,并管理注册与结果。

主要功能

  1. 01创建并分发 D7 事件
  2. 02生成和注册事件处理器
  3. 03区分 D7 与旧版签名
  4. 04处理事件结果与取消
  5. 05核对安装和卸载注册

适用场景

  1. 01为 Bitrix 模块添加事件
  2. 02处理旧版用户或页面事件
  3. 03检查事件处理器签名
  4. 04审查持久化事件注册

安装

复制下面的命令,在终端中运行。

$npx skills add https://github.com/bxmaximum/bitrix-framework-skills --skill bitrix-events

安装后在 Claude Code 中输入/bitrix-events确认已加载。

详细介绍

Bitrix 事件

基线:main 23.0+ · 已验证:main 26.800.0

由谁分发,决定处理器签名

分发器(在调用方中查找)示例处理器接收结果
new Event(...) + ->send()自定义事件、main:OnBeforeMailSend、ORM 表事件VERSION 2(registerEventHandler、addEventHandler):Event 对象。VERSION 1(*Compatible):...array_values($params)$event->getResults();非 EventResult 返回值会被包装为 UNDEFINED
GetModuleEvents() + ExecuteModuleEventEx()(旧版)main:OnBeforeUserAdd、OnAfterUserAdd、OnPageStart、OnEpilog、iblock:OnBeforeIBlockElementAdd原始参数,不论注册时使用哪个 VERSION——例如 array &$arFields由调用方决定
  • 旧版 OnBefore*:取消操作 = $APPLICATION->ThrowException('…'); return false;(调用方会检查 === false)。通过引用 &$arFields 修改数据;返回数组(['FIELDS' => …])会被忽略。
  • ORM 表事件 / highload 记录事件使用 Bitrix\Main\ORM\EventManager 和 ORM\EventResult::modifyFields()——参见 bitrix-orm;HL 事件名称参见 bitrix-highloadblock。

发布 D7 事件

php bitrix.php make:event PostCreated -m vendor.blog -C Post(自 main 25.900 起;更早版本需手动编写类)→ Vendor\Blog\Public\Event\Post\PostCreatedEvent(不使用 -C 时:…\Public\Event\)。生成的类不传递任何参数——请添加参数:

namespace Vendor\Blog\Public\Event\Post;

use Bitrix\Main\Event;

final class PostCreatedEvent extends Event
{
    public function __construct(public readonly int $postId, public readonly int $authorId)
    {
        parent::__construct('vendor.blog', 'PostCreated', ['postId' => $postId, 'authorId' => $authorId]);
    }
}
$event = new PostCreatedEvent($post->getId(), $post->getAuthorId());
$event->send();
foreach ($event->getResults() as $result)
{
    if ($result->getType() === \Bitrix\Main\EventResult::ERROR)
    {
        // caller decides: abort, log, collect errors
    }
}

附带原因取消:返回 new EventResult(EventResult::ERROR, ['error' => new Error('…', 'CODE')])——只有读取该结果的调用方才会处理它(邮件事件:bitrix-mail)。

处理事件

php bitrix.php make:eventhandler PostCreated --event-module=vendor.blog -m vendor.notify——name 是事件名称,-m 是处理器模块 → Vendor\Notify\Internals\Integration\Vendor\Blog\EventHandler\PostCreatedEventHandler::handle(PostCreatedEvent $event)。请为事件类添加缺失的 use。

public static function handle(PostCreatedEvent $event): EventResult
{
    $notifier = ServiceLocator::getInstance()->get(Notifier::class);
    $result = $notifier->notifyAuthor($event->authorId);

    return new EventResult($result->isSuccess() ? EventResult::SUCCESS : EventResult::ERROR, $result->getErrorMessages());
}

处理器是静态回调,绝不会由容器构建:请在处理器内部解析服务(bitrix-framework)。

注册

持久化(模块安装程序;在 DoUninstall 中使用相同参数取消注册):

EventManager::getInstance()->registerEventHandler(
    fromModuleId: 'vendor.blog',
    eventType: 'PostCreated',
    toModuleId: 'vendor.notify',
    toClass: PostCreatedEventHandler::class,
    toMethod: 'handle',
);
  • registerEventHandlerCompatible()(参数相同,VERSION 1):D7 事件随后传递 ...array_values($params),而不是 Event。对于旧版 ExecuteModuleEventEx 事件,这两种调用都会传递原始参数;按照惯例,内核会对这些事件使用 *Compatible。
  • 自 main 26.600* 起:在 install/migrations/events.php 中声明处理器(register() = VERSION 2,registerCompatible() = VERSION 1)——bitrix-modules。
  • 仅限当前请求:addEventHandler($fromModuleId, $eventType, $callback, $includeFile = false, $sort = 100)(VERSION 2)/ addEventHandlerCompatible()(VERSION 1),例如在 init.php 中调用。
  • 顺序:$sort 升序(默认 100)——这是 addEventHandler 的第 5 个参数,registerEventHandler 的第 6 个参数。
  • Event::send() 即使发生 ERROR 也会运行所有处理器,但处理器抛出异常会中止调用链,并将异常传播给调用方。

检查清单

  • 处理器签名与分发器匹配(Event 与原始 &$arFields)。
  • 每个 registerEventHandler 都必须在卸载时使用完全相同的参数调用 unRegisterEventHandler。
  • 命名参数使用内核名称(fromModuleId,而不是 fromModule)。
  • 处理器捕获并记录自身异常;繁重任务交由 Messenger(bitrix-background-jobs)处理。
  • 自定义事件放在 lib/Public/Event/ 中,处理器放在 lib/Internals/Integration/<Module>/EventHandler/ 中。

评论

支持 Markdown