我研究了中断与循环轮询,并了解了不必等待轮询的中断的优点.轮询在我看来就像事件驱动编程或者至少类似于监听器,轮询的作用实际上就像听输入或输出一样.您是否同意或者我是否误解了轮询(周期性收听)和事件驱动编程(也听所谓的听众)之间的任何重要区别?
在片刻,我们设计并计划将我们的系统转换为微服务架构模式.
为了松散耦合,我们考虑使用JMS主题的事件驱动设计.这看起来很棒.但我现在不知道如何通过微服务的多个实例解决问题.对于故障转移和负载平衡,我们有每个服务的n个实例.如果事件发布到主题,则每个实例将接收并处理该事件.
可以使用数据存储中的锁定和处理状态来处理此问题.但是这个解决方案看起来非常昂贵,每个实例都有相同的工作.这对我来说不是负担.
这种模式有一些好的解决方案或最佳实践吗?
我正在尝试学习一些事件驱动编程的基础知识.因此,对于练习,我正在尝试编写一个程序,该程序读取大型二进制文件并使用它执行某些操作但不进行阻塞调用.我想出了以下内容:
var fs = require('fs');
var BUFFER_SIZE = 1024;
var path_of_file = "somefile"
fs.open(path_of_file, 'r', (error_opening_file, fd) =>
{
if (error_opening_file)
{
console.log(error_opening_file.message);
return;
}
var buffer = new Buffer(BUFFER_SIZE);
fs.read(fd, buffer, 0, BUFFER_SIZE, 0, (error_reading_file, bytesRead, buffer) =>
{
if (error_reading_file)
{
console.log(error_reading_file.message);
return;
}
// do something e.g. print or write to another file
})
})
Run Code Online (Sandbox Code Playgroud)
我知道我需要设置一个while循环以便读取完整的文件,但在上面的代码中我只读取文件的前1024个字节,并且不能制定如何在不使用阻塞循环的情况下继续读取文件.我们怎么能这样做?
我正在为我们的新后端项目考虑一些框架/编程方法。它涉及一个 BackendForFrontend 实现,它聚合下游服务。为简单起见,这些是它经过的步骤:
事件驱动编程如何比“常规”线程每请求处理更好?一些网站试图解释,通常归结为这样的:
第二种解决方案是非阻塞调用。调用者没有等待答案,而是继续执行,但提供了一个回调,一旦数据到达就会执行。
我不明白的是:我们需要一个线程/处理程序来等待这些数据,对吗?很高兴事件处理程序可以继续,但我们仍然需要(在本例中)每个请求的线程/处理程序等待每个下游请求,对吗?
考虑这个例子:下游请求需要 n 秒才能返回。在这 n 秒内,r 个请求进来。在 thread-per-request 中,我们需要 r 个线程:每个请求一个。经过 n 秒后,第一个线程完成处理并可用于新请求。
在实现事件驱动设计时,我们需要 r+1 个线程:一个事件循环和 r 个处理程序。每个处理程序接受一个请求,执行它,并在完成后调用回调。
那么这如何改进呢?
我知道基于事件与基于请求/驱动架构之间的根本区别。问题是基于请求的总是同步完成而基于事件的总是异步完成的吗?
此外,在 API 世界(请求-响应)中,如果请求消息无效,您通常会返回 400 http 代码。幸运的是,在 API 世界中,我们可以执行契约测试,使集成更加健壮。
除了将消息放入错误队列之外,在消息队列中处理此类似问题的最佳方法是什么?发布者服务或消费者服务是否有责任首先获得问题通知?
architecture messaging message-queue event-driven-design request-response
我的对象在状态发生变化时会引发StatusChanged事件 - 但是,应用程序需要根据新状态执行其他操作.
例如,如果新状态为Disconnected,则必须更新状态栏文本并发送电子邮件通知.
所以,我想创造一个枚举与可能的状态(连接,断开,ReceivingData,SendingData等),并具有与事件的EventArgs的参数发送时,复活(见下文)
定义对象:
class ModemComm
{
public event CommanderEventHandler ModemCommEvent;
public delegate void CommanderEventHandler(object source, ModemCommEventArgs e);
public void Connect()
{
ModemCommEvent(this, new ModemCommEventArgs ModemCommEventArgs.eModemCommEvent.Connected));
}
}
Run Code Online (Sandbox Code Playgroud)
定义新的EventArgs参数:
public class ModemCommEventArgs : EventArgs{
public enum eModemCommEvent
{
Idle,
Connected,
Disconnected,
SendingData,
ReceivingData
}
public eModemCommEvent eventType { get; set; }
public string eventMessage { get; set; }
public ModemCommEventArgs(eModemCommEvent eventType, string eventMessage)
{
this.eventMessage = eventMessage;
this.eventType = eventType;
}
}
Run Code Online (Sandbox Code Playgroud)
然后,我在应用程序中为事件创建一个处理程序:
ModemComm comm = new ModemComm(); …Run Code Online (Sandbox Code Playgroud) 我们的团队开始实施事件驱动设计。我们现在正在确定记录这些事件的模式的最佳工具和实践是什么。
用于此用例的常用工具有哪些?
任何链接或建议表示赞赏。
我要实现文档管理服务为业务流程层底层服务,如存储,分析,反病毒扫描等之间的编排要求是使层灵活,针对不同类型的文档,不同的流可以快速实施
的一个方法是将其建模为事件驱动系统,并使用 Apache Flink 等框架在事件上实现处理管道。
另一种思考方式是——工作流。将此设计为在 Apache Airflow 或 Uber Cadence 等工作流引擎上运行的工作流。
什么是更好的方法。
除了可追溯性(您也可以通过 Cubit 中的适当日志记录来实现)和高级事件转换(我想不出 Cubit 无法做到的任何“高级”事件转换,因为总有办法做到这一点)使用 Cubit。如果您使用干净的架构,域/数据层可以帮助进行复杂的数据操作)。
这些是我正在寻找的应该能够用 Bloc 完成的事情,因为这些事情实际上不能用 Cubit 完成。然而,这些似乎是不可能的(或者是吗?),因为在 Bloc 上添加事件需要您识别将添加事件的实际 Bloc。bloc.add(YourEvent())。
此外,事件共享有些争议,因为这可能会导致糟糕的架构/难以维护。
对于事件溯源,我无法在文档中找到这是否可能(返回到特定的过去状态?)。
我在这里错过了什么吗?
event-driven-design flutter clean-architecture bloc flutter-bloc
event-driven ×3
architecture ×2
bloc ×1
c# ×1
cloudevents ×1
enums ×1
events ×1
flutter ×1
flutter-bloc ×1
interrupt ×1
jms ×1
listener ×1
messaging ×1
node.js ×1
parameters ×1
spring ×1
spring-jms ×1
webserver ×1
workflow ×1