扩展 symfony notifier 的核心是实现自定义 transport 和 channel:先创建实现 transportinterface 的 imtransport 类处理第三方请求,再注册为 notifier.transport_factory 服务并配置 dsn;接着创建继承 abstractchannel 的 imchannel,并通过 getchannels() 或 channelpolicy 动态路由通知。

扩展 Symfony Notifier 的通知渠道,核心是实现一个自定义 Transport 和配套的 Channel,而不是改写 Notification 类或硬编码逻辑。官方推荐路径是“先有 Transport,再配 Channel”,整个过程解耦清晰、可测试、易维护。
写一个 Transport 类处理新渠道
Transport 是真正对接第三方服务的底层组件,必须实现 TransportInterface。比如你要接入某国产 IM 服务商:
- 新建类
App\Notifier\Transport\ImTransport,实现send()方法:构造 HTTP 请求、签名、处理响应、抛出TransportException(失败时) - 在
__construct()中接收必要依赖,如HttpClientInterface和凭据(建议从环境变量注入) - 重写
__toString()返回唯一标识,例如'im://default',它会用于 DSN 解析和调试命令识别
注册 Transport 并配置 DSN
Transport 写完后不会自动生效,需手动注册并暴露为可配置服务:
- 在
config/services.yaml中声明服务,并打上notifier.transport_factory标签:App\Notifier\Transport\ImTransport:tags: [{ name: notifier.transport_factory, provider: im }] - 在
config/packages/notifier.yaml的transports:下添加一行:im: 'im://default' - 确保
.env里有对应环境变量,如IM_APP_ID=xxx和IM_APP_SECRET=yyy,并在 Transport 构造中读取
绑定 Channel 并启用路由策略
有了 Transport,还需让系统知道“什么通知走这个渠道”。Channel 是逻辑层的桥梁:
- 创建
App\Notifier\Channel\ImChannel,继承AbstractChannel,只须覆盖getName()返回'im' - 在
notifier.yaml的chatter_transports:或texter_transports:中加入im(取决于你发的是聊天类还是短信类消息) - 关键一步:在
Notification::getChannels()中返回['im'],或通过ChannelPolicy动态决定——这才是可扩展的用法,避免把渠道写死在业务代码里
本地开发与测试建议
新渠道上线前,别急着调真实接口:
- 用
NullTransport替换掉你的ImTransport,验证路由是否走到正确 channel;它不发请求,只记日志 - 想看通知内容是否生成正确?换成
chatz://(需装symfony/chatz-notifier),它把通知转成数组输出到 debug toolbar - 运行
php bin/console notifier:transport:debug确认 im transport 已加载且 DSN 解析无误——这是排查静默失败最直接的方式











