通過3個 Hello World 應用來了解 ASP.NET 5 應用是如何執行的(1)

發表於2015-09-28

微軟在開發ASP.NET 5(當時被稱為ASP.NET vNext)是採用的代號為Project K,所以執行時被稱為KRuntime。KRuntime是一個SDK,它包含了編譯和執行應用程式的所有資源。接下來我們通過三個Hello World例項來演示如何利用KRuntime讓我們編寫的應用執行起來。這三個例項如此的簡單,以至於我們根本不需要利用IDE(Visual Studio 2015)來編寫,我們甚至無需安裝VS 2015。

作為第一個Hello World應用,我們會編寫一個包含入口點(Entry Point)的程式,並通過執行KRuntime的K.cmd命令來啟動它。我們先建立一個空的目錄並將其命名為“HelloWorld”,我們接下來建立的三個應用都儲存在這裡。接下來我們建立一個名稱為“Project1”的子目錄,它程式碼了作為第一個Hello World程式的專案,所有相關的原始檔都儲存在這裡。我們直接在Project1目錄下建立一個文字檔案,並將其命名為“Program.cs”。我們直接利用NotePad來編寫這個Program類。如下所示的是這個型別的定義,我們可以看到這個型別中包含了唯一的作為入口點的Main方法(可以定義成例項方法或者靜態方法)。

KRuntime眼中的專案是一個目錄,能夠成為專案的目錄必須具有一個名稱為“project.json”的檔案。這是一個採用JSON格式的文字檔案,與當前專案編譯/執行相關的配置均定義與此。換句話說,我們熟悉不過的web.config在ASP.NET 5專案已經不再需要了,而project.json不僅僅是web.config的替代者,更多的配置資訊被放置在這裡。我們在Project1目錄下新增這樣的project.json檔案。由於我們的應用是如此簡單,我們不需要在此定義任何配置,所以我們將內容定義為“{}”。

到目前為止,我們第一個Hello World就定義好了,現在我們可以執行KRuntime提供的K.cmd以命令列的方式啟動它。KRuntime的核心是KRE(KRuntime Enviroment),不僅多個版本的KRE可以在同一臺機器上並存,同一個應用程式可以採用不同版本的KRE來執行。KRE的安裝、升級和相關設定(比如設定預設的KRE)通過KVM(K Version Manager)來完成。我們可以執行如下命令來下載和執行相應的指令碼來安裝KVM(KVM的安裝時針對當前使用者的,所以需要當前使用者具有Admin許可權)。

成功安裝KVM後,在%USERPROFILE%目錄(預設為“C:\Users\{UserName}”)下會建立一個名為.kre的子目錄,命令檔案“kvm.cmd”被拷貝到其下的“\bin”目錄下。接下來我們以如下的方式執行這個命令並採用upgrade引數來安裝新的KRE或者將對現有的KRE進行升級。

在確保KRE已經安裝在你機器上之後,我們啟動Visual Studio 2015(目前為Preview版本)的命令列工具“Developer Command Prompt for VS 2014”(照理說應該命名為“Developer Command Prompt for VS 2015” 在VS 2015 Preview版本中確實是“2014”)或者直接使用CMD命令列。在將Project1目錄作為當前目錄(執行CD命令)後執行按照如下的形式執行K run命令之後(我將HelloWorld目錄儲存在C:\下),我們的程式被成功執行。

我們在通過執行K run命名啟動程式之前並沒有執行任何編譯操作,所以K run會自動幫助我們對目標專案進行編譯。實際上這是一個動態編譯的過程,具體的編譯是 通過一個名叫Roslyn的編譯器完成的。具體來說,編譯器會將當前目錄(%CD%)作為目標專案的根目錄,根據project.json的設定來選擇相應的原始檔進行編譯。對於我們的程式來說,我們不曾在project.json中定義任何配置,所以目錄下的.cs檔案(Program.cs)會預設作為原始檔編譯到生成的程式集中(程式集會以專案的根目錄進行命名,所以編譯生成的目標程式集名稱為Project1.dll)。

成功編譯之後,目標程式集中的以Program命名的型別被解析出來,定義其中的Main方法將會作為入口程式被執行。具體來說,如果這是一個靜態方法,該方法會被直接執行;如果這是一個例項方法,一個Program物件被建立出來,它的Main方法隨之被執行。關於程式入口的解析,有一點值得提醒一下:一般來說定義在啟動程式中唯一的靜態Main方法會預設作為入口點,但是隻有定義在Program類中的Main方法才會被視為合法的入口點。除此之外,K.cmd並不要求Main方法是靜態的。它也並不要求Program類具有無參建構函式,因為在例項化Program物件的時候,內建的DI容器能夠自動提供相應的引數。

對於上面建立的這個Hello World應用來說,程式入口點由應用自身來提供,所以應用本身具有自我執行的能力。從應用託管(Host)的角度來講,這樣的應用同時負責對自身的託管。將應用與託管環境獨立起來其實是更好的選擇,因為這樣可以使同一個應用執行於不同的環境中。

在下一篇中我們就來演示如何為應用指定入口程式來達到應用與應用託管的分離。

相關文章