Blazor Server 和 WebAssembly 應用程式入門指南

Blazor Server 和 WebAssembly 應用程式入門指南

如果您一直緊跟 .NET 世界的最新發展趨勢,那麼現在您一定聽說過 Blazor。

最後更新 2021/12/9 下午9:25
技术译民
預計閱讀 15 分鐘
分類
Blazor
標籤
.NET C# Blazor

翻譯自 Waqas Anwar 2021 年 3 月 12 日的文章 《A Beginner’s Guide To Blazor Server and WebAssembly Applications》

A-Beginner-Guide-To-Blazor-Server-and-WebAssembly-Applications

如果您一直緊跟 .NET 世界的最新發展趨勢,那麼現在您一定聽說過 Blazor。目前在 .NET 社群中有很多關於 Blazor 的宣傳,這種宣傳最常見的原因是它引入了一些大多數 .NET 開發人員十幾年來一直夢寐以求的東西,即:既可以在伺服端又可以在瀏覽器中執行 C# 的能力。Blazor 允許我們使用 HTML、CSS 和 C#(而不是 JavaScript)來建構互動式 Web 應用程式。在本教學中,我將介紹 Blazor 的基本概念,並概述可用於 Blazor 的不同代管模型。我還會介紹每種代管模型的優缺點,以便您可以為下一個 Blazor 專案代管模型做出最佳的決定。

Blazor 是什麼?

Blazor 是一個免費、開源的單頁應用程式(SPA)開發框架,使開發人員能夠在伺服端和用戶端上使用 C# 建構互動式 Web 應用程式。Blazor 不需要在用戶端上安裝任何外掛程式來在瀏覽器中執行 C#/.NET 程式碼。它使用 WebAssembly 執行 .NET 程式碼,WebAssembly 是所有主流瀏覽器都支援的 Web 標準。Blazor 還可以在伺服端執行 .NET 程式碼並建構 UI,然後透過 SignalR 連線僅將更新的 DOM 傳輸到用戶端。

BLAZOR

WebAssembly 是什麼?

WebAssembly(有時簡寫為 Wasm)是一種可攜式的二進位格式(低階指令集),被設計用於在任何能夠解釋這些指令的主機上執行。WebAssembly 的主要目標是允許開發人員建構高效能的 Web 應用程式,但其格式也被設計為可執行於和整合到其他環境中。WebAssembly 目前受到了所有主流瀏覽器的支援,比如 Chrome、Android 版 Chrome、Edge、Firefox、Safari、Opera 等。

WebAssembly

Blazor 代管模型

Blazor 元件模型是 Blazor 的核心,它的設計方式使計算 UI 變更和呈現 UI 彼此分離。 這就是為什麼無論您使用何種方式渲染您的應用程式,基本的元件模型都保持不變的原因。 在撰寫本文時,有四種渲染/代管模型可用,它們都處於不同的開發階段。

  1. Blazor Server
  2. Blazor WebAssembly
  3. Blazor Electron
  4. Mobile Blazor Bindings

Blazor Electron 和 Mobile Blazor Bindings 目前處於實驗階段,Microsoft 尚未承諾發佈這些代管模型,因此我不會在本文中討論它們。

Blazor Server App 是什麼?

Blazor Server 應用程式在伺服器上執行,可享受完整的 .NET Core 執行階段支援。所有處理都在伺服器上完成,UI/DOM 變更透過 SignalR 連線回傳給用戶端。這種雙向 SignalR 連線是在使用者第一次從瀏覽器中載入應用程式時建立的。 由於 .NET 程式碼已經在伺服器上執行,因此您無需為前端建立 API。您可以直接存取服務、資料庫等,並在傳統的伺服器端技術上做任何您想做的事情。

Blazor-Server-Apps

§何時使用 Blazor Server

  1. 當您想在完整的 .NET Core 執行階段上執行應用程式時
  2. 當您想要保持應用程式的初始下載大小非常小時
  3. 當您想保持應用啟動時間非常快時
  4. 當您想把應用程式的程式碼保留在伺服器上,而不希望它被下載到用戶端時
  5. 當您想要一個快速的應用開發週期,而現有的 .NET 開發人員幾乎不需要學習曲線時
  6. 當您想讓您的應用對搜尋引擎友好時
  7. 當您希望應用程式在舊的瀏覽器上執行,而不依賴於 WebAssembly 時
  8. 當您想在 Visual Studio 中像偵錯普通 .NET 應用程式一樣偵錯 .NET 程式碼時
  9. 當您想要建構內部網路或低需求的對公眾應用程式時

§何時不要使用 Blazor Server

  1. 當您的應用程式在高延遲環境中執行時
  2. 當您希望您的應用程式離線工作,而不需要一個與伺服器的固定 SignalR 連線時
  3. 當您不想增加伺服器資源以回應大量連線的 SignalR 用戶端時

Blazor WebAssembly App 是什麼?

這種代管模型是現代流行的 SPA 框架(比如 Angular、Vue 和 React)的直接競爭對手,也是大多數開發人員有興趣學習 Blazor 的主要原因。它允許開發人員使用 C# 取代 JavaScript 編寫所有前端 UI 邏輯。在這種代管模型中,第一次請求時,會將應用程式的 DLL 及其所有相依性和小尺寸的 Mono .NET 執行階段下載到用戶端。然後,用戶端中的 Mono 執行階段就會載入並執行應用程式程式碼。Blazor WebAssembly 程式可以用 C、C# 等其他語言編寫,然後編譯成 WebAssembly 位元組碼。

Blazor-WebAssembly-Apps

§何時使用 Blazor WebAssembly

  1. 當您想要將整個應用程式編譯為靜態檔案,並將它們提供給用戶端,而不需要伺服器上的 .NET 執行階段時。這意味著您的後端可以用 PHP、Node 或 Rails 編寫,並服務於用 Blazor 編寫的前端應用程式。
  2. 當您想要建構可以在用戶端離線執行而無需持續連接到伺服端的應用程式時。
  3. 當您想要將處理轉移到用戶端並減少伺服端的負載時。
  4. 當您想在用戶端和伺服端之間共用程式碼和函式庫時。

§何時不要使用 Blazor WebAssembly

  1. 當由於下載到用戶端的檔案/DLL 太多,而您無法在有效負載上妥協時。
  2. 當您無法在緩慢的啟動時間上(特別是在網路連線不佳的情況下)妥協時。
  3. 當您無法妥協於應用程式必須執行在具有完整的安全限制的瀏覽器沙箱環境中時。

為了更好地理解 Blazor 代管模型,讓我們在 Visual Studio 2019 中分別建立一個 Blazor Server 和 Blazor WebAssembly 應用程式。

在 Visual Studio 2019 中建立 Blazor Server 應用

打開 Visual Studio 2019 並點擊建立新專案。從可用的範本清單中選擇 Blazor App 範本並點擊下一步。

Create-New-Blazor-App-Project-in-Visual-Studio-2019

指定專案名稱(比如 BlazorServerApp)並點擊下一步。您將看到下面的對話方塊,詢問您選擇要建立的 Blazor 應用程式的類型。我們要建立 Blazor Server 應用,所以請選擇 Blazor Server App 並點擊 建立 按鈕。

Blazor-Server-App-in-Visual-Studio-2019

Visual Studio 將為我們建立一個 Blazor Server 應用程式,其中在方案總管中包含以下資料夾和檔案。

Blazor-Server-App-in-Solution-Explorer

讓我們來討論一下 Blazor Server App 中可用的一些重要檔案和資料夾。

§Program.cs

這個檔案包含 Main 方法,它是專案的進入點。Main 方法中呼叫 CreateHostBuilder 方法,為我們設定預設的 ASP.NET Core 宿主。

public class Program
{
    public static void Main(string[] args)
    {
        CreateHostBuilder(args).Build().Run();
    }

    public static IHostBuilder CreateHostBuilder(string[] args) =>
        Host.CreateDefaultBuilder(args)
            .ConfigureWebHostDefaults(webBuilder =>
            {
                webBuilder.UseStartup<startup>();
            });
}

§Startup.cs

它與我們在標準 ASP.NET Core 專案中使用的檔案相同。需要重點注意的一點是 ConfigureServices 方法中呼叫了 AddServerSideBlazor,該方法新增 Blazor Server App 相關的服務。

public void ConfigureServices(IServiceCollection services)
{
    services.AddRazorPages();
    services.AddServerSideBlazor();
    services.AddSingleton<weatherforecastservice>();
}

在此檔案的 Configure 方法中我們還有以下兩行重要的程式碼。MapBlazorHub 方法設定 Blazor Server App 所需的 SignalR Hub Endpoints。MapFallbackToPage 方法會將所有未與任何控制器、razor 頁面等匹配的請求對應到 _Host 頁面,這將允許所有動態內容請求路由到 SPA 框架,而不是拋出 404 Not Found。

app.UseEndpoints(endpoints =>
{
    endpoints.MapBlazorHub();
    endpoints.MapFallbackToPage("/_Host");
});

§_Host.cshtml

這是應用程式的根頁面,每個 Razor 元件/頁面都將在此 host 頁面中呈現。它具有基本的 HTML 元素,例如 html、head 和 body,以及一些特殊元素。請注意,Blazor 是一個基於元件的框架,Blazor 中的每一內容都是一個元件。<component> 指定了我們想讓應用程式根元件呈現的位置。

<component type="typeof(App)" render-mode="ServerPrerendered"></component>

該檔案還在末尾注入了 blazor.server.js 檔案,此 JavaScript 檔案包含設定 SignalR 連線到伺服端的程式碼。此連線在瀏覽器載入應用程式後立即建立,然後被用於伺服端和用戶端瀏覽器之間的即時通訊。如果您想瞭解有關 SignalR 的更多知識,請閱讀我的文章 Display Live Sports Updates using ASP.NET Core SignalR

<script src="_framework/blazor.server.js"></script>

§App.razor

這是 Blazor App 的主要元件,其主要工作是攔截路由並呈現 FoundNotFound 元件。 如果找到與路由匹配的元件,則呈現 Found 元件,如果未找到匹配的元件,則呈現 NotFound 元件。

<Router AppAssembly="@typeof(Program).Assembly" PreferExactMatches="@true">
  <Found Context="routeData">
    <RouteView RouteData="@routeData" DefaultLayout="@typeof(MainLayout)" />
  </Found>
  <NotFound>
    <LayoutView Layout="@typeof(MainLayout)">
      <p>Sorry, there's nothing at this address.</p>
    </LayoutView>
  </NotFound>
</Router>

§MainLayout.cshtml

MainLayout 檔案包含應用程式的主版面配置,其標記可以被多個 Razor 元件共用。這個版面配置元件通常包含應用程式的常見 UI 元素,例如頁首、功能表、頁尾、側邊欄等。為我們產生的預設 MainLayout 有一個側邊欄,用來渲染 NavMenu 元件,它還使用 Razor 語法 @Body 來指定其他元件的內容將在版面配置標記中呈現的位置。

@inherits LayoutComponentBase

<div class="page">
  <div class="sidebar">
    <NavMenu />
  </div>

  <div class="main">
    <div class="top-row px-4">
      <a href="https://docs.microsoft.com/aspnet/" target="_blank">About</a>
    </div>

    <div class="content px-4">@Body</div>
  </div>
</div>

§wwwroot 資料夾

該資料夾包含靜態檔案,例如圖片、字型、圖示、CSS 和 JavaScript 檔案等。

§Pages 和 Shared 資料夾

該資料夾包含我們之前討論過的 _Host.cshtml 檔案以及一些 Razor 元件。Blazor 應用程式是具有 .razor 副檔名的 Razor 元件的集合。其中一些元件稱為可路由元件,因為可以使用其路由存取它們。例如,當我們導覽到應用程式根 URL 時,將呈現下面的 Index.razor 元件。該 URL 是使用 Index.razor 元件頂部的 @page 指令指定的。

§Index.razor

@page "/"

<h1>Hello, world!</h1>

Welcome to your new app.

<SurveyPrompt Title="How is Blazor working for you?" />

請注意,上面的頁面還使用了一個子元件 SurveyPrompt,之所以稱它為子元件,是因為它沒有 @page 指令,它可以被嵌入到其他元件中。

Pages 資料夾中還有一些其他的 razor 元件,這些元件都可以使用檔案頂部指定的路徑進行存取。例如,當我們導覽到 /counter 路徑時,Counter 元件將呈現。類似地,FetchData 元件將使用 /fetchdata 路徑呈現。

Razor Server 應用程式還有一個包含共用元件的 Shared 資料夾。這些元件可以被整個應用程式中的任何元件使用,就像我們上面看到的 SurveyPrompt 元件一樣。Shared 資料夾中另一個有趣的共用元件是 NavMenu 元件,它呈現 Blazor Server 應用程式的頂部導覽列。

§_Imports.razor

該檔案類似於我們在 ASP.NET MVC Web 應用程式中的 _ViewImports.cshtml 檔案,它包含我們可以在不同 razor 元件中使用的命名空間清單。在 _Imports.razor 檔案中宣告所有這些命名空間的好處是我們不需要在每個 razor 元件中重複引入它們。

@using System.Net.Http @using Microsoft.AspNetCore.Authorization @using
Microsoft.AspNetCore.Components.Authorization @using
Microsoft.AspNetCore.Components.Forms @using
Microsoft.AspNetCore.Components.Routing @using
Microsoft.AspNetCore.Components.Web @using
Microsoft.AspNetCore.Components.Web.Virtualization @using Microsoft.JSInterop

現在是時候執行我們的 Blazor Server 應用程式並在瀏覽器中查看它的運作情況了。在 Visual Studio 中按 F5,您將看到一個漂亮的預設 Blazor Server 應用程式。試試從側邊欄導覽到不同的頁面,並嘗試在 Counter 頁面上使用計數器,您會注意到沒有頁面重新整理或回傳到伺服器。一切都像經典的 SPA 那樣流暢和快速,瀏覽器和伺服端的所有通訊都是使用 SignalR 連線進行的。

Default-Blazor-Server-App-Running-in-Browser

您也可以打開瀏覽器開發者工具,您會注意到所有標準的 CSS 和 JavaScript 檔案(包括 blazor.server.js 檔案)都下載到了用戶端,並透過 Web Sockets 建立了一個 SignalR 連線。

Blazor-Server-App-Files-in-Browser-Developer-Tools

在 Visual Studio 2019 中 建立 Blazor WebAssembly 應用

我們已經瞭解了 Blazor Server App 的基礎知識,並在瀏覽器中看到了它的運作情況。現在讓我們建立一個 Blazor WebAssembly App,以便我們可以理解它們的不同之處。按照我們上面提到的相同步驟,並使用 Blazor App 範本在 Visual Studio 中建立一個新的 Blazor 應用程式。當您被詢問選擇 Blazor App 的類型時,這次需要選擇 Blazor WebAssembly App

Create-Blazor-WebAssembly-App-in-Visual-Studio-2019

Visual Studio 將為我們建立一個 Blazor WebAssembly 應用程式,其中在方案總管中包含以下資料夾和檔案。

Blazor-Client-App-in-Solution-Explorer

您可以輕鬆發現這兩種類型的應用程式之間的一些差異。例如,在 Blazor WebAssembly 應用程式中沒有以下檔案:

  1. _Host.cshtml
  2. Error.cshtml
  3. Startup.cs
  4. appsettings.json

§index.html

在 Blazor WebAssembly 應用程式中,我們會在 wwwroot 資料夾中有一個 index.html 檔案,作為主頁面, 該檔案在末尾注入了 blazor.webassembly.js 檔案,此檔案由框架提供以處理下載 .NET 執行階段、Blazor 應用程式及其所有相依性。它還包含為了執行應用而初始化執行階段的程式碼。

§Program.cs

在 Blazor WebAssembly 應用程式中,應用程式的根元件在 Program.cs 檔案中的 Main 方法中指定。應用程式的根元件是 App.razor,你可以看到它是如何被新增到 RootComponents 集合中的。

public class Program
{
    public static async Task Main(string[] args)
    {
        var builder = WebAssemblyHostBuilder.CreateDefault(args);
        builder.RootComponents.Add<app>("#app");

        builder.Services.AddScoped(sp => new HttpClient { BaseAddress = new Uri(builder.HostEnvironment.BaseAddress) });

        await builder.Build().RunAsync();
    }
}

在 Visual Studio 中按 F5,您將看到一個相似的 Blazor WebAssembly 應用程式。嘗試從側邊欄導覽到不同的頁面,並嘗試像之前在 Blazor Server App 中所做的那樣在 Counter 頁面上使用計數器。 一切看起來感覺一模一樣,也沒有伺服器端回傳。

Default-Blazor-Server-App-Running-in-Browser

正如我們已經知道的那樣,Blazor WebAssembly 應用程式會在用戶端下載應用程式及其所有相依性,因此如果您打開瀏覽器開發者工具,會看到用戶端下載了大量 DLL(只會在第一次瀏覽時下載)。

Blazor-Client-App-Files-in-Browser-Developer-Tools

以上所有檔案只會在第一次請求時下載,然後它們被快取在瀏覽器中。如果您再次重新整理頁面,將會看到這一次下載的檔案很少。

Blazor-Client-App-Files-in-Browser-Developer-Tools-Second-Request

總結

在本文中,我試圖為您介紹 Blazor SPA 框架的基本概念,我們看到了兩個 Blazor 應用程式使用兩種不同的代管模型進行代管。因為 Blazor 框架嚴重依賴於 razor 元件,所以兩個專案中的大部分程式碼和檔案都是相同的。這些元件是 Blazor 應用程式的建構區塊,無論使用哪種代管模型,我們都可以以相似的方式建構這些元件。如果您喜歡本文,請分享它並傳播知識。

作者: Waqas Anwar

翻譯: 技術譯站

連結: 英文原文

繼續探索

延伸閱讀

更多文章
同分類 / 同標籤 2024/2/29

Winform中也可以這樣做資料展示

在做winform開發的過程中,經常需要做資料展示的功能,之前一直使用的是gridcontrol控制項,今天想透過一個範例,跟大家介紹一下如何在winform blazor hybrid中使用ant design blazor中的table元件做資料展示。

繼續閱讀
同分類 / 同標籤 2024/2/29

Winform的介面也可以變好看?

前幾天跟大家介紹了在winform中使用blazor hybrid,而且還說配上blazor的UI可以讓我們的winform程式設計的更加好看,接下來我想以一個在winform blazor hybrid中繪圖的範例來進行說明,希望對你有所幫助。

繼續閱讀