.NET Core 2迁移至.NET Core 7:Startup.cs本地化配置的适配修改问询
.NET Core 2迁移至.NET Core 7:Startup.cs本地化配置的适配修改问询
嘿,我帮你梳理下从.NET Core 2升级到7时本地化配置的关键修改点和注意事项,这些都是我实际升级项目时踩过的坑,希望对你有用:
一、传统Startup.cs模式的适配修改
如果你的项目还保留着Startup.cs的传统结构,针对你原有的代码可以做这些优化调整:
1. RequestLocalizationOptions配置简化
原代码里先移除再重新创建Cookie请求文化提供者的写法可以优化,直接复用默认实例调整顺序和属性即可,减少不必要的对象创建:
services.Configure<RequestLocalizationOptions>(opts => { var supportedCultures = new List<CultureInfo> { new CultureInfo("en"), new CultureInfo("ar"), new CultureInfo("ar-AE"), new CultureInfo("en-GB"), new CultureInfo("fr-FR"), new CultureInfo("fr"), new CultureInfo("en-US"), }; opts.DefaultRequestCulture = new RequestCulture("ar-AE"); opts.SupportedCultures = supportedCultures; opts.SupportedUICultures = supportedCultures; // 把Cookie提供者移到第一位,替代原移除再插入的冗余写法 var cookieProvider = opts.RequestCultureProviders.OfType<CookieRequestCultureProvider>().FirstOrDefault(); if (cookieProvider != null) { opts.RequestCultureProviders.Remove(cookieProvider); opts.RequestCultureProviders.Insert(0, cookieProvider); cookieProvider.CookieName = ".AspNetCore.Culture"; } });
2. 本地化服务注册的最佳实践调整
.NET Core 7推荐使用更贴合场景的服务注册方法,同时简化资源程序集的获取逻辑:
services.AddLocalization(options => options.ResourcesPath = "Resources"); // 用AddControllersWithViews替代AddMvc,更清晰地指向MVC场景(如果是Razor页面项目用AddRazorPages) services.AddControllersWithViews() .AddViewLocalization(LanguageViewLocationExpanderFormat.Suffix) .AddDataAnnotationsLocalization(options => { // 简化程序集获取,不用再绕GetTypeInfo的弯子 var resourceAssembly = typeof(SharedResource).Assembly; options.DataAnnotationLocalizerProvider = (type, factory) => factory.Create("SharedResources", resourceAssembly.GetName().Name); });
3. 中间件顺序的关键注意点
在Configure方法中,UseRequestLocalization必须放在路由中间件之前,确保本地化设置在路由处理、视图渲染前生效:
public void Configure(IApplicationBuilder app, IWebHostEnvironment env) { // 其他前置中间件(比如异常处理、静态文件) if (env.IsDevelopment()) { app.UseDeveloperExceptionPage(); } else { app.UseExceptionHandler("/Home/Error"); app.UseHsts(); } // 必须放在UseRouting之前! var locOptions = app.ApplicationServices.GetService<IOptions<RequestLocalizationOptions>>(); app.UseRequestLocalization(locOptions.Value); app.UseHttpsRedirection(); app.UseStaticFiles(); app.UseRouting(); // 路由中间件要在本地化之后 app.UseAuthorization(); app.UseEndpoints(endpoints => { endpoints.MapControllerRoute( name: "default", pattern: "{controller=Home}/{action=Index}/{id?}"); }); }
二、如果改用.NET 7的Top-level Statements(Program.cs)
如果你的项目升级后切换到了Program.cs的顶级语句模式,配置会更简洁,示例如下:
var builder = WebApplication.CreateBuilder(args); // 注册本地化服务 builder.Services.AddLocalization(options => options.ResourcesPath = "Resources"); // 配置请求本地化选项 builder.Services.Configure<RequestLocalizationOptions>(opts => { var supportedCultures = new List<CultureInfo> { new CultureInfo("en"), new CultureInfo("ar"), new CultureInfo("ar-AE"), new CultureInfo("en-GB"), new CultureInfo("fr-FR"), new CultureInfo("fr"), new CultureInfo("en-US"), }; opts.DefaultRequestCulture = new RequestCulture("ar-AE"); opts.SupportedCultures = supportedCultures; opts.SupportedUICultures = supportedCultures; var cookieProvider = opts.RequestCultureProviders.OfType<CookieRequestCultureProvider>().FirstOrDefault(); if (cookieProvider != null) { opts.RequestCultureProviders.Remove(cookieProvider); opts.RequestCultureProviders.Insert(0, cookieProvider); cookieProvider.CookieName = ".AspNetCore.Culture"; } }); // 注册MVC服务 builder.Services.AddControllersWithViews() .AddViewLocalization(LanguageViewLocationExpanderFormat.Suffix) .AddDataAnnotationsLocalization(options => { var resourceAssembly = typeof(SharedResource).Assembly; options.DataAnnotationLocalizerProvider = (type, factory) => factory.Create("SharedResources", resourceAssembly.GetName().Name); }); var app = builder.Build(); // 应用本地化设置(必须在路由之前) var locOptions = app.Services.GetRequiredService<IOptions<RequestLocalizationOptions>>(); app.UseRequestLocalization(locOptions.Value); // 其他中间件配置 if (!app.Environment.IsDevelopment()) { app.UseExceptionHandler("/Home/Error"); app.UseHsts(); } app.UseHttpsRedirection(); app.UseStaticFiles(); app.UseRouting(); app.UseAuthorization(); app.MapControllerRoute( name: "default", pattern: "{controller=Home}/{action=Index}/{id?}"); app.Run();
三、.NET Core 7本地化的核心变化注意事项
- 中间件顺序是重中之重:本地化中间件必须在路由、授权等中间件之前,否则本地化设置不会生效到路由解析、视图渲染或数据注解验证中,这是升级后最容易踩的坑。
- API简化:.NET Core 3.0+之后,很多反射相关的API(比如
GetTypeInfo())已经被简化,直接用typeof(T).Assembly就能获取程序集,不用再做冗余的类型信息转换。 - 默认请求文化提供者顺序:.NET 7的默认顺序是
QueryString→Cookie→AcceptLanguage,你的原代码把Cookie移到第一位的逻辑可以保留,完全符合业务需求。 - 资源文件逻辑无大变化:
Resources文件夹下的资源文件命名规范(比如SharedResources.resx、SharedResources.ar.resx)和.NET Core 2一致,不需要额外调整。 - 视图代码无需修改:你原来的视图代码
@SharedHtmlLocalizer["index"]可以直接复用,只要SharedHtmlLocalizer正确注入即可。
备注:内容来源于stack exchange,提问作者Jeswin Pathrose
相关产品推荐
相关产品推荐

