从发布-订阅模式到消息队列

作者&投稿:藩珠 (若有异议请与网页底部的电邮联系)
~ 发布-订阅模式又称为观察者模式(网上也有很多说这两种模式区别,个人觉得区别不大),在发布-订阅模式中,主要是两大块。就是发布和订阅,那么发布(publish)和订阅(subscribe)之前的关联点就是主题(topic).
举个生活的例子,午餐定外卖,燕姐(broker)在外卖群里发布了两个可以点的餐馆,都城和辉记(这个可以称为主题),小明(Consumer)点了辉记的,文哥(Consumer)点了都城的(这个可以称为订阅),都城餐馆(producer)和辉记餐馆(producer)做好了饭菜就回给外卖小哥送过来(消息协议),饭菜到了燕姐那里之后,那么小明和文哥就能去燕姐那里去拿(pull),也可以燕姐送过来(push)。这就是我们生活中最常见的发布-订阅模式。

从上文中可以得到,外卖群是一个载体(MQ),承载消息的存储和传送,从这里可以引出消息队列的这个概念,下面,继续说下消息队列。

MQ (Message Queue) 又称消息队列. 队列我们都知道,那什么是消息呢?消息指的是同一台机器的进程之间,或不同机器之间传输的数据。最简单的说,我们一个Rpc 请求,所带的数据就是一个消息。这就是传统的通信模式。但是这种模式有很多缺陷,例如当网络不好的时候,这种调用可能会丢失。

队列提供了一种一步通信协议,这意味着消息的发送者和接收者不需要同时于消息保持联系,发送者的消息会存储在队列中,直到接收者拿到它。 一般我们把消息的发送者称为生产者,消息的接收者称为消费者。由于生产者和消费者之间是不透明的,他们靠中间的纽带-队列来联系,那么在队列中,是消费者占主动还是生产者占主动呢,其实根据不同的获取消息的方式可以分为 pull or push 着两种。按字面上的理解,就是pull 是消费者需要自己控制去队列拉取消息,而push则是生产者占主动位置,将产生的消息push 给消费者,而这种push 可以点对点,也可以是一对多,而这种一对多的模式就是我们常说的广播模式

在分布式系统中,消息中间件是非常重要的组件,主要解决应用耦合,异步消息,流量削峰等问题。

常用的消息队列中间件有 activeMQ,RabbitMQ,ZeroMQ,Kafka,MetaMQ,RocketMQ
(可参考 https://mp.weixin.qq.com/s/ad7jibTb5nTzh3nDQYKFeg ? 觉得这篇文章写得很不错也很详细)

这次我主要写的是kafka 这个消息中间件,kafka 是采用pull 这种模式来消费信息的,生产者将消息放入队列中,而消费者可以通过epull 方法获取消息来消费,下面还是先说下kafka 的几个关键概念吧

Kafka是最初由Linkedin公司开发,是一个分布式、分区的、多副本的、多订阅者,基于zookeeper协调的分布式日志系统(也可以当做MQ系统),常见可以用于web/nginx日志、访问日志,消息服务等等,Linkedin于2010年贡献给了Apache基金会并成为顶级开源项目

主要应用场景是:日志收集系统和消息系统。

Kafka主要设计目标如下:

同时支持离线数据处理和实时数据处理。

一个典型的kafka集群中包含若干producer,若干broker,若干consumer,以及一个Zookeeper集群。Kafka通过Zookeeper管理集群配置,选举leader,以及在consumer group发生变化时进行rebalance。producer使用push模式将消息发布到broker,consumer使用pull模式从broker订阅并消费消息。

Topic & Partition

一个topic可以认为一个一类消息,每个topic将被分成多个partition,每个partition在存储层面是append log文件。

在Kafka文件存储中,同一个topic下有多个不同partition,每个partition为一个目录,partiton命名规则为topic名称+有序序号,第一个partiton序号从0开始,序号最大值为partitions数量减1

每个partion(目录)相当于一个巨型文件被平均分配到多个大小相等segment(段)数据文件中。但每个段segment file消息数量不一定相等,这种特性方便old segment file快速被删除。

每个partiton只需要支持顺序读写就行了,segment文件生命周期由服务端配置参数决定。

这样做的好处就是能快速删除无用文件,有效提高磁盘利用率。

segment file组成:由2大部分组成,分别为index file和data file,此2个文件一一对应,成对出现,后缀".index"和“.log”分别表示为segment索引文件、数据文件.

segment文件命名规则:partion全局的第一个segment从0开始,后续每个segment文件名为上一个segment文件最后一条消息的offset值。数值最大为64位long大小,19位数字字符长度,没有数字用0填充。

同一Topic的一条消息只能被同一个Consumer Group内的一个Consumer消费,但多个Consumer Group可同时消费这一消息。

这是Kafka用来实现一个Topic消息的广播(发给所有的Consumer)和单播(发给某一个Consumer)的手段。一个Topic可以对应多个Consumer Group。如果需要实现广播,只要每个Consumer有一个独立的Group就可以了。要实现单播只要所有的Consumer在同一个Group里。用Consumer Group还可以将Consumer进行自由的分组而不需要多次发送消息到不同的Topic。

参考:

http://www.linkedkeeper.com/detail/blog.action?bid=1016&hmsr=toutiao.io&utm_medium=toutiao.io&utm_source=toutiao.io


从发布-订阅模式到消息队列
发布-订阅模式又称为观察者模式(网上也有很多说这两种模式区别,个人觉得区别不大),在发布-订阅模式中,主要是两大块。就是发布和订阅,那么发布(publish)和订阅(subscribe)之前的关联点就是主题(topic).举个生活的例子,午餐定外卖,燕姐(broker)在外卖群里发布了两个可以点的餐馆,都城和辉记(...

kafka——消费者原理解析
kafka采用发布订阅模式:一对多。发布订阅模式又分两种:Kafka为这两种模型提供了单一的消费者抽象模型: 消费者组 (consumer group)。 消费者用一个消费者组名标记自己。 一个发布在Topic上消息被分发给此消费者组中的一个消费者。 假如所有的消费者都在一个组中,那么这就变成了队列模型。 假如所有...

设计模式之订阅发布模式
在现代软件开发中,订阅发布模式(Publish-Subscribe, 简称Pub\/Sub)就像一座桥梁,连接着事件驱动架构中的发布者与接收者,实现了业务逻辑的高效解耦。这种模式的优势显著,包括性能优秀、耦合度低、支持多对多通信,以及卓越的可扩展性,使得系统能够轻松应对复杂多变的业务场景。在Java的世界里,它的实现...

mitt用100行实现发布-订阅模式还收获了9k的Star
Mitt,一个轻盈的发布-订阅模式神器,以其100行精炼代码在代码世界里熠熠生辉,赢得了高达9000颗星星的热烈追捧。它巧妙地解决了对象间的多对多依赖,让状态变更的瞬间,所有订阅者都能同步接收到通知,犹如购房者瞬间掌握房源动态,售楼处信息一键传达。发布-订阅模式的魅力在于其逻辑解耦的高效性,允许信息...

观察者模式和发布-订阅模式的区别
观察者模式有一个别名叫“发布-订阅模式”,或者说是“订阅-发布模式”,订阅者和订阅目标是联系在一起的,当订阅目标发生改变时,逐个通知订阅者。【2】案例 【3】主要解决的问题 一个对象状态改变给其他对象通知的问题,而且要考虑到易用和低耦合,保证高度的协作。【4】优点 【5】缺点 【1】介绍...

观察者模式和发布订阅模式有什么不同?
观察者模式和发布订阅模式在软件设计中都是实现松耦合和可重用性的关键策略,但它们的实现方式和应用场景有所不同。让我们深入探讨这两种模式的区别。首先,观察者模式(Observer Pattern)是一种行为设计模式,它定义了对象之间的一对多依赖关系,当一个对象的状态发生改变时,所有依赖它的对象都会自动得到...

分布式消息mq的两种订阅方式
分布式消息 MQ 的两种订阅方式如下:一、点对点模式:1、场景:客户端A和客户端B使用同一队列,进行消息通讯,客户端 A 发布消息,客户端 B 接收消息。2、点对点模式包含三个角色——消息队列,发送者,接收者:发送者发送消息到消息队列中,接收者从消息队列中取出消息进行接收,消息接收后,消息队列中...

mqtt是什么
MQTT是一种基于发布\/订阅模式的消息协议。它主要用于机器对机器通信的场合,作为一种轻量级的发布\/订阅消息协议,适用于各种场景下的网络通信。其设计思想是构建一种低开销、可靠的网络协议,用于机器对机器之间的通信和数据传输。MQTT协议广泛应用于物联网的场景中,如智能家居、工业自动化等领域。它在设备...

如何采用MQTT协议实现android消息推送
该协议的特点有:使用发布\/订阅消息模式,提供一对多的消息发布,解除应用程序耦合。对负载内容屏蔽的消息传输。 使用 TCP\/IP 提供网络连接。有三种消息发布服务质量:“至多一次”,消息发布完全依赖底层 TCP\/IP 网络。会发生消息丢失或重复。这一级别可用于如下情况,环境传感器数据,丢失一次读记录无所谓,因为...

订阅发布模式的框架主要方法
订阅发布模式的框架主要方法包括:1、发布者(Publisher):负责创建事件并将其发布到事件总线(EventBus)上,以便其他订阅者(Subscriber)可以接收到事件并进行响应。2、订阅者(Subscriber):负责注册到事件总线上,以便在事件被发布时接收到事件并进行响应。3、事件(Event):表示要发布的事件,包含一些...

灵川县18685127356: redis为什么总是把订阅/发布和消息队列联系在一起 -
全颖奥铂: 首先redis的发布订阅模式不会缓存数据,就是我发布了,如果你已经可以接受了,那么你就能接收到,如果你还没有准备好那么就会错误准备好之前的数据.至于为啥为啥和消息队列联系在一起,是因为redis的发布订阅模式的实现就是通过消息队列实现的.比如多个发布端都可以发布消息,而订阅端都会接收到消息.可见中间必然有一个队列取集中发布的消息.然后把消息按序发出去

灵川县18685127356: redis怎么做消息队列 -
全颖奥铂: 有两种方法:1. Redis自带的PUB/SUB机制,即发布-订阅模式.这种模式生产者(producer)和消费者(consumer)是1-M的关系,即一条消息会被多个消费者消费,当只有一个消费者时即可以看做一个1-1的消息队列,但这种方式并不适合题...

灵川县18685127356: 消息队列的使用场景是怎样的 -
全颖奥铂: 个人认为消息队列的主要特点是异步处理,主要目的是减少请求响应时间和解耦.所以主要的使用场景就是将比较耗时而且不需要即时(同步)返回结果的操作作为消息放入消息队列.同时由于使用了消息队列,只要保证消息格式不变,消息的...

灵川县18685127356: 如何使用Jedis操作Redis消息队列 -
全颖奥铂: 代码样例如下,使用前,注意打开redis的server程序.代码样例 package RedisExample; import redis.clients.jedis.Jedis; public class TestRedis { public static void main(String[] args) { Jedis redis = new Jedis("localhost"); // SimpleExample(redis...

灵川县18685127356: 第一次用Redis做消息队列,求解答 -
全颖奥铂: 用的是订阅模式还是点对点,一般redis不建议使用前者.参考:https://davidmarquis.wordpress.com/2013/01/03/reliable-delivery-message-queues-with-redis/

灵川县18685127356: 消息服务和消息队列有何区别 -
全颖奥铂: 消息队列(Message Queue)是基于高可用分布式集群技术,搭建了包括发布订阅、接入、管理、监控报警等一套完整的高性能消息云服务.消息通知服务(Message and Notification Service)是一种高效、可靠、安全、便捷、可弹性扩展的分布式消息服务.

灵川县18685127356: java消息队列应用在哪些场景? 具体说明下 -
全颖奥铂: 对@用心阁 的实例补充.1.短信发送.2.日志记录.3.邮件发送.4.通知服务.......

灵川县18685127356: redis如何同时取出队列中的多条数据 -
全颖奥铂: public void test2Trans() { long start = System.currentTimeMillis(); Transaction tx = jedis.multi(); try{ for (int i = 0; i < 100000; i++) { tx.set("t" + i, "t" + i); } }catch(Exception e){ tx.discard(); } List results = tx.exec(); long end = System....

灵川县18685127356: 緑巨人怎么用 -
全颖奥铂: 两者不是一个范畴里的概念吧.1.callback回调,这个概念C++就有了.比如说WindowsForm程序的MainProc(),当某些事件发生时,系统调用程序的MainProc(),通知程序发生了什么事,而具体如何处理,完全由你在MainProc决定.C#...

灵川县18685127356: 怎么快速刷分 知道分数 -
全颖奥铂: 积分不能刷,可以通过下面的方法获得:在里,每天可以稳获22分:首次登录得2分经验值,每天的前10个回答,每个可以得2分经验值.还有,现在每日签到也能得到经验值.签到方法:随便打开一个问题,在右侧...

本站内容来自于网友发表,不代表本站立场,仅表示其个人看法,不对其真实性、正确性、有效性作任何的担保
相关事宜请发邮件给我们
© 星空见康网