2017-05-29 222 views
3

我目前有一個服務結構應用程序由多個服務組成。我試圖實現的是排隊機制,因此一個服務可以將消息發佈到隊列,而另一個服務可以接收來自同一隊列的消息。Azure服務結構服務間通信

下不工作(用於監聽的服務,沒有什麼出隊):

PublisherService

protected override async Task RunAsync(CancellationToken cancellationToken) 
{ 
    var myQueue = await StateManager.GetOrAddAsync<IReliableQueue<string>>("fooQueue"); 
    while (true) 
    { 
     cancellationToken.ThrowIfCancellationRequested(); 
     using (var tx = this.StateManager.CreateTransaction()) 
     { 
      // Put some message in the queue 
      await myQueue.EnqueueAsync(tx, "Foobar"); 

      await tx.CommitAsync(); 
     } 

     await Task.Delay(TimeSpan.FromSeconds(1), cancellationToken); 
    } 
} 

ListenerService

protected override async Task RunAsync(CancellationToken cancellationToken) 
{ 
    var myQueue = await StateManager.GetOrAddAsync<IReliableQueue<string>>("fooQueue"); 
    while (true) 
    { 
     cancellationToken.ThrowIfCancellationRequested(); 
     using (var tx = this.StateManager.CreateTransaction()) 
     { 
      var result = await myQueue.TryDequeueAsync(tx); 

      if (result.HasValue) 
      { 
       ServiceEventSource.Current.ServiceMessage(this.Context, "New message receieved: {0}", result.Value.ToString()); 
      } 

      await tx.CommitAsync(); 
     } 

     await Task.Delay(TimeSpan.FromSeconds(1), cancellationToken); 
    } 
} 

它看起來像隊列範圍僅限於一個服務。這似乎不是文檔中指定的限制。

所以我的問題是:

  • 是這個實際上一些無證的限制?
  • 或者在上面的代碼中有什麼錯誤?
  • 我怎麼能實現上面的場景(一個服務將消息添加到隊列中,另一個服務從同一隊列中檢索消息)?

很顯然,我可以使用Azure的服務總線,但我不能有以下幾個原因:

    在我的實際真實世界的場景
  • ,我將有幾個隊列(可變數目),所以它會需要按需創建服務總線隊列(這不完全是一個快速操作)
  • 增加了一個依賴於另一個Azure的服務(這樣增加了整個系統的失效概率)
  • 花費更多
  • 更復雜的部署

回答

3

ReliableQueues是本地的服務肯定的,因爲它的目的是保存狀態特定的服務。該狀態被複制到其他實例。這就像在.Net中正常的System.Collections.Generic.Queue<T>

對於低成本解決方案,也許您可​​以使用Azure Storage Queues。是的,它增加了依賴性,但它具有高可用性。這是一個折衷,只有你可以決定接受與否。

在另一方面,認爲開箱:

創建多個ReliableQueues有狀態服務和公開方法等服務可以調用使用備用遠程通信,如:

class QueuingService 
{ 
    void AddToQueue<T>(string queuename, T input) { .. } 
    void DeQueue(string queuename) { .. } 
} 

這將創建當然依賴性,但它具有Service Fabric提供的所有安全機制,並且不會花費太多。但是,再次,你正在自己建造一個窮人的服務公共汽車/天藍色的存儲隊列。

關於文檔,沒有它不會是這麼說的很多話,一個可靠的隊列綁定到1個服務,但你如何解釋this

服務織物提供可用於有狀態的編程模型,它取決於。通過可靠集合的.NET開發人員。具體來說,Service Fabric提供可靠的字典和可靠的隊列類。當你使用這些類,你的狀態(我的解釋:該服務的狀態)劃分(可伸縮性),複製(可用性)和分區(ACID語義)內辦理。

+0

謝謝,這是有道理的。我不確定我會選擇哪種方式(Azure存儲隊列或遠程通信)。每個人都有自己的優點/缺點。再次感謝,這非常有幫助。 – ken2k

+0

但話又說回來,你正在建設一個貧窮的芒服務總線/ Azure存儲隊列自己。 - 這意味着這不是使用ReliableQueue的正確方法嗎? – AsValeO

+1

@AsValeO你的意思是「正確的方式」。如果您將它用於其設計用途:將數據存儲在使用位置,即位於單一有狀態服務中。你不能把它變成別的東西,就像一個跨多個服務的隊列一樣。 –

1

如果添加了故障處理重試模式所有的調用代碼,你不應該需要在您的通話之間的隊列,看https://docs.microsoft.com/en-us/azure/service-fabric/service-fabric-reliable-services-communication

相關部件從鏈接在這裏:

異常處理程序負責確定發生異常時要採取的操作。異常分爲可重試和不可重試。 不可重試的異常只是重新返回給調用者。 可重試異常進一步分爲瞬態和非瞬態。 短暫的例外是那些可以簡單而不需要重新解析服務端點地址重試。這些將包括瞬時網絡問題或服務錯誤響應,而不是那些表明服務端點地址不存在的服務錯誤響應。 非暫時性異常是那些需要重新解析服務端點地址的異常。其中包括表明服務端點無法到達的異常,表明服務已移至其他節點。你的答案

+0

雖然此鏈接可能回答這個問題,最好在這裏包含答案的重要部分,並提供參考鏈接。如果鏈接頁面更改,則僅鏈接答案可能會失效。 - [評分](/審查/低質職位/ 17388453)從引用鏈接 – marsze

+0

添加文字,感謝@marsze – Robert