专题03——RabbitMQ

1. RabbitMQ安装

服务端

使用如下sh脚本安装:

#!/bin/sh

sudo apt-get install curl gnupg apt-transport-https -y

## Team RabbitMQ's main signing key
curl -1sLf "https://keys.openpgp.org/vks/v1/by-fingerprint/0A9AF2115F4687BD29803A206B73A36E6026DFCA" | sudo gpg --dearmor | sudo tee /usr/share/keyrings/com.rabbitmq.team.gpg > /dev/null
## Community mirror of Cloudsmith: modern Erlang repository
curl -1sLf https://ppa1.novemberain.com/gpg.E495BB49CC4BBE5B.key | sudo gpg --dearmor | sudo tee /usr/share/keyrings/rabbitmq.E495BB49CC4BBE5B.gpg > /dev/null
## Community mirror of Cloudsmith: RabbitMQ repository
curl -1sLf https://ppa1.novemberain.com/gpg.9F4587F226208342.key | sudo gpg --dearmor | sudo tee /usr/share/keyrings/rabbitmq.9F4587F226208342.gpg > /dev/null ## Add apt repositories maintained by Team RabbitMQ
sudo tee /etc/apt/sources.list.d/rabbitmq.list <<EOF
## Provides modern Erlang/OTP releases
##
deb [signed-by=/usr/share/keyrings/rabbitmq.E495BB49CC4BBE5B.gpg] https://ppa1.novemberain.com/rabbitmq/rabbitmq-erlang/deb/ubuntu jammy main
deb-src [signed-by=/usr/share/keyrings/rabbitmq.E495BB49CC4BBE5B.gpg] https://ppa1.novemberain.com/rabbitmq/rabbitmq-erlang/deb/ubuntu jammy main ## Provides RabbitMQ
##
deb [signed-by=/usr/share/keyrings/rabbitmq.9F4587F226208342.gpg] https://ppa1.novemberain.com/rabbitmq/rabbitmq-server/deb/ubuntu jammy main
deb-src [signed-by=/usr/share/keyrings/rabbitmq.9F4587F226208342.gpg] https://ppa1.novemberain.com/rabbitmq/rabbitmq-server/deb/ubuntu jammy main
EOF ## Update package indices
sudo apt-get update -y ## Install Erlang packages
sudo apt-get install -y erlang-base \
erlang-asn1 erlang-crypto erlang-eldap erlang-ftp erlang-inets \
erlang-mnesia erlang-os-mon erlang-parsetools erlang-public-key \
erlang-runtime-tools erlang-snmp erlang-ssl \
erlang-syntax-tools erlang-tftp erlang-tools erlang-xmerl ## Install rabbitmq-server and its dependencies
sudo apt-get install rabbitmq-server -y --fix-missing

配置文件在/etc/rabbitmq中,通过rabbitmq-env.conf配置环境,rabbitmq-env.conf如下:

export RABBITMQ_NODENAME=rabbit@localhost
export RABBITMQ_NODE_IP_ADDRESS=127.0.0.1
export ERL_EPMD_ADDRESS=127.0.0.1

客户端

使用NuGet安装RabbitMQ.Client

2. 接收者

using System.Text;
using RabbitMQ.Client;
using RabbitMQ.Client.Events; // 工厂方法,用于配置连接
var factory = new ConnectionFactory
{
// RabbitMQ的服务端地址
HostName = SharedConfig.Configuration.HostName,
// 异步消费
DispatchConsumersAsync = true
}; // 建立连接
using var connection = factory.CreateConnection();
// 创建信道
var channel = connection.CreateModel(); // 注:XxxDeclare的意思是:没有就创建,有就复用(由于不知道是Sender还是Receiver先启动,所以都要声明)
// 声明交换机
channel.ExchangeDeclare(exchange: SharedConfig.Configuration.ExchangeName,
type: SharedConfig.Configuration.ExchangeType);
// 声明队列
channel.QueueDeclare(queue: SharedConfig.Configuration.QueueName, durable: true, exclusive: false, autoDelete: false,
arguments: null);
// 将队列与交换机绑定
channel.QueueBind(queue: SharedConfig.Configuration.QueueName, exchange: SharedConfig.Configuration.ExchangeName,
routingKey: SharedConfig.Configuration.EventName); // 从队列中获取消息(拉取模式)
var asyncEventingBasicConsumer = new AsyncEventingBasicConsumer(channel);
// 订阅Received事件
asyncEventingBasicConsumer.Received += OnMessageReceived;
// 确认队列中正在消费的事件状态(Ack或Reject)
channel.BasicConsume(queue: SharedConfig.Configuration.QueueName, autoAck: false, consumer: asyncEventingBasicConsumer); Console.ReadLine(); async Task OnMessageReceived(object sender, BasicDeliverEventArgs args)
{
try
{
var bytes = args.Body.ToArray();
var message = Encoding.UTF8.GetString(bytes);
Console.WriteLine($"{DateTime.Now}: 收到了消息-{message}");
channel.BasicAck(args.DeliveryTag, multiple: false);
await Task.Delay(800);
}
catch (Exception e)
{
channel.BasicReject(args.DeliveryTag, true); // 失败重发
Console.WriteLine($"处理收到的消息出错,{e.Message}");
}
}

3. 发送者

using System.Globalization;
using System.Text;
using RabbitMQ.Client; var connectionFactory = new ConnectionFactory
{
HostName = SharedConfig.Configuration.HostName,
DispatchConsumersAsync = true
};
// 和RabbitMQ建立TCP连接
using var connection = connectionFactory.CreateConnection(); // 每间隔3s将当前时间发送到队列当中去,共发送30次
for (int i = 0; i < 30; i++)
{
// 等待发送的消息
string message = DateTime.Now.ToString(CultureInfo.InvariantCulture);
// 将消息重新编码为RabbitMQ能够接受的格式(byte[])
var mqMessage = Encoding.UTF8.GetBytes(message); // 创建信道
using (var channel = connection.CreateModel())
{
var properties = channel.CreateBasicProperties();
// 消息递送模式:持久化模式
properties.DeliveryMode = 2;
// 声明交换机
// 注:XxxDeclare的意思是:没有就创建,有就复用(由于不知道是Sender还是Receiver先启动,所以都要声明)
channel.ExchangeDeclare(exchange: SharedConfig.Configuration.ExchangeName,
type: SharedConfig.Configuration.ExchangeType);
// 发布消息
channel.BasicPublish(exchange: SharedConfig.Configuration.ExchangeName,
routingKey: SharedConfig.Configuration.EventName, mandatory: true,
basicProperties: properties, body: mqMessage);
} Console.WriteLine($"发布了消息:{message}");
Thread.Sleep(3000);
}

4. 共用的配置类

namespace SharedConfig;

public struct Configuration
{
// RabbitMQ的地址,这里用本地地址和默认端口
public const string HostName = "localhost";
// 交换机名称
public const string ExchangeName = "exchange1";
// 交换机类型
public const string ExchangeType = "direct";
// 当作routingKey使用(路由的依据)
public const string EventName = "event1";
// 队列名称
public const string QueueName = "queue1";
}

dotnet学习笔记-专题03-RabbitMQ-01的更多相关文章

  1. Puppet学习笔记(CentOS6.3+Puppet3.01)

    Puppet学习笔记(CentOS6.3+Puppet3.01)  技术 Add comments Oct262012 下了决心,好好学习puppet,周末专门去参加一个puppet的培训,难得朋友那 ...

  2. openresty 学习笔记五:访问RabbitMQ消息队列

    openresty 学习笔记五:访问RabbitMQ消息队列 之前通过比较选择,决定采用RabbitMQ这种消息队列来做中间件,目的舒缓是为了让整个架构的瓶颈环节.这里是做具体实施,用lua访问Rab ...

  3. RabbitMQ学习笔记五:RabbitMQ之优先级消息队列

    RabbitMQ优先级队列注意点: 1.只有当消费者不足,不能及时进行消费的情况下,优先级队列才会生效 2.RabbitMQ3.5以后才支持优先级队列 代码在博客:RabbitMQ学习笔记三:Java ...

  4. 【Ext.Net学习笔记】03:Ext.Net DirectEvents用法详解、DirectMethods用法详解

    Ext.Net通过DirectEvents进行服务器端异步的事件处理.[Ext.Net学习笔记]02:Ext.Net用法概览.Ext.Net MessageBus用法.Ext.Net布局 中已经简单的 ...

  5. Duilib学习笔记《03》— 控件使用

    在前面已经对duilib有个一个基本的了解,并且创建了简单的空白窗体.这仅仅只是一个开始,如何去创建一个绚丽多彩的界面呢?这就需要一些控件元素(按钮.文本框.列表框等等)来完善. 一. Duilib控 ...

  6. 再起航,我的学习笔记之JavaScript设计模式01

    我的学习笔记是根据我的学习情况来定期更新的,预计2-3天更新一章,主要是给大家分享一下,我所学到的知识,如果有什么错误请在评论中指点出来,我一定虚心接受,那么废话不多说开始我们今天的学习分享吧! 在通 ...

  7. Fortran学习笔记:03 数组(Array)

    Fortran学习笔记目录 书接上回:Fortran学习笔记:02 流控制语句 数组(Array) 定义数组 一维数组 program main implicit none integer :: i ...

  8. JavaSE学习笔记05面向对象编程01

    面向对象编程01 java的核心思想就是OOP 面向过程&面向对象 面向过程思想: 步骤清晰简单,第一步做什么,第二步做什么...... 面向过程适合处理一些较为简单的问题 面向对象思想: 物 ...

  9. 《Effective C++ 》学习笔记——条款03

    ***************************************转载请注明出处:http://blog.csdn.net/lttree************************** ...

  10. Solr 6.7学习笔记(03)-- 样例配置文件 solrconfig.xml

    位于:${solr.home}\example\techproducts\solr\techproducts\conf\solrconfig.xml <?xml version="1. ...

随机推荐

  1. html 跳转到新的网址

    更新window.location.href后面的值即可 文件名为 index.html <!DOCTYPE html> <html> <head> <met ...

  2. .NET 8 + WPF 企业级工作流系统

    前言 推荐一款基于.NET 8.WPF.Prism.DryIoc.MVVM设计模式.Blazor以及MySQL数据库构建的企业级工作流系统的WPF客户端框架-AIStudio.Wpf.AClient ...

  3. 游戏AI行为决策——MLP(多层感知机/人工神经网络)

    游戏AI行为决策(特别篇)--MLP(附代码与项目) 你一定听说过神经网络的大名,你有想过将它用于游戏AI的行为决策上吗?其实在(2010年发布的)<最高指挥官2>中就有应用了,今天请允许 ...

  4. DOM & BOM – 冷知识 (新手)

    JS 无法 query select 到伪元素 参考: 使用JS控制伪元素的几种方法 JS style remove property 是 kebab-case set property 是 came ...

  5. Spring —— bean实例化

    bean 实例化 bean本质上就是对象,创建bean使用构造方法完成(反射)      构造方法(常用)        静态工厂*        实例工厂*        FactoryBean(实 ...

  6. 更新iManager离线镜像包方法

    例如将iserver_gisapplication_mapping_10_1_0.tar镜像更新到iManager仓库中 步骤一.将镜像导入本地镜像仓库 docker load -i iserver_ ...

  7. map,unordered_map,multimap,unordered_multimap

    std::map(有序映射) std::unordered_map(无序映射) std::multimap(有序多重映射) std::unordered_multimap(无序多重映射) 它们的使用方 ...

  8. 线段树介绍(segment tree)

    1.引入 给定一个区间\([1, n]\),希望你实现一种数据结构,支持以下操作: 1.修改\(i\)号节点的值. 2.询问区间\([i, j]\)中所有节点的和. 这不是树状数组板子 3.修改区间\ ...

  9. 【官宣】2024 DTC数据技术嘉年华全议程发布:汇聚行业精英,共襄年度盛宴

    龙腾四海内,风云际会时.由墨天轮数据社区和中国数据库联盟(ACDU)主办的第十三届数据技术嘉年华 将于2024年4月12日至13日在北京新云南皇冠假日酒店盛大召开.本次大会的主题是"智能·云 ...

  10. 图菱科技 SaaS 系统容器化最佳实践

    大家好,我是龚承明,在图菱(成都)科技有限公司任职,主要负责公司的产品系统研发以及公司IT基础设施的建设工作.本篇文章将为大家介绍下我司在采用 KubeSphere 平台实现公司业务系统容器化过程中的 ...