消息队列学习笔记(一)

Java架构之消息队列 (一):消息队列的概述 消息队列系列分享大纲:  一、消息队列的概述 二、消息队列之RabbitMQ的使用 三、消息队列之Kafka的使用 四、消息队列之RabbitMQ的原理详解 五、消息队列之Kafka的原理详解 六、消息队列之面试集锦 1.消息队列的概述 消息队列(Message Queue)中间件是分布式系统中重要的组件; 主要解决应用耦合,异步消息,流量削锋等问题; 实现... 阅读详情

1.消息队列常用场景

    消息队列最常被使用的三种场景:异步处理、流量控制和服务解耦。
    消息队列的适用范围不仅仅局限于这些场景,还有包括:作为发布 / 订阅系统实现一个微服务级系统间的观察者模式;连接流计算任务和数据;用于将消息广播给大量接收者。
    简单的说,我们在单体应用里面需要用队列解决的问题,在分布式系统中大多都可以用消息队列来解决。同时我们也要认识到,消息队列也有它自身的一些问题和局限性,包括:引入消息队列带来的延迟问题;增加了系统的复杂度;可能产生数据不一致的问题。

2.消息队列的基本标准

  • 消息的可靠传递:确保不丢消息;
  • Cluster:支持集群,确保不会因为某个节点宕机导致服务不可用,当然也不能丢消息;
  • 性能:具备足够好的性能,能满足绝大多数场景的性能要求。

3.选择消息队列

    如果说,消息队列并不是你将要构建系统的主角之一,你对消息队列功能和性能都没有很高的要求,只需要一个开箱即用易于维护的产品,使用RabbitMQ。
    如果你的系统使用消息队列主要场景是处理在线业务,比如在交易系统中用消息队列传递订单,那 RocketMQ 的低延迟和金融级的稳定性是你需要的。
    如果你需要处理海量的消息,像收集日志、监控信息或是前端的埋点这类数据,或是你的应用场景大量使用了大数据、流计算相关的开源产品,那 Kafka 是最适合你的消息队列。

4.消息丢失

一条消息从生产到消费完成这个过程,可以划分三个阶段:

  • 生产阶段: 在这个阶段,从消息在 Producer 创建出来,经过网络传输发送到 Broker 端。
  • 存储阶段: 在这个阶段,消息在Broker端存储,如果是集群,消息会在这个阶段被复制到其他的副本上。
  • 消费阶段: 在这个阶段,Consumer 从 Broker 上拉取消息,经过网络传输发送到 Consumer 上。

    在生产阶段,消息队列通过最常用的请求确认机制,来保证消息的可靠传递,正确处理返回值或者捕获异常,就可以保证这个阶段的消息不会丢失。

    存储阶段正常情况下,只要Broker在正常运行,就不会出现丢失消息的问题,但是如果 Broker出现了故障,比如进程死掉了或者服务器宕机了,还是可能会丢失消息的。如果对消息的可靠性要求非常高,可以通过配置Broker参数来避免因为宕机丢消息。

    在消费阶段,不要在收到消息后就立即发送消费确认,而是应该在执行完所有消费业务逻辑之后,再发送消费确认。

  • 在生产阶段,需要捕获消息发送的错误,并重发消息。
  • 在存储阶段,可以通过配置刷盘和复制相关的参数,让消息写入到多个副本的磁盘上,来确保消息不会因为某个 Broker 宕机或者磁盘损坏而丢失。
  • 在消费阶段,需要在处理完全部消费业务逻辑之后,再发送消费确认。

5.消息重复

幂等性:其任意多次执行所产生的影响均与一次执行的影响相同。

    实现幂等性的方法:

  1. 利用数据库的唯一约束实现幂等
  2. 为更新的数据设置前置条件
  3. 记录并检查操作

6.消息积压

1.避免消息积压

生产端性能优化:

    对于发送消息的业务逻辑,只需要注意设置合适的并发和批量大小,就可以达到很好的发送性能

消费端性能优化:
    一定要保证消费端的消费性能要高于生产端的发送性能,这样的系统才能健康的持续运行。

    消费端的性能优化除了优化消费业务逻辑以外,也可以通过水平扩容,增加消费端的并发数来提升总体的消费性能。特别需要注意的一点是,在扩容 Consumer 的实例数量的同时,必须同步扩容主题中的分区(也叫队列)数量,确保Consumer的实例数和分区数量是相等的。

2.处理消息积压

    能导致积压突然增加,最粗粒度的原因,只有两种:要么是发送变快了,要么是消费变慢了。大部分消息队列都内置了监控的功能,只要通过监控数据,很容易确定是哪种原因。
    如果是单位时间发送的消息增多,比如说是赶上大促或者抢购,短时间内不太可能优化消费端的代码来提升消费性能,唯一的方法是通过扩容消费端的实例数来提升总体的消费能力。如果短时间内没有足够的服务器资源进行扩容,没办法的办法是,将系统降级,通过关闭一些不重要的业务,减少发送方发送的数据量,最低限度让系统还能正常运转,服务一些重要业务。
    还有一种不太常见的情况,你通过监控发现,无论是发送消息的速度还是消费消息的速度和原来都没什么变化,这时候你需要检查一下你的消费端,是不是消费失败导致的一条消息反复消费这种情况比较多,这种情况也会拖慢整个系统的消费速度。
    如果监控到消费变慢了,你需要检查你的消费实例,分析一下是什么原因导致消费变慢。优先检查一下日志是否有大量的消费错误,如果没有错误的话,可以通过打印堆栈信息,看一下你的消费线程是不是卡在什么地方不动了,比如触发了死锁或者卡在等待某些资源上了。

7.消息的序列化

    要想使用网络框架的API来传输结构化的数据,必须得先实现结构化的数据与字节流之间的双向转换。这种将结构化数据转换成字节流的过程,我们称为序列化,反过来转换,就是反序列化。
    在选择序列化实现时,需要权衡这样几个因素:

  • 序列化后的数据最好是易于人类阅读的;
  • 实现的复杂度是否足够低;
  • 序列化和反序列化的速度越快越好;序列化后的信息密度越大越好,也就是说,同样的一个结构化数据,序列化之后占用的存储空间越小越好;

8.Kafka的高性能IO

1.使用批量消息提升服务端处理能力
    构建批消息和解开批消息分别在发送端和消费端的客户端完成,不仅减轻了Broker的压力,最重要的是减少了 Broker处理请求的次数,提升了总体的处理能力。
2.使用顺序读写提升磁盘 IO 性能
    顺序读写相比随机读写省去了大部分的寻址时间,它只要寻址一次,就可以连续地读写下去,所以说,性能要比随机读写要好很多。Kafka就是充分利用了磁盘的这个特性。它的存储设计非常简单,对于每个分区,它把从Producer收到的消息,顺序地写入对应的 log 文件中,一个文件写满了,就开启一个新的文件这样顺序写下去。消费的时候,也是从某个全局的位置开始,也就是某一个 log 文件中的某个位置开始,顺序地把消息读出来。
3.利用 PageCache 加速消息读写
    Kafka在读写消息文件的时候,充分利用了PageCache的特性。一般来说,消息刚刚写入到服务端就会被消费,按照LRU的“优先清除最近最少使用的页”这种策略,读取的时候,对于这种刚刚写入的PageCache,命中的几率会非常高。也就是说,大部分情况下,消费读消息都会命中 PageCache,带来的好处有两个:一个是读取的速度会非常快,另外一个是,给写入消息让出磁盘的 IO 资源,间接也提升了写入的性能。
4.使用零拷贝技术加速消费流程。

9.数据压缩

  • 不压缩直接传输需要的时间是: 传输未压缩数据的耗时。
  • 使用数据压缩需要的时间是: 压缩耗时 + 传输压缩数据耗时 + 解压耗时。

10.RocketMQ Producer

DefaultMQProducer的启动过程

  • 通过一个单例模式(Singleton Pattern)的 MQClientManager 获取 MQClientInstance 的实例 mQClientFactory,没有则自动创建新的实例;
  • 在 mQClientFactory 中注册自己;
  • 启动 mQClientFactory;
  • 给所有 Broker 发送心跳。
    //获取 MQClientInstance 的实例 mQClientFactory,没有则自动创建新的实例
    this.mQClientFactory = MQClientManager.getInstance().getOrCreateMQClientInstance(this.defaultMQProducer, rpcHook);
    //在 mQClientFactory 中注册自己
    boolean registerOK = mQClientFactory.registerProducer(this.defaultMQProducer.getProducerGroup(), this);
    if (!registerOK) {
        this.serviceState = ServiceState.CREATE_JUST;
        throw new MQClientException("The producer group[" + this.defaultMQProducer.getProducerGroup()
            + "] has been created before, specify another name please." + FAQUrl.suggestTodo(FAQUrl.GROUP_NAME_DUPLICATE_URL),
            null);
    }

    this.topicPublishInfoTable.put(this.defaultMQProducer.getCreateTopicKey(), new TopicPublishInfo());

    if (startFactory) {
        mQClientFactory.start();
    }

    ...
    
    给所有 Broker 发送心跳
    this.mQClientFactory.sendHeartbeatToAllBrokerWithLock();

11.Kafka Consumer

Kafka 消费模型的几个要点:

  • Kafka 的每个 Consumer(消费者)实例属于一个ConsumerGroup(消费组);
  • 在消费时,ConsumerGroup中的每个Consumer独占一个或多个Partition(分区);
  • 对于每个 ConsumerGroup,在任意时刻,每个 Partition 至多有 1 个 Consumer 在消费;
  • 每个 ConsumerGroup 都有一个 Coordinator(协调者)负责分配 Consumer 和 Partition 的对应关系,当 Partition或是Consumer发生变更时,会触发rebalance(重新分配)过程,重新分配 Consumer 与 Partition 的对应关系;
  • Consumer 维护与 Coordinator 之间的心跳,这样 Coordinator 就能感知到 Consumer 的状态,在 Consumer 故障的时候及时触发 rebalance。
肖特基二极管的反向恢复过程 本博客简述肖特基二极管反向恢复过程。 阅读详情

相关推荐

【LDLTS解析】从重叠峰到精准参数:拉普拉斯深能级瞬态光谱如何重塑半导体缺陷分析

本文深入解析了拉普拉斯深能级瞬态光谱(LDLTS)技术如何革新半导体缺陷分析。针对传统DLTS难以分辨重叠峰的痛点,LDLTS通过拉普拉斯逆变换对高精度电容瞬态曲线进行数学解卷积,成功分离发射率相近的缺陷信号,实现从模糊宽峰到精准独立峰的转变。该技术不仅大幅提升了缺陷激活能和捕获截面等关键参数的提取精度,更推动分析范式从经验拟合转向第一性原理,为先进半导体工艺开发与良率提升提供了强大的精准诊断工具。

weixin_29224309的博客 273

Linux系统调优

Linux在进行系统调优的时候,首先要考虑整个操作系统的结构,然后针对各个部分进行优化,下面展示一个Linux系统的各个组成部分: 有上图可以看出,我们可以调整的有应用程序,库文件,内核,驱动,还有硬件本身,所以接下来讲对这些进行详细的介绍,从而是系统的性能有所提高。 内核子系统中主要包括一下几个方面: 1. network(网络) 2. ...

weixin_34232617的博客 259

Kylin系统离线环境下的dpkg依赖包高效部署指南

本文详细介绍了在Kylin系统离线环境下高效部署dpkg依赖包的完整方案,包括预下载依赖包、构建本地APT仓库以及高级故障排查技巧。通过实战经验和优化建议,帮助用户解决依赖地狱问题,提升部署效率,特别适用于银河麒麟V10等内网环境。

weixin_29051245的博客 386

为什么循环队列要浪费一个存储空间

单向队列会出现“假溢出”问题,而循环队列却能解决“假溢出”问题。常规的循环队列实现方法需要浪费一个存储空间,那么如果不浪费一个空间是否也能实现一个循环队列呢?

zwx900102的博客 3433

Smart200 PLC实现Bool信号接通延时、关闭延时作用

解决Smart200 PLC时间继电器和脉冲扫描P或N不能重复使用的问题,用于Bool信号延时接通和延时关闭的作用,可调整时间基数

gk_121的博客 4318

基于opencv-ANN的水果识别模型训练

本文通过opencv-ann-mlp训练模型,实现对五种水果进行分类识别。本文详细介绍该项目的各个过程,包括数据准备、预处理、样本读取、训练数据集制作、训练标签制作、模型参数设置、模型训练,模型测试验证等,总结该过程需要注意的事项。

qq_15985873的博客 3973

ROS订阅最新的消息及queue_size和buff_size的理解

机器人应用中难免会遇到运算起来很费时间的操作,比如图像的特征提取、点云的匹配等等。有时候,不可避免地,我们需要在ROS的Subscriber的Callback回调函数中进行这些费时的操作。Subscriber所订阅的消息的发布频率可能是很高的,而这些操作的运算速度肯定达不到消息发布的速度。所以,如果我们要是没有取舍的对于每个消息都调用一次回调函数,那么势必会导致计算越来越不实时,很有可能当下在处理...

qq_37082966的博客 1万+

HSM 网络安全 信息安全

HSM HSM信息安全功能 汽车电子网络安全中HSM 的应用场景 选择适合汽车电子网络安全的 HSM 符合汽车安全标准和法规要求的HSM HSM 在汽车电子网络安全中的可靠性和安全性 评估汽车电子网络的安全性 汽车 HSM(Hardware Security Module)模块开发 汽车 HSM(Hardware Security Module)模块测试

天赐好车的博客 1237

消息队列_12(内存管理)

内存管理:如何避免内存溢出和频繁的垃圾回收 java、Go语言等,采用的都是自动内存管理机制。 自动内存管理机制优点:方便,降低开发难度,提升效率,完美地解决内存泄漏问题。 同时会存在一些问题。 1.自动内存管理机制的实现原理 内存管理,主要考虑申请内存和内存回收。 申请内存的逻辑: 计算要创建对象所需占用的内存大小 在内存中找一块连续并且是空闲的内存空间,标记为已占用 把申请的内存地址绑定到对...

qq_21486655的博客 723

ParaView: GUI 轴网格

ParaView: GUI 轴网格

希望我的博客,能帮上你解决学习中工作中所遇到的问题 1923

MuJoCo 入门教程(二)

本章介绍 MuJoCo 的数学和算法基础。对于熟悉广义或关节坐标建模和仿真的读者来说,整体框架是相当标准的。因此,我们将对这些材料进行简要总结。本章的大部分篇幅用于介绍我们如何处理接触和其他约束条件。这种方法是基于我们最近的研究,也是 MuJoCo 所独有的,因此我们花时间对其进行了详细的激励和解释。更多信息可参见下面的论文,尽管本章中的一些技术思想是新的,在其他地方还没有描述过。

机器人控制与仿真应用 3712

队列

队列 队列是一个有序列表,它遵循先进先出的原则。 队列有两种实现方法式:数组和链表 数组实现        因为队列是从队尾添加元素,从队首进行删除元素,因此需要两个变量来记录,一个front记录队首,一个rear记录队尾的后一个位置,此时需要让数组预留一个位置(为了有效区分队列空与队列满的添加),length保存是数组长度。 例如:   假设队列的长度为4...

weixin_43933163的博客 214

把注释掉的代码删除掉:在 SAP ABAP 团队里打造可回溯、可测试、可演进的代码库

摘要 SAP ABAP项目中常见的"注释掉代码"反模式存在严重隐患:它增加代码噪音,制造虚假安全感,并可能引发安全和合规风险。Clean ABAP指南明确建议删除这类代码,理由包括: 版本控制系统已提供完整历史回溯能力 注释代码会误导开发者,增加理解成本 临时禁用需求应通过Feature Toggle实现 必须保留的参考代码应放入$TMP等隔离区域 团队应建立自动化检查机制,将"删除注释代码"纳入工程规范,确保代码库只表达当前有效的行为逻辑。在AI时代,可以利用工具辅

2007 年 ~ 2025 年,深耕 SAP 技术 18 年 2451

消息队列学习笔记一:ActiveMQ消息队列的动态生成

消息队列学习笔记一:ActiveMQ消息队列的动态生成 处理步骤 建立服务接口(并生成实现类) 创建连接工厂 //创建连接工厂 ActiveMQConnectionFactory connFactory = new ActiveMQConnectionFactory( ActiveMQConnection.DEFAULT_USER, ActiveMQConnection.DEF...

公子&小白的博客 1642

RU DOS版、EFI版32bit/64bit BIOS常用工具

DOS版、EFI版的RU工具,可用来查看IO、MEM、PCI、SMBIOS等资源。亲测在EFI SHELL下可用。

假人有限元模型

假人模型,车辆碰撞假人有限元模型,适合做乘员安全的研究者利用

Kafka学习笔记(一):什么是消息队列?什么是Kafka?

目录一、消息队列的概述(一)前置知识点1、集群和分布式2、队列(Queue)的含义3、同步与异步的含义(二)消息队列的含义与特点二、Kafka(一) 概述(二) 常用名词含义三、Zookeeper(一)Zookeeper概述四、Kafka和其他消息队列的对比(一)Kafka与RabbitMQ(二)Kafka与ActivitiMQ参考导航 一、消息队列的概述 (一)前置知识点 1、集群和分布式 集群:同一业务部署在多台服务器上或者不同的服务节点上。 分布式:一个业务被拆分为多个子业务部署在不同的服务器上或者

原来是小雨啊的博客 2151

SAP B1中文培訓教材_SDK

公司内部培训资料,对开发工具 ,DIAPI, UIAPI,Add-ON有详细解说

Kafka学习笔记(一)——消息队列

Kafka——消息队列一、消息队列的介绍1. 定义2. 特点3. 模式二、消息队列的应用场景1. 异步处理2. 应用耦合3. 限流削峰4. 消息驱动的系统三、消息队列的缺点四、消息队列的两种模式1. 点对点模式2. 发布/订阅模式 一、消息队列的介绍 消息(Message)是指在应用之间传送的数据,消息可以非常简单,比如只包含文本字符串,也可以更复杂,可能包含嵌入对象。 消息队列(Message ...

AidenBrett7的博客 434

ssm框架搭建

这个是一个在idea上成功跑起来的ssm框架项目,保存在这里方便以后使用直接下载

Kafka学习笔记一(消息队列)

众所周知,敲代码写需求的时候,最常见的就是给你加需求,或者给你改需求这种令人头疼的事。当系统B要接入你的系统A获取数据时,要改代码,系统C要获取数据时,也要改代码;如果后面还有其他系统要来获取数据,这样一直改吗?当然不,消息队列就可以解决这个问题。相比起传统模式那样系统间耦合度强的情况,MQ模式可以直接将你的消息写入消息队列,让需要获取消息的系统自己从消息队列中订阅,系统A不需要再做任何修改就可以实现业务了,轻松降低模块之间的耦合。

kiriko233的博客 421

MSMQ消息队列学习笔记(一)

1.创建消息队列            ///         /// 在指定的路径中创建非事务性“消息队列”队列         ///         /// 要创建队列的路径         /// 返回:表示新队列的 System.Messaging.MessageQueue         public static MessageQueue Create(strin

dandan12的专栏 2703

Windows消息机制学习笔记(一)—— 消息队列

Windows消息机制学习笔记(一)—— 消息队列前言基本概念实验一:使用代码画出最简单窗口第一步:编译并运行以下代码第二步:查看运行结果第三步:使用其它窗口对其进行覆盖,观察效果 前言 一、学习自滴水编程达人中级班课程,官网:https://bcdaren.com 二、海东老师牛逼! 基本概念 接触过编程的人,或多或少用到过消息机制,但大多数人(包括我自己)只是知道相关API的基本用法,却不知道它是如何实现的 从本章起,我们将带着以下几个问题一起来学习消息机制: 什么是窗口句柄?在哪里?有什么用?

lzyddf的博客 973

消息队列-RabbitMQ学习笔记(一)

生产者:Producer,类比为快递员,发送消息的人(客户端)消费者:Consumer,类比为取快递的人,接受读取消息的人(客户端)消息:Message,类比为快递,就是生产者要传输给消费者的数据消息队列:Queue ,类比快递柜,就是用来存储消息的地方问:为什么不直接传输,要用消息队列?答:生产者不用关心你的消费者要不要消费、什么时候消费,我只需要把东西给消息队列,我的工作就算完成了。生产者和消费者实现了解耦,互不影响。

qq_46614863的博客 1121

RabbitMQ学习笔记(一)中间件及消息队列介绍

MQ(message queue),从字面意思上看,本质是个队列,FIFO 先入先出,只不过队列中存放的内容是 message 而已,还是一种跨进程的通信机制,用于上下游传递消息。在互联网架构中,MQ 是一种非常常 见的上下游“逻辑解耦+物理解耦”的消息通信服务。使用了 MQ 之后,消息发送上游只需要依赖 MQ,不 用依赖其他服务。Broker接收和分发消息的应用,RabbitMQ Server 就是 Message Broker。

程哥哥的一亩三分地 298

消息队列-ActiveMQ学习笔记(一)-JMS介绍与环境搭建

一、介绍JMS(来自于百度百科)        JMS即Java消息服务(Java Message Service)应用程序接口,是一个Java平台中关于面向消息中间件(MOM)的API,用于在两个应用程序之间,或分布式系统中发送消息,进行异步通信。 1、体系结构: JMS提供者:连接面向消息中间件的,JMS接口的一个实现。提供者可以是Java平台的JMS实现,也可以是非Java平台

绝版灬小伙的博客 3498

【奈学教育】| 公开课RocketMq学习笔记一 、消息队列场景分析

一、消息队列 1、在消息的传输过程中保存消息的容器,生产者和消费者不直接通讯,依靠队列保证消息的可靠性,避免了系统间的相互影响。 2、场景分析一 1)当天交易满3笔送5元红包 2)连续登陆5天送10元红包 3)新注册送5元红包 4)运营活动可能需要在业务逻辑中各个环节加入运营活动逻辑,而且有时效性,频繁在正常业务逻辑中添加/删除代码显然不合理且分险大,需要测试支撑等,流程比较复杂。 3、核心基础服务,可能各个业务线都会关注某些请求处理结果,不断修改代码添加向业务的通知不合理。 .

promiseful的博客 335

【Linux学习笔记】进程通信之消息队列和信号量

本文介绍了Linux进程通信中的消息队列和信号量机制。消息队列允许进程间发送不同类型的数据块,具有随内核的生命周期特性。信号量主要用于同步和互斥,通过P/V操作保护临界资源,本质是资源预订机制。文章还阐述了并发编程概念如临界区、共享资源等,并分析了内核如何组织IPC资源。最后提供了一个在minishell中实现管道功能的代码示例,展示了进程间通信的实际应用。这些机制是Linux系统编程的重要基础,需要深入理解其原理和实现方式。

大白的编程日记. 1165

消息队列学习笔记

全称为Message Queue。“消息队列”是在消息的传输过程中保存消息的容器。它是典型的:生产者、消费者模型。生产者不断向消息队列中生产消息,消费者不断的从队列中获取消息。因为消息的生产和消费都是异步的,而且只关心消息的发送和接收,没有业务逻辑的侵入,这样就实现了生产者和消费者的解耦。

qq_45901741的博客 1277

RT-Thread学习笔记——消息队列

前言 本文学习RT-Thread的消息队列,支持不定长度消息的收发,涉及消息队列的工作机制、消息队列相关函数以及基于STM32的RT-Thread消息队列应用示例,采用RTT&正点原子联合出品潘多拉开发板进行实验,基于STM32L475VET6。 一、消息队列的工作机制 消息队列能够接收来自线程或中断服务例程中不固定长度的消息,并把消息缓存在自己的内存空间中。其他线程也能够从消...

Sanjay_Wu的博客 9499
上一篇: 类加载中的属性问题
下一篇: 消息队列学习笔记(二)
过河的小卒子
博客等级 码龄10年 39粉丝 112原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值