Orleans入門例子


Orleans入門例子

  這是Orleans系列文章中的一篇.首篇文章在此

       一.鋪墊。

   雖然是個入門例子,還是需要一些鋪墊。

       Orleans的最小完全體,應該分為2個部分。一個是Orleans客戶端,一個是Orleans服務端,這里為什么要加上“Orleans”這個限定詞語呢?那是因為Orleans的完全體,才是普通意義上的服務端主程。它們共同構成了游戲服務器,網站服務器等等。

在Orleans客戶端中,我們使用GrainClient類以及Grain類,在Orleans服務端內,我們主要使用silo類和grain類。這里要說說Silo類,前面說過Grain類是處於“單線程機制”約束下的類,那么它們運行在哪個地方呢?就是Silo類所在的地方。Silo類是Grain地代碼實際執行的地方,它是Grain類的宿主,它承載着所有的Grain實例,也許是幾百萬個Grain實例。在一些語境下,silo,silohost,以及Orleans服務端,這三個詞語有可能代表同一個意思.

一個外部請求的處理大部分情況下需要很多個Grain實例,進行一連串的方法調用后才能處理完畢,這些Grain實例形成一個處理消息的鏈條,這個消息流走於Grain鏈內直至處理完畢。那么這個消息是如何第一次到達Grain鏈條里呢?GrainClient類的作用就是入口,它通知Silo類,有新消息達到,它需要哪個Grain類實例,需要調用特定的方法等。

       經過以上鋪墊,要想創造一個Orleans完全體,我來用vs2017創建一個解決方案,里面添加4個項目:Client,Host,Grains,IGrains。它們的作用分別解釋如下:

  1. Client:這個顯而易見,里面就是要運行GrainClient的。它要和Host通信,這就要求它引用IGrains項目。這是個控制台項目
  2. Host:這個也是顯而易見,里面就是要運行Silo的。它應該引用Grains項目以及IGrains項目,因為它要承載Grain(這就要求引用Grains類),並且需要Grain實例間的通信(這就要求引用IGrains項目),這是個控制台項目
  3. Grains:這個里面實現所有IGrain載明的接口,實現所有的Grain類,包括它們的方法以及字段。(它要求引用IGrain。。。廢話)這是個類庫項目
  4. IGrains:這里放置所有Grains類要擴展的接口。這是個類庫項目。

  同時為了使用Orleans框架,我們還需要引用Orleans的類庫,官方教程里有方案,不過,我們采用簡單的辦法,統一引用一個類庫集合,下文有述。

  好吧,以上解釋不管懂與不懂,你就暫且記下,先按照步驟一步一步來吧。也許某個階段,你就突然懂了。我相信在讀的各位對這種醍醐灌頂的感覺一定不陌生。

 

  按照以上套路,我開始了我的工作,我打算跟世界say Hi:

  二.創建

  我創建了四個項目的解決方案,它長成這個樣子,注意它們的.net框架版本都是4.6.1:

  

 

 

  好了我們要引用Orleans類庫啦,說了半天,終於要主角登場啦,好激動,所以我nuget引用了Microsoft.Orleans.Server,它長這樣子:

  

 

 

  里面沒有實際內容,我現在先弄IGrains,它很簡單,就一個接口一個方法:長成這樣:

  

 

 

  我再弄Grains項目:它就是要實現IGrains項目里的接口,所以先引用哪個項目,然后實現它,長這樣子。

  

 

 

  我再實現Client項目,它需要引用IGrains項目,它長這樣子:

  

 

 

  最后是Host類,它長這樣子:

   

 

 

  現在我高興的運行這個Orleans完全體,它再一連串的日志記錄之后,跳出了 hello world如下圖

 

 

  …我成功地創造了Orleans地完全體。好了全系列文章到此結束。

  再見

 

 

 

 

 

 

 補充

  噢,我還需要補充一下下。

  搞了半天,鬧這么大動靜,就寫了個簡版的WCF?並不是,這里只是展示了碼Orleans的主要步驟。這里有幾個要點需要解釋一下:

 

1.IGrains的所有接口方法,必須是返回Task類的。這個是必須的,因為Orleans的“單線程機制”,是建立在Task類之上的。它是利用TaskScheduler類,實現“單線程機制”的。啥?有人問怎么實現的?你確信自己入門教程還沒有看完就想知道?…以后再說吧。反正接口的方法,必須是返回Task。

2.IGrains接口擴展自IGrainWithInteger接口,這個IGrainWithInteger接口是Orleans提供的,之前說過,Grain實例之間需要通信,這就需要彼此區分,要有各自的主標識。這個接口,就規定了主標識是長整數(名字是整數,但是實際上是長整數)。Grain實例的主標識還可以是其他類型:比如字符串和Guid等等。

3.Grains項目中,實現了我規定的接口,就表明自己的主標識是長整數,它又擴展自Grain類,就表明自己受“單線程機制”約束了
4.Host項目,只是引用了Grains項目,但是沒有再代碼中具體使用。它如何知道自己要承載哪些Grain類?Host利用反射檢查所有目錄里的類庫文件,如果找到grain類,它就加載,並管理起來
5.GrainClient有靜態的,有動態的類,我這里先使用靜態類講解。動態類其實一樣。我調用的時候,使用一個參數“12345”。就是要告訴Host。我要激活主標識是12345的Grain類實例。然后又調用了它的say方法。它聰明的再host的控制台窗口打印出say hello。

 

   

  到現在,我們就明白了,再Orleans的世界里,給grain發送消息,實質上是調用對應的接口,grain實例接收到消息以后,使用對應的方法進行處理。(吃瓜群眾:這不就是一個RPC框架嘛…呵呵。)

  在這個簡單的例子里,展現出的東西還有很多,不過今天很晚了,打完收工。明天繼續說說這個例子展現的內容。

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM