如何在 Web 窗体中嵌入和使用 Blazor WebAssembly?

How to embed and use Blazor WebAssembly in Web Forms?

有一个 Web 窗体应用程序,我想通过将 Blazor 嵌入到 Web 窗体页面中,逐页逐步移植到 Blazor WebAssembly Angular。

将 Blazor 应用程序发布到名为“Blazor”的子目录下的 Web 窗体项目。如果我 运行 Web Forms 应用程序并点击 http://localhost:1234/Blazor,Blazor 应用程序 运行 没问题(在编辑 Blazor index.html => <base href="/Blazor/" />).但是,当我尝试将 Blazor 嵌入 Web 窗体页面时,它不起作用。 Web 表单页面 asp:content 包含 Blazor index.html 页面包含的内容:

<%@ Page Title="EmbedTest" Language="C#" MasterPageFile="~/Site.Master" AutoEventWireup="true" CodeBehind="EmbedTest.aspx.cs" Inherits="WebFormBlazor.EmbedTest" %>

<asp:Content ID="BodyContent" ContentPlaceHolderID="MainContent" runat="server">
    <app>Loading...</app>

    <div id="blazor-error-ui">
        An unhandled error has occurred.
        <a href="" class="reload">Reload</a>
        <a class="dismiss"></a> 
    </div>

    <script src="/Blazor/wwwroot/_framework/blazor.webassembly.js"></script>
</asp:Content>

当我访问 http://localhost:1234/EmbedTest 时,页面显示: 加载中... 发生了未处理的错误。重新加载

并且在控制台中出现以下错误消息: 未捕获的语法错误:意外的标记“<”blazor.webassembly.js:1

这种方法确实适用于 Angular。我在尝试使用 Blazor WebAssembly 时错过了什么?

更新: 根据 Magoo 先生的说法,它不是在下载 blazor.webassembly.js,而是在下载解释错误消息的 index.html。

在 Web 表单页面中将页面中的路径从 /Blazor/wwwroot/_framework/blazor.webassembly.js 更改为 /Blazor/_framework/blazor.webassembly.js,现在下载脚本但遇到新错误。为 blazor.boot.json.

提供 404 未找到

Blazor.webassembly.js 不知道基本 href 应该是 /Blazor/ 并尝试从 localhost:1234/_framework/blazor.boot.json 获取 blazor.boot.json 而不是 localhost:1234/Blazor/_framework/blazor.boot.json.

那么下一期:如何告诉 blazor.webassembly.js 它的基本 href 应该是除“/”之外的其他内容(在我的例子中是“/Blazor/”)?

获得概念验证:

  1. 生成了默认的 Blazor WebAssembly 项目。
  2. 构建项目并将输出 _framework 目录及其内容复制到 Web 窗体项目中。
  3. 将 Blazor web.config 中的以下内容添加到 Web 窗体 web.config:
  <system.webServer>
    <staticContent>
      <remove fileExtension=".dat" />
      <remove fileExtension=".dll" />
      <remove fileExtension=".json" />
      <remove fileExtension=".wasm" />
      <mimeMap fileExtension=".dll" mimeType="application/octet-stream" />
      <mimeMap fileExtension=".dat" mimeType="application/octet-stream" />
      <mimeMap fileExtension=".json" mimeType="application/json" />
      <mimeMap fileExtension=".wasm" mimeType="application/wasm" />
    </staticContent>
    <httpCompression>
      <dynamicTypes>
        <add mimeType="application/octet-stream" enabled="true" />
        <add mimeType="application/wasm" enabled="true" />
      </dynamicTypes>
    </httpCompression>
  </system.webServer>
  1. 将 Counter.aspx Web 表单页面的内容编辑为:
<%@ Page Title="Counter" Language="C#" MasterPageFile="~/Site.Master" AutoEventWireup="false" CodeBehind="Counter.aspx.cs" Inherits="WebFormBlazor.Counter" %>

<asp:Content ID="BodyContent" ContentPlaceHolderID="MainContent" runat="server">
    <app></app>

    <script src="_framework/blazor.webassembly.js"></script>
</asp:Content>
  1. 将 Blazor MainLayout.razor 编辑为:
@inherits LayoutComponentBase
<div>
    @Body
</div>
  1. 运行 Web Forms 项目并转到 http://localhost:1234/Counter,Web Form Counter 页面出现了嵌入的 Blazor Counter 页面。

如果你想要的不仅仅是一个 web 表单页面中的一个 blazor 页面,我建议你使用 iframe 在你的 web 表单应用程序中托管 blazor 应用程序。这将使它们独立,并且您不会 运行 两次获取资产的风险,and/or 变得无效 HTML and/or DOM webforms 页面上的操作伤害 blazor 应用程序。

通常,您还应该记住,WebForms 不会 运行 在 .NET Core(或 .NET 5 及更高版本)上,而 Blazor 运行 仅在 .NET Core 3 或.NET 5(或更高版本),因此这种技术组合以后可能会影响您。

如果你想一页一页地移动,而你除了 blazor 应用程序之外别无他物 - 只要你能确保正确的路径和基本路径(如果你的文件夹中有文件夹),上面的 PoC 应该会成功webforms 应用程序,这可能会影响 blazor 路由和路径)。此外,启动 wasm 应用程序对于客户端来说很慢,因此您可能需要考虑使用服务器端 blazor 页面(这肯定需要 iframe)。

编辑:您可能会发现 MS 正在为 WebForms 制作的这本书 -> Blazor 迁移 https://docs.microsoft.com/en-us/dotnet/architecture/blazor-for-web-forms-developers/