事件驱动架构是计算机科学中一种高度可扩展的范例。它允许我们可以多方系统异步处理事件。

事件总线是发布/订阅模式[1]的实现,其中发布者发布数据,并且感兴趣的订阅者可以监听这些数据并基于这些数据作出处理。这使发布者与订阅者松耦合。发布者将数据事件发布到事件总线,总线负责将它们发送给订阅者。

传统的实现事件总线的方法会涉及到使用回调。订阅者通常实现接口,然后事件总线通过接口传播数据。

channelchannel

我们专注于基于主题(topic)的事件。发布者发布到主题,订阅者可以收听它们。

定义数据结构

structDataEvent

在这里,我们已经将基础数据定义为接口,这意味着它可以是任何值。我们还将主题定义为结构的成员。订阅者可能会收听多个主题,因此,我们通过主题来让订阅者可以区分不同的事件的做法是不错的。

介绍 channels

DataEventDataChannel
DataChannelSliceDataChannel

事件总线

EventBussubscribersDataChannelSlices
maptopicsmapchannel

订阅主题

channelchannel
channel

发布主题

要发布事件,发布者需要提供广播给订阅者所需要的主题和数据。

channel

请注意,我们在发布方法中使用了 Goroutine 来避免阻塞发布者

开始

EventBus

为了测试新创建的事件总线,我们将创建一个以随机间隔时间发布到指定主题的方法。

接下来,我们需要一个可以收听主题的 main 函数。它使用辅助方法打印出事件的数据。

channels
channel

示例输出将如下所示

channel
channel

完整的代码

使用 channel 取代回调的理由

传统的回调方式要求实现某种接口。

例如,

使用回调的话,如果你想订阅一个事件,你需要实现该接口,以便事件总线可以传播它。

channel

结论

本文的目的是指出编写事件总线的不同实现方法。

这可能不是理想的解决方案。

channel

我已经使用切片来存储主题的所有订阅者。这用于简化文章。这需要用 SET 替换,以至于列表中不存在重复的订阅者。

传统的回调方法可以使用提供的相同的原理去简单地实现。你可以轻松地在 Goroutine 中进行异步装饰发布事件。

文中链接

[1]

发布/订阅模式: https://en.wikipedia.org/wiki/Publish%E2%80%93subscribe_pattern

[2]

Kasun Vithanage: https://levelup.gitconnected.com/@kasvith

[3]

咔叽咔叽: https://github.com/watermelo

[4]

polaris1119: https://github.com/polaris1119

[5]

GCTT: https://github.com/studygolang/GCTT