簡體   English   中英

如何使用 pika 和 rabbitmq 的多線程來執行請求和響應 RPC 消息

[英]how to use multithreading with pika and rabbitmq to perform Requests and Responses RPC Messages

我正在使用 Rabbitmq 進行一個項目,我正在使用 RPC 模式,基本上我正在接收或使用來自隊列的消息,進行一些處理,然后發送回響應。 我使用 Pika,我的目標是為每個任務使用一個線程,因此對於每個任務,我將專門為該任務創建一個線程。 我還讀到,最佳實踐是只建立一個連接,並根據需要建立多個通道,但我總是收到此錯誤:
'start_sumption 不能從' pika.exceptions.RecursionError 的范圍內調用:start_sumption 不能從另一個 BlockingConnection 或 BlockingChannel 回調的范圍內調用。

我做了一些研究,發現 Pika 不是線程安全的,我們應該為每個線程使用一個獨立的連接和一個通道。 但我不想這樣做,因為它被認為是不好的做法。 所以我想在這里問一下是否有人已經實現了這項工作。 我還讀到,如果我不使用 BlockingConnection 來實例化我的 Connection 並且有一個名為 add_callback_threadsafe 的函數可以使這成為可能。 但不幸的是沒有示例,我閱讀了文檔,但它很復雜,如果沒有示例,我很難理解他們想要描述的內容。

我的嘗試是聲明兩個類。 每個類將代表一個任務執行器,它接收或使用來自隊列的消息,並基於此進行一些處理並返回響應。 我的想法是在兩個任務之間共享一個rabbitmq 連接,但每個任務都會獲得一個獨立的通道。 在上面的代碼中,傳遞給函數的 rabbit 參數是一個類,其中包含一些變量,如 Connection 和其他函數,如 EventSubscriber,當調用它時,它將分配一個新的 Channel 並開始使用來自該特定交換和 routingKey 的消息。 接下來我聲明一個線程並將訂閱或消費函數作為該線程的目標。 另一個任務類看起來也和這個類一樣,這就是為什么我只上傳這個代碼。 在主類中,我與 rabbitmq 建立連接,並將其作為參數傳遞給兩個任務類的構造函數。

On_Deregistration 類:

def __init__(self, rabbit):
   self.event(rabbit) # this will call event function and pass the connection shared between all Tasks. rabbit parameter hold a connection to rabbitmq

def event(self, rabbit):
 
    self.Subscriber = rabbit.EventSubscriber(rabbit,  'testing.test',  'test', False,  onDeregistrationFromHRS # this func is task listener)

def subscribeAsync(self):
    self.Subscriber.subscribe() # here i call start_consuming

def start(self):
    """start Subscribtion in an Independant Thread  """
    thread = threading.Thread(target = self.subscribeAsync )  
    thread.start()
    if thread.isAlive():
        print("asynchronous subscription started")

主課:

類應用程序:

def __init__(self):

    self.rabbitMq = RabbitMqCommunicationInterface(host='localhost', port=5672)
    firstTask =  On_Deregistration(self.rabbitMq)
    secondTask =  secondTask(self.rabbitMq)

應用程序 = 應用程序()

錯誤:'start_sumption 可能無法從 ' 的范圍內調用

pika.exceptions.RecursionError: start_sumption 不能從另一個 BlockingConnection 或 BlockingChannel 回調的范圍內調用

我搜索了這個錯誤的原因,顯然 pika 不是線程安全的,但必須有一個解決方案。 也許不使用 BlockingConnection ? 也許有人可以給我一個如何做到這一點的示例,因為我嘗試過但沒有奏效。 也許我錯過了一些關於如何使用 rabbitmq 實現多線程的信息

所以經過長時間的研究,我發現 Pika 不是線程安全的。 至少就目前而言,也許在新版本中它將是線程安全的。 所以現在對於我的項目,我停止使用 Pika 而我使用的是b-rabbit ,它是 Rabbitpy 周圍的線程安全包裝器。 但我必須說 Pika 是一個很棒的庫,我發現 API 的描述和結構比 rabbitpy 更好,但是對於我的項目來說,必須使用多線程,這就是為什么 Pika 目前是一個糟糕的選擇。 我希望這對未來的人有所幫助

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM