如何分离.NET 8 Blazor Server的依赖配置与UI项目以实现干净架构?
解决方案:拆分Blazor Server宿主与UI项目以实现干净架构
核心思路
把原Blazor项目拆成两个独立项目,明确职责边界:
- 宿主项目:专管依赖注入配置、应用启动流程,可引用所有底层项目(领域、持久化、UI接口等)
- UI项目:仅存放Blazor组件、静态资源,只允许引用UI接口类库,彻底杜绝直接访问底层项目类型的可能
步骤1:调整项目结构
创建宿主项目
- 新建
<Project Sdk="Microsoft.NET.Sdk.Web"/>类型的项目(命名示例:MyApp.Host) - 删除默认生成的
Pages、wwwroot等UI相关文件夹
改造原Blazor项目为UI类库
- 将原Blazor项目的Sdk改为
<Project Sdk="Microsoft.NET.Sdk.Razor"/>,适配纯UI组件类库场景 - 保留
Pages、Shared、wwwroot、_Imports.razor、App.razor、_Host.cshtml等UI核心文件 - 移除原项目中所有
builder.Services.AddXXX()这类DI配置代码 - 清理依赖引用,确保只引用UI接口项目,不再直接引用领域、持久化等底层项目
步骤2:修正宿主项目的路径问题
在宿主项目的Program.cs中,手动指定ContentRootPath和WebRootPath指向UI项目的对应目录:
// 获取UI项目根目录(根据实际项目名称调整路径) var uiProjectRoot = Path.Combine(Directory.GetCurrentDirectory(), "../MyApp.UI"); var builder = WebApplication.CreateBuilder(new WebApplicationOptions { ContentRootPath = uiProjectRoot, WebRootPath = Path.Combine(uiProjectRoot, "wwwroot") }); // 在这里集中配置所有依赖注入(调用领域、持久化等项目的扩展方法) builder.Services.AddDomainServices(); builder.Services.AddPersistenceServices(); builder.Services.AddUiServices(); // 引用UI接口层的扩展方法,而非直接依赖UI实现 // 配置Blazor服务,关联UI项目的组件 builder.Services.AddRazorPages(); builder.Services.AddServerSideBlazor(); var app = builder.Build(); // 常规Blazor Server中间件配置 if (!app.Environment.IsDevelopment()) { app.UseExceptionHandler("/Error"); app.UseHsts(); } app.UseHttpsRedirection(); app.UseStaticFiles(); app.UseRouting(); app.MapBlazorHub(); app.MapFallbackToPage("/_Host"); app.Run();
步骤3:优化UI项目的依赖与发布
UI项目配置调整
在UI项目的.csproj中添加以下配置,确保静态资源能被宿主项目正确识别:
<PropertyGroup> <StaticWebAssetBasePath>/</StaticWebAssetBasePath> </PropertyGroup> <ItemGroup> <!-- 仅引用UI接口类库,保持依赖清洁 --> <ProjectReference Include="..\MyApp.UI.Contracts\MyApp.UI.Contracts.csproj" /> </ItemGroup>
发布时的资源同步
发布宿主项目时,可通过MSBuild参数指定UI项目的输出目录,确保静态资源被正确复制:
dotnet publish MyApp.Host/MyApp.Host.csproj /p:UiProjectOutputPath=../MyApp.UI/bin/Release/net8.0/publish
关键注意事项
- 严格管控引用链:宿主项目是唯一允许引用所有项目的入口,UI项目只能依赖UI接口层,领域层不依赖任何上层项目
- 避免硬编码路径:可通过配置文件或MSBuild变量动态获取UI项目路径,提升项目灵活性
- 验证资源访问:启动宿主项目后,务必测试CSS、JS等静态资源是否加载正常,Blazor组件能否正确渲染
内容的提问来源于stack exchange,提问作者Desty
相关产品推荐
相关产品推荐

