Blazor的呈现模式与LiteDB项目中的坑点

参照文档指引,准备用.NET 8的Blazor和LiteDB撸个小项目,结果引入的LiteDB相关代码一直无法访问目录中的数据库,重建了好几次项目都无果。琢磨了半天才发现自己踩了新版本Blazor的呈现模式(RenderMode)的坑。看来还是要持续学习.NET新技术,跟上时代步伐!

解决方案

先给出我琢磨出来的解决方案,有两种办法

  1. 在引用LiteDB数据库的Razor页面最上方,使用@rendermode指令声明该页面的呈现模式为InteractiveServer,即交互式SSR模式
@page "..."
@rendermode InteractiveServer
  1. 在应用的App.razor页面Routes标签内,声明应用整体的呈现模式为InteractiveServer
<body>
    <Routes @rendermode="RenderMode.InteractiveServer" />
</body>

问题原理

问题的根源在于.NET 8版本之后,新的Blazor框架集成了之前的Blazor Server和Blazor Wasm两种托管模型,并且使用“渲染模式”定制整个应用乃至具体页面的呈现方式。根据文档,渲染模式共有四种:

名称 描述 呈现位置 交互
静态服务器(Static Server) 静态服务器端呈现(静态 SSR) 服务器 ❌否
交互式服务器(InteractiveServer) 使用 Blazor Server 的交互式服务器端呈现(交互式 SSR)。 服务器 ✔️是
交互式 WebAssembly(Interactive WebAssembly) 使用 Blazor WebAssembly 的客户端呈现 (CSR)†。 客户端 ✔️是
交互式自动(Interactive Auto) 下载 Blazor 捆绑包后,在后续访问时先使用 Blazor Server 然后使用 CSR 的交互式 SSR。 服务器,然后客户端 ✔️

四种模式里,Static Server即静态托管按下不表,InteractiveServer对应的就是之前的Blazor Server,Interactive WebAssembly对应Blazor Wasm,这都没问题。问题出在新增的Interactive Auto上。

按照微软设想,Interactive Auto可以实现应用模式的灵活切换。理想状态下应用初次加载或网络条件优良时在该模式下启用SSR服务端渲染,网络不佳或再次加载时切换到Wasm模式。应用的切换逻辑则由页面上的@rendermode指令或整个应用的Routes组件决定。

那么,如果没有指定页面的@rendermode指令怎么办呢?如果父级有指定过呈现模式,那么组件会继承其呈现模式,这就对应了上面解决方案里的方法二:通过为应用的路由组件指定呈现模式,让子页面继承。但如果父组件没有指定过呈现模式,组件自己也没有指定过呈现模式,运行时就默认会对该页面使用Static Server呈现模式。该模式下无法运行事件处理程序,当然也无法读写数据库,所以我们需要手动为应用指定呈现模式,这是解决方法一背后的原理。

参考资料:

  1. https://chrissainty.com/blazor-in-dotnet-8-full-stack-web-ui/
  2. https://learn.microsoft.com/zh-cn/aspnet/core/blazor/components/render-modes?view=aspnetcore-8.0
posted @ 2024-02-16 22:33  启真湖畔的佐时雨  阅读(247)  评论(0编辑  收藏  举报