閘機控制系統從設計到實現全解析:第 5 篇:RabbitMQ 消息隊列與閘機通信設計

第 5 篇:RabbitMQ 消息隊列與閘機通信設計

RabbitMQ 是一款開源的消息隊列中間件(Message Queue,MQ),基于 Erlang 語言開發,遵循 AMQP(Advanced Message Queuing Protocol,高級消息隊列協議) 標準,主要用于在分布式系統中實現消息的可靠傳遞,核心價值是解耦系統組件、削峰填谷、異步通信等。

RabbitMQ

一、核心定位:為什么需要 RabbitMQ?

RabbitMQ 作為“中間件”,通過存儲轉發消息的方式,讓發送方(生產者)和接收方(消費者)“解耦”:生產者只需要把消息發給 RabbitMQ,不必關心誰來接收;消費者從 RabbitMQ 取消息,不必關心誰發來的。雙方通過消息間接通信,提高系統靈活性和穩定性。

二、核心概念與架構

RabbitMQ 的工作流程基于“生產者-交換機-隊列-消費者”的鏈路,核心組件包括:

  1. 生產者(Producer):發送消息的應用(如訂單系統生成“新訂單”消息)。
  2. 交換機(Exchange):接收生產者的消息,根據“路由規則”將消息轉發到對應的隊列。交換機是 RabbitMQ 靈活路由的核心,有 4 種類型:
    • 直連交換機(Direct Exchange):消息的“路由鍵”(Routing Key)必須與隊列綁定的“綁定鍵”完全匹配才轉發(如“order.pay”只能匹配“order.pay”)。
    • 主題交換機(Topic Exchange):支持通配符匹配(* 匹配一個單詞,# 匹配多個單詞),適合按“主題”分類消息(如“order.*”可匹配“order.pay”“order.cancel”)。
    • 扇形交換機(Fanout Exchange):忽略路由鍵,將消息廣播到所有綁定的隊列(適合“一對多”通知,如“系統通知”需要所有模塊接收)。
    • Headers 交換機:不依賴路由鍵,根據消息頭(Headers)的鍵值對匹配(較少用)。
  3. 隊列(Queue):存儲消息的緩沖區,消息最終會進入隊列等待消費者取走。隊列是“持久化”的(可配置),即使 RabbitMQ 重啟,未消費的消息也能保留。
  4. 綁定(Binding):連接交換機和隊列的“規則”,包含“綁定鍵”(Binding Key),用于交換機判斷消息該轉發到哪個隊列。
  5. 消費者(Consumer):從隊列中獲取并處理消息的應用(如支付系統接收“新訂單”消息并處理支付)。
三、工作流程(核心邏輯)
  1. 生產者發送消息時,會指定消息的“路由鍵”(Routing Key)和目標交換機。
  2. 交換機根據自身類型和“綁定規則”(綁定鍵),將消息轉發到匹配的隊列。
  3. 隊列存儲消息,等待消費者連接并獲取。
  4. 消費者從隊列中取走消息并處理,處理完成后向 RabbitMQ 發送“確認信號(Ack)”,RabbitMQ 收到后刪除隊列中的該消息(避免重復消費)。
一、引入消息隊列的作用

閘機控制涉及設備通信,采用同步調用易受網絡波動影響。引入 RabbitMQ 可實現:

  • 系統解耦:閘機控制服務與設備通信模塊分離,便于獨立擴展。

  • 異步處理:開閘、關閘命令異步發送,不阻塞主線程。

  • 可靠性保障:消息持久化,避免命令丟失。

二、RabbitMQ 核心組件設計

在這里插入圖片描述

  1. 交換機(Exchange)
  • gate.control.exchange:處理閘機控制命令(開閘 / 關閘)。

  • access.record.exchange:處理通行記錄存儲。

  1. 隊列(Queue)
  • gate.command.queue:綁定閘機控制交換機,接收命令。

  • record.save.queue:綁定記錄交換機,異步保存通行信息。

  1. 消息模型
// 閘機命令消息public class GateCommand{public string GateCode { get; set; } // 目標閘機編碼public int CommandType { get; set; } // 1-開閘/0-關閘public DateTime Timestamp { get; set; } = DateTime.Now;}
三、RabbitMQ 集成實現
  1. 安裝依賴
dotnet add package RabbitMQ.Client
  1. 封裝消息服務
public class RabbitMQService : IDisposable{private readonly IConnection _connection;private readonly IModel_channel;public RabbitMQService(string connectionString){var factory = new ConnectionFactory { Uri = new Uri(connectionString) };_connection = factory.CreateConnection();_channel = _connection.CreateModel();// 聲明交換機和隊列_channel.ExchangeDeclare("gate.control.exchange", ExchangeType.Direct, durable: true);_channel.QueueDeclare("gate.command.queue", durable: true, exclusive: false, autoDelete: false);_channel.QueueBind("gate.command.queue", "gate.control.exchange", "gate.command");}// 發送閘機命令public void PublishGateCommand(GateCommand command){var body = Encoding.UTF8.GetBytes(JsonConvert.SerializeObject(command));_channel.BasicPublish(exchange: "gate.control.exchange",routingKey: "gate.command",basicProperties: null,body: body);}// 消費命令(閘機端實現)public void ConsumeGateCommands(Action<GateCommand> handler){var consumer = new EventingBasicConsumer(_channel);consumer.Received += (model, ea) => {var body = ea.Body.ToArray();var command = JsonConvert.DeserializeObject\<GateCommand>(Encoding.UTF8.GetString(body));handler(command);_channel.BasicAck(ea.DeliveryTag, multiple: false);};_channel.BasicConsume(queue: "gate.command.queue", autoAck: false, consumer: consumer);}public void Dispose(){_channel?.Close();\connection?.Close();}}
四、閘機命令處理流程
  1. 驗證通過后,系統向 RabbitMQ 發送開閘命令(CommandType=1)。

  2. 閘機端消費者接收命令,執行物理開閘操作。

  3. 開閘成功后,觸發票證狀態更新回調。

  4. 延遲 5 秒后,系統發送關閘命令(CommandType=0),完成一次控制流程。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/web/92999.shtml
繁體地址,請注明出處:http://hk.pswp.cn/web/92999.shtml
英文地址,請注明出處:http://en.pswp.cn/web/92999.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

Linux 常用命令大全:覆蓋日常 99% 操作需求

1、基本命令 pwd&#xff1a;顯示當前工作目錄的絕對路徑&#xff0c;例如在復雜目錄結構中快速確認位置&#xff0c;執行后會輸出類似/home/user/documents的結果。 cd&#xff1a;切換目錄&#xff0c;cd 目錄路徑可進入指定目錄&#xff0c;cd ~回到當前用戶的家目錄&…

普通電腦與云電腦的區別有哪些?全面科普

近年來&#xff0c;越來越多的人不再購置升級自己的電腦&#xff0c;轉而選擇云電腦&#xff0c;云端產品正在變得越來越普及易用。那么它究竟跟我們的普通本地設備有什么區別吶&#xff1f;或許很多人并不知悉&#xff0c;對此&#xff0c;本篇內容小編就為大家簡要科普一下普…

【Python】支持向量機SVM

示例代碼&#xff1a;import numpy as np import matplotlib.pyplot as plt from sklearn import svm from sklearn.datasets import make_blobs from sklearn.model_selection import train_test_split from sklearn.metrics import accuracy_score, classification_report# 設…

當AI學會“抄近路”:殘差網絡如何突破深度學習的極限

**——解讀《Deep Residual Learning for Image Recognition》**今天我想帶大家回到2015年&#xff0c;見證人工智能領域的一場“捷徑革命”——由何愷明等人提出的**深度殘差學習框架&#xff08;ResNet&#xff09;**。這篇論文解決了困擾AI界多年的“深度詛咒”&#xff0c;…

HCIP--BGP綜合實驗

目錄 BGP綜合實驗報告 一、實驗拓撲 二、實驗要求 三、實驗思路 &#xff08;一&#xff09;IP地址規劃 &#xff08;二&#xff09;整體思路 四、實驗步驟 &#xff08;一&#xff09; IP地址配置 &#xff08;二&#xff09; AS2內部配置OSPF協議 &#xff08;三&a…

Java 基礎編程案例:從輸入交互到邏輯處理

在Java編程學習中&#xff0c;輸入輸出、循環控制和邏輯判斷是核心基礎。本文整理了10個經典案例&#xff0c;涵蓋Scanner輸入處理、斐波那契數列、成績統計、登錄驗證等場景&#xff0c;幫助初學者掌握編程邏輯與實用技巧。 一、Scanner輸入交互&#xff1a;獲取用戶輸入并處理…

LeetCode 面試經典 150_數組/字符串_整數轉羅馬數字(18_12_C++_中等)(模擬)(對各位進行拆解)

LeetCode 面試經典 150_數組/字符串_整數轉羅馬數字&#xff08;18_12_C_中等&#xff09;題目描述&#xff1a;輸入輸出樣例&#xff1a;題解&#xff1a;解題思路&#xff1a;思路一&#xff08;模擬&#xff09;&#xff1a;思路二&#xff08;對各位進行拆解&#xff09;&a…

計算機網絡摘星題庫800題筆記 第6章 應用層

第6章 應用層 6.1 網絡應用的架構 考點 1 CS 架構 題組闖關 1.DNS 是基于 ( ) 模式的分布式系統。 A. C/S B. B/S C. P2P D. 以上均不正確 1.【參考答案】A 【解析】本題考查網絡應用模型。 DNS 作為分布式應用&#xff0c;是一種典型的 C/S 模式&#xff0c;是隨著 Internet 技…

BLUCK電路的輸入電容應該怎么選取

借用TI的BULK芯片討論一下輸入電容怎么選取的問題&#xff0c;BULK電源是我們常用的電源&#xff0c;它的原理請看之前的文章&#xff1a; 高壓差為何不用LDO&#xff1f;DCDC效率更高&#xff01;-CSDN博客 本文我們探討一下輸入電容&#xff0c;輸入電容是控制紋波的關鍵&a…

CAN仲裁機制的原理

我們來詳細講 CAN 仲裁機制 的原理和工作方式,這是 CAN 總線最核心的特性之一。 1?? 基本概念 CAN 總線是 多主機、多節點的串行總線,所有節點共享一根差分信號線(CAN_H / CAN_L)。 每個節點都可以隨時發送消息(多主機機制) 總線只能同時有一個節點成功發送 仲裁 用…

【GPT入門】第46課 vllm安裝、部署與使用

【GPT入門】第46課 vllm安裝、部署與使用 1.準備服務器 2. 安裝 conda環境,隔離base環境 3. vllm使用 3.1 在線推理, openai兼容服務器 3.2 模型離線調用 4. 沒有使用GPU問題分析 1.準備服務器 cuda 版本選12.1 vllm官網介紹: https://vllm.hyper.ai/docs/getting-started/…

【從網絡基礎到實戰】理解TCP/IP協議體系的核心要點(包含ARP協議等其他協議介紹)

前言&#xff1a; 學習計算機網絡不僅是軟件開發的基礎功&#xff0c;更是成為一名合格后端工程師、網絡工程師的重要門檻。本文將基于 TCP/IP 協議體系&#xff0c;系統梳理網絡層、數據鏈路層、以及相關協議的核心知識&#xff0c;并結合實際案例與代碼示例幫助理解。一、網絡…

Python 元類基礎:從理解到應用的深度解析

在 Python 的高級編程中&#xff0c;元類&#xff08;metaclass&#xff09; 無疑是最神秘又最強大的特性之一。它不僅是構建類的“工廠”&#xff0c;更是 Python 靈活對象模型的體現。本文將帶你從基礎概念入手&#xff0c;深入理解元類的本質、工作機制以及實際應用&#xf…

Nginx 配置代理服務器的詳細方法

一、什么是代理服務器&#xff1f; 類型說明正向代理客戶端通過代理訪問目標服務器&#xff08;隱藏客戶端身份&#xff09;反向代理客戶端訪問代理服務器&#xff0c;由代理服務器請求后端服務器&#xff08;隱藏后端服務器&#xff09; 二、Nginx 反向代理配置方法&#xff…

Lombok插件介紹及安裝(Eclipse)

一、Lombok 的用途 Lombok是一個 Java 庫&#xff0c;通過注解的方式簡化 Java 代碼的編寫。它能夠自動生成常見的代碼&#xff0c;如getter、setter、toString、equals、hashCode等方法&#xff0c;從而減少樣板代碼&#xff0c;使代碼更加簡潔、易讀。 Lombok 通過添加**Dat…

硬核操作!Go 語言生成 “會爬墻的清潔機器人”,玻璃外墻自己擦

本文聚焦于利用 Go 語言開發 “會爬墻的清潔機器人” 這一硬核技術&#xff0c;圍繞該機器人如何實現玻璃外墻自主清潔展開。首先介紹開發背景與需求&#xff0c;接著闡述 Go 語言在其中的優勢&#xff0c;詳細講解機器人的核心技術&#xff0c;包括吸附系統、運動控制、清潔機…

Qt——實現”Hello World“、認識對象樹與Qt坐標系

在創建項目時&#xff0c;使用的基類Base Class為QWidget 1. 使用圖形化界面的方式實現“Hello World” 雙擊文件&#xff1a;widget.ui&#xff0c;進入designer模式&#xff1a;在“控件盒子”的“Display Widgets”中找到“Label”&#xff0c;并拖放到白板中雙擊剛剛拖放到…

智能合約開發全流程實戰指南

目錄 靈感探索與概念驗證合約開發常見問題 Hardhat 初始化項目問題合約編譯錯誤處理智能合約設計缺陷 合約測試最佳實踐 單元測試環境配置測試用例編寫技巧測試覆蓋率和策略常見測試失敗原因 合約部署實戰指南 部署到不同網絡部署前準備事項部署后驗證方法部署費用和Gas優化 合…

IPA1299至為芯替代TI ADS1299的腦機接口芯片

在腦機接口、神經科學研究和醫療電子設備領域&#xff0c;腦電信號采集芯片是連接生物電信號與數字世界的重要組件。目前&#xff0c;TI等國際廠商憑借技術優勢占據市場主要份額&#xff0c;國內廠商在成本控制、供貨周期和技術自主性方面面臨挑戰。英集芯推出的IPA1299低噪聲多…

「數據獲取」《中國海洋生態環境狀況公報》(2001-2023年)(獲取方式看綁定的資源)

01、數據簡介在 2023 年的海洋環境監測工作中&#xff0c;監測范圍廣泛且細致。全年對 1359 個海洋環境質量國家控制點位進行了水質監測&#xff0c;這些點位分布在我國管轄的各大海域&#xff0c;能夠全面反映海洋整體水質狀況&#xff1b;對 230 個入海河流國家控制斷面開展監…