2013-08-07 25 views
0

我已經瀏覽了rabbitMQ插件的優秀文檔。但是,我仍然對一些事情感到困惑。如何使用rabbitMQ插件和grails發送和接收域對象

方案

我的應用程序將需要來自用戶的文件上傳,做各種事情的文件和相應的域對象上設置的某些屬性。這些工作中的一部分可能是勞動密集型的,所以我正在使用隊列。我設想請求排隊,消費者從隊列中提取請求並使用它們。

問題

我要存儲在隊列中的域對象。我這樣做:rabbitSend 'myqueue', colorObjcolorObj是域類的一個對象Color 但是,在ColorServicehandleMessage(...)當我從隊列中獲取項目時,該項目的類型不是Color。請注意,在RabbitMQ的儀表板,我可以看到在插入到隊列中的項目,所以在config.groovy我的隊列開始是好的(我用amq.direct

  • 我怎麼能發送和從隊列中取出一個域對象?
  • 從我目前看到的行爲來看,handleMessage不需要實例化。即使我沒有撥打ColorService,它仍然會自行執行handleMessage。這是一種正常的行爲?

下面是代碼:

控制器

Color colorObj = colorService.newRequest(params, request.getFile('color.filename') 
if (colorObj.validate) 
    rabbitSend 'myqueue', colorObj 
... 

服務

class ColorService { 
    static rabbitQueue = 'myqueue' 

    void handleMessage(message) { 
    println "came in message: " + message instanceof Color //this prints false 
    } 
} 

回答

1

,因爲它表明in the documentation,您可以發送StringMap

爲什麼不派id你的域對象:

rabbitSend 'myqueue', colorObj.id 

然後,加載它回來時,被處理的消息:

void handleMessage(message) { 
    println "Got ${Color.get(message)}" 
} 

或者,如果您不需要直到消息被處理,發送一個所有需要的數據的映射,並讓服務在成功處理後創建域對象?

2

正如蒂姆所說,如果你可以通過只傳遞最簡單的域實例ID。在消息傳輸過程中,您需要小心對域實例的更改。

或者,如果它是你感興趣的數據,我寧願連載的對象爲JSON使用類似

rabbitSend 'myqueue', (colorObj as JSON).toString() 

當然,現在的東西你的聽衆正在接收一個字符串,所以你必須將其轉換回來:

void handleMessage(String message) { 
    def color = new Color(JSON.parse(message)) 
    println "came in message: " + color instanceof Color 
} 

GPRABBITMQ-15 issue上有一點關於此的討論。

+0

太好了,我會試試這個ID,因爲這是最簡單的方法。另外,我是否明白,我的理解是,服務類中的'handleMessage'不需要實例化?我看到的行爲是,當我排隊時,服務的handlemessage可以不用我甚至實例化服務 – Anthony

+0

正確,插件會自動實例化'ColorService'並將它附加到消息偵聽器容器,因爲'static rabbitQueue'屬性。 –