当前位置: 首页 > article >正文

快速掌握 GO 之 RabbitMQ

更多个人笔记见:
github个人笔记仓库
gitee 个人笔记仓库
个人学习,学习过程中还会不断补充~ (后续会更新在github和 gitee上)

文章目录

    • 作用
    • 经典例子
        • 生产者(发送端)
        • 消费者(接收端)

作用

类似一个“中间过渡器”,应对突发流量导致数据库连接池耗尽或者请求导致服务崩溃

  • 流量洪峰​​:促销活动时,前置 Nginx 将请求写入 RabbitMQ,后端服务按能力消费
  • 容灾恢复​​:数据库故障期间,消息持久化在队列;恢复后继续消费 (消费指的是 Mysql 取出数据然后存起来)
  • 将任务分发到多个消费者实例,确保高负载下任务均匀分配。这就可以实现负载均衡 (比如多个 worker 处理帖子审核)

需要考虑如果用户的申请不是很多情况下,多引入一层 RabbitMQ 其实会导致实际的速度变慢(毕竟多加了一层)

经典例子

GO 语言相关库:go get -u github.com/streadway/amqp

docker 快速部署 rabbitMQ:docker run -d --name rabbitmq -p 5672:5672 -p 15672:15672 rabbitmq:3-management

  • 5672:AMQP 端口
  • 15672:管理界面端口,访问 http://localhost:15672 ( 默认用户/密码:guest/guest)
生产者(发送端)

创建 producer文件夹下创建producer.go ,然后单独 go run(同时 go run 后面的消费者记得)

package mainimport ("fmt""log""time""github.com/streadway/amqp"
)// 统一错误输出
func failOnError(err error, msg string) {if err != nil {log.Fatalf("%s: %s", msg, err)}
}func main() {// 连接 RabbitMQconn, err := amqp.Dial("amqp://guest:guest@localhost:5672/")failOnError(err, "Failed to connect to RabbitMQ")defer conn.Close() //关闭连接ch, err := conn.Channel() //建立通道,通过 conn 建立的,可以调用 amqp 中的函数failOnError(err, "Failed to open a channel")defer ch.Close()// 声明队列q, err := ch.QueueDeclare("post_queue", // 指定创建或引用的队列名称false,        // 持久化  false 表示队列不会持久化到磁盘,重启 RabbitMQ 后会丢失。true 的话重启后就还在false,        // 自动删除   设置为 false 表示队列不会自动删除,如果 true,最后一个消费者断开后队列删除false,        // 独占   设置为 true 表示该队列只供一个消费者使用,当连接关闭后,队列会自动删除。false表示队列可以被多个连接使用false,        // 无等待  false 表示需要服务器确认队列创建,true表示客户端不会等待服务器的确认响应,如果操作失败也不会收到错误通知nil,          // 额外参数  额外参数可以用来设置队列的特殊属性,如消息TTL、队列最大长度、死信队列等)failOnError(err, "Failed to declare a queue")// 设置定时器,每5秒发送一次消息ticker := time.NewTicker(1 * time.Second)defer ticker.Stop()// 创建一个函数用于发送消息,这样循环调用函数就是发送多次消息sendMessage := func(msgContent string) {err = ch.Publish("",     // 交换机名称   这里是默认交换机,能够将消息直接路由到与路由键同名的队列q.Name, // 路由键   也就是队列名称,路由键应该与目标队列名称一致,消息才能被正确路由false,  // mandatory标志  false 表示消息无法路由到队列,则消息会被丢弃  如果是 true 就是当消息不能路由到队列时,RabbitMQ会返回一个Basic.Return命令给生产者false,  // immediate 标志   false 表示如果队列中没有消费者,消息会被存入队列等待消费, true表示当没有消费者能够立即消费该消息时,消息不会入队而是被丢弃amqp.Publishing{ //消息内容和性质ContentType: "text/plain",       //制定为 MIME 类型Body:        []byte(msgContent), //转换为字节类型})if err != nil {log.Printf("Failed to publish a message: %s", err)return}log.Printf(" [x] Sent %s", msgContent)}count := 1log.Println("Starting periodic message sending. Press Ctrl+C to exit.")// 等待定时器触发,定期发送消息for range ticker.C {sendMessage(fmt.Sprintf("Hello, RabbitMQ! Message #%d", count))count++}
}
  • 这里我将函数设置为每间隔 1s 就发送消息,同时记录数据
  • 如果运行后,隔一段时间再启动消费者,或者说运行中途关闭消费者,过一段时间再启动消费者,会发现中间发出的信号也会打印出来,这说明实际上是有存储在 RabbitMQ 中的(运行的时候,关闭后存储就需要看上面的设置了)
消费者(接收端)

consumer 文件夹下创建 consumer.go 然后单独一个终端 go run

package mainimport ("log""github.com/streadway/amqp"
)func failOnError(err error, msg string) {if err != nil {log.Fatalf("%s: %s", msg, err)}
}func main() {//建立连接conn, err := amqp.Dial("amqp://guest:guest@localhost:5672/")failOnError(err, "Failed to connect to RabbitMQ")defer conn.Close()//连接 channelch, err := conn.Channel()failOnError(err, "Failed to open a channel")defer ch.Close()q, err := ch.QueueDeclare("post_queue", false, false, false, false, nil)failOnError(err, "Failed to declare a queue")msgs, err := ch.Consume(q.Name, // 队列"",     // 消费者标签true,   // 自动确认false,  // 独占false,  // 无本地false,  // 无等待nil,    // 额外参数)failOnError(err, "Failed to register a consumer")forever := make(chan bool)go func() {for d := range msgs {log.Printf("Received: %s", d.Body)}}()log.Printf(" [*] Waiting for messages. To exit press CTRL+C")<-forever
}

相关文章:

快速掌握 GO 之 RabbitMQ

更多个人笔记见&#xff1a; github个人笔记仓库 gitee 个人笔记仓库 个人学习&#xff0c;学习过程中还会不断补充&#xff5e; &#xff08;后续会更新在github和 gitee上&#xff09; 文章目录 作用经典例子生产者&#xff08;发送端&#xff09;消费者&#xff08;接收端&a…...

SQL Server 事务详解:概念、特性、隔离级别与实践

一、事务的基本概念 事务&#xff08;Transaction&#xff09;是数据库操作的基本单位&#xff0c;它是由一组SQL语句组成的逻辑工作单元。事务具有以下关键特性&#xff0c;通常被称为ACID特性&#xff1a; ​​原子性&#xff08;Atomicity&#xff09;​​&#xff1a;事务…...

MAC软件游戏打开提示已损坏

打开「终端.app」&#xff0c;输入以下命令并回车&#xff0c;输入开机密码回车 sudo spctl --master-disable 按照上述步骤操作完成后&#xff0c;打开「系统偏好设置」-「安全与隐私」-「通用」&#xff0c;确保已经修改为「任何来源」。 打开「终端.app」&#xff0c;输入…...

React基础教程(13):路由的使用

文章目录 1、什么是路由?2、路由安装3、路由使用(1)路由方法导入和使用(2)定义路由以及重定向(3)嵌套路由(4)路由跳转方式(5)动态路由动态路由写法一动态路由写法二4、实现效果5、完整代码下载1、什么是路由? 路由是根据不同的url地址展示不同的内容或页面。 一个…...

力扣刷题(第四十三天)

灵感来源 - 保持更新&#xff0c;努力学习 - python脚本学习 解题思路 1. 逐位检查法&#xff1a;通过右移操作逐位检查每一位是否为1&#xff0c;统计计数 2. 位运算优化法&#xff1a;利用 n & (n-1) 操作消除最低位的1&#xff0c;减少循环次数 3. 内置函数法&…...

Centos环境下安装/重装MySQL完整教程

目录 一、卸载残留的MySQL环境&#xff1a; 二、安装MySQL&#xff1a; 1、下载MySQL官方的yum源&#xff1a; 2、更新系统yum源&#xff1a; 3、确保系统中有了对应的MySQL安装包&#xff1a; 4、安装MySQL服务&#xff1a; 5、密钥问题安装失败解决方法&#xff1a; …...

【Linux】环境变量完全解析

9.环境变量 文章目录 9.环境变量一、命令行参数二、获取环境变量程序中获取环境变量1. 使用命令行参数2. 使用系统调用函数getenv("字符串");3. 使用系统提供的全局变量environ 命令行中查询环境变量 三、常见环境变量1. HOME2. OLDPWD3. PATH4. SHELL 四、环境变量与…...

【Java】mybatis-plus乐观锁-基本使用

乐观锁&#xff08;Optimistic Locking&#xff09;是解决并发问题的重要机制。它通过在数据更新时验证数据版本来确保数据的一致性&#xff0c;从而避免并发冲突。与悲观锁不同&#xff0c;乐观锁并不依赖数据库的锁机制&#xff0c;而是通过检查数据的版本或标志字段来判断数…...

力扣每日一题——找到离给定两个节点最近的节点

目录 题目链接&#xff1a;2359. 找到离给定两个节点最近的节点 - 力扣&#xff08;LeetCode&#xff09; 题目描述 解法一&#xff1a;双指针路径交汇法​ 基本思路 关键步骤 为什么这样可行呢我请问了&#xff1f; 举个例子 特殊情况 Java写法&#xff1a; C写法&a…...

机器学习与深度学习03-逻辑回归01

目录 上集回顾1. 逻辑回归与线性回归的区别2.逻辑回归的常见目标函数3.逻辑回归如何分类4.Sigmoid函数详解5.逻辑回归模型的参数 上集回顾 上一节文章地址&#xff1a;链接 1. 逻辑回归与线性回归的区别 应用领域 线性回归通常⽤于解决回归问题&#xff0c;其中⽬标是预测⼀…...

卷积神经网络(CNN)入门学习笔记

什么是 CNN&#xff1f; CNN&#xff0c;全称 卷积神经网络&#xff08;Convolutional Neural Network&#xff09;&#xff0c;是一种专门用来处理图片、语音、文本等结构化数据的神经网络。 它模仿人眼识别图像的方式&#xff1a; 从局部到整体&#xff0c;一步步提取特征&a…...

【优笔】基于STM32的多模态智能门禁系统

代码功能详细描述 该代码实现了一个基于STM32的多模态智能门禁系统,整合密码、指纹、人脸识别(预留)三种验证方式,并提供完善的管理功能。系统架构如下图所示: #mermaid-svg-Uufpcoeo5Lega096 {font-family:"trebuchet ms",verdana,arial,sans-serif;font-size…...

Metasploit工具使用详解(上)丨小白WEB安全入门笔记

Metasploit工具使用详解(上)丨小白WEB安全入门笔记 一、课程定位与工具概述 课程性质&#xff1a; 小白WEB安全入门课程聚焦基础操作&#xff0c;非深度专题&#xff08;Metasploit专题可讲数十节课&#xff09;目标&#xff1a;掌握基本概念和简单漏洞利用 Metasploit核心定…...

Femap许可证与网络安全策略

随着科技的快速发展&#xff0c;网络安全问题已成为各行各业关注的焦点。在电磁仿真领域&#xff0c;Femap作为一款领先的软件&#xff0c;其许可证的安全性和网络策略的重要性不言而喻。本文将探讨Femap许可证与网络安全策略的关系&#xff0c;确保您的电磁仿真工作能够在一个…...

VLAN的作用和原理

1. 为什么要有vlan&#xff1f; 分割广播域&#xff0c;避免广播风暴&#xff0c;造成网络资源的浪费 可以灵活的组网&#xff0c;便于管理&#xff0c;同时还有安全加固的功能 2. vlan是怎么实现的&#xff1f;端口的原理&#xff1f; 设置VLAN后&#xff0c;流量之间的转…...

深入探讨集合与数组转换方法

目录 1、Arrays.asList() 1.1、方法作用 1.2、内部实现 1.3、修改元素的影响 1.4、注意事项 2、list.toArray() 2.1、方法作用 2.2、内部实现 2.3、修改元素的影响 2.4、特殊情况 1、对象引用 2、数组copy 3、对比总结 4、常见误区与解决方案 5、实际应用建议…...

让大模型看得见自己的推理 — KnowTrace结构化知识追踪

让大模型“看得见”自己的推理 —— KnowTrace 结构化知识追踪式 RAG 全解析 一句话概括:把检索-推理“改造”成 动态知识图构建任务,再让 LLM 只关注这张不断精炼的小图 —— 这就是显式知识追踪的核心价值。 1. 背景:为什么 RAG 仍难以搞定多跳推理? 长上下文负担 传统 I…...

【HarmonyOS 5应用架构详解】深入理解应用程序包与多Module设计机制

⭐本期内容&#xff1a;【HarmonyOS 5应用架构详解】深入理解应用程序包与多Module设计机制 &#x1f3c6;系列专栏&#xff1a;鸿蒙HarmonyOS&#xff1a;探索未来智能生态新纪元 文章目录 前言应用与应用程序包应用程序的基本概念应用程序包的类型标识机制应用安装流程 应用的…...

【Oracle】DCL语言

个人主页&#xff1a;Guiat 归属专栏&#xff1a;Oracle 文章目录 1. DCL概述1.1 什么是DCL&#xff1f;1.2 DCL的核心功能 2. 用户管理2.1 创建用户2.2 修改用户2.3 删除用户2.4 用户信息查询 3. 权限管理3.1 系统权限3.1.1 授予系统权限3.1.2 撤销系统权限 3.2 对象权限3.2.1…...

MySQL强化关键_017_索引

目 录 一、概述 二、索引 1.主键索引 2.唯一索引 3.查看索引 4.添加索引 &#xff08;1&#xff09;建表时添加 &#xff08;2&#xff09;建表后添加 5.删除索引 三、树 1.二叉树 2.红黑树 3.B树 4.B树 &#xff08;1&#xff09;为什么 MySQL 选择B树作为索引…...

stm32——SPI协议

stm32——SPI协议 STM32的SPI&#xff08;Serial Peripheral Interface&#xff0c;串行外设接口&#xff09;协议是一种高速、全双工、同步的串行通信协议&#xff0c;广泛评估微控制器与各种外设&#xff08;如传感器、器件、显示器、模块等&#xff09;之间的数据传输。STM3…...

Linux 下如何查看进程的资源限制信息?

简介 Linux 上的 cat /proc/$pid/limits 命令提供有关特定进程的资源限制的信息&#xff0c;其中 $pid 是相关进程的进程 ID &#xff08;pid&#xff09;。该文件是 /proc 文件系统的一部分&#xff0c;该文件系统是一个虚拟文件系统&#xff0c;提供有关进程和系统资源的信息…...

【备忘】php命令行异步执行超长时间任务

环境说明&#xff1a; 操作系统&#xff1a;windows10 IDE&#xff1a;phpstorm 开发语言&#xff1a;php7.4 框架&#xff1a;thinkphp5.1 测试环境&#xff1a;linuxwindows均测试通过。 初级方法&#xff1a; function longRunningTask() {$root_path Tools::get_ro…...

对于ARM开发各种手册的分类

手册名称全称主要内容适用范围是不是讲SysTick&#xff1f;Cortex-M3 Technical Reference Manual (TRM)Cortex-M3 Technical Reference Manual描述 Cortex-M3内核架构&#xff0c;如寄存器模型、总线接口、指令集、异常模型只适合 Cortex-M3 内核&#xff0c;不含外设❌ 没有C…...

java开发中#和$的区别

在Spring框架中&#xff0c;$ 和 # 是两种不同的表达式前缀&#xff0c;用于从不同的来源获取值或执行计算。下面详细解释它们的区别和用法&#xff1a; 一、$ 占位符&#xff08;Property Placeholder&#xff09; 1. 作用 从配置文件&#xff08;如 application.propertie…...

在 RK3588 上通过 VSCode 远程开发配置指南

在 RK3588 上通过 VSCode 远程开发配置指南 RK3588 设备本身不具备可视化编程环境&#xff0c;但可以通过 VSCode 的 Remote - SSH 插件 实现远程代码编写与调试。以下是完整的配置流程。 一、连接 RK3588 1. 安装 Debian 系统 先在 RK3588 上安装 Debian 操作系统。 2. 安…...

OpenHarmony标准系统-HDF框架之音频驱动开发

文章目录 引言OpenHarmony音频概述OpenHarmony音频框图HDF音频驱动框架概述HDF音频驱动框图HDF音频驱动框架分析之音频设备驱动HDF音频驱动框架分析之supportlibs实现HDF音频驱动框架分析之hdi-passthrough实现HDF音频驱动框架分析之hdi-bindev实现HDF音频驱动加载过程HDF音频驱…...

HTML Day03

Day03 0. 引言1. CSS1.1 CSS的3种使用方法1.2 内联样式1.3 内部样式表1.4 外部CSS文件 2. 图像3. 表格3.1单元格间距和单元格边框 4. 列表4.1 有序表格的不同类型4.2 不同类型的无序表格4.3 嵌套列表 5. 区块6. 布局6.1 div布局6.2 表格布局 0. 引言 HELLO ^ _ ^大家好&#xf…...

篇章六 数据结构——链表(二)

目录 1. LinkedList的模拟实现 1.1 双向链表结构图​编辑 1.2 三个简单方法的实现 1.3 头插法 1.4 尾插法 1.5 中间插入 1.6 删除 key 1.7 删除所有key 1.8 clear 2.LinkedList的使用 2.1 什么是LinkedList 5.2 LinkedList的使用 1.LinkedList的构造 2. LinkedList的…...

Python60日基础学习打卡Day39

昨天我们介绍了图像数据的格式以及模型定义的过程&#xff0c;发现和之前结构化数据的略有不同&#xff0c;主要差异体现在2处 模型定义的时候需要展平图像由于数据过大&#xff0c;需要将数据集进行分批次处理&#xff0c;这往往涉及到了dataset和dataloader来规范代码的组织…...