You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Blazor Server URL含文化代码本地化:资源加载异常与按钮失效

Blazor Server带文化代码URL本地化的资源加载问题及解决方法

我在Blazor Server项目中实现带文化代码的URL本地化访问,支持类似https://example.com/en/counter(英文)、https://example.com/fr/counter(法文)、https://example.com/es/counter(西班牙文)的路由格式。页面本地化功能正常,但出现资源加载异常,导致Counter组件的按钮点击无响应。

经排查,问题源于使用CultureTemplatePageRouteModelConvention动态给所有页面路由添加{culture}前缀,导致Blazor框架文件、CSS等静态资源的请求路径被错误修改,无法正确加载。

原问题配置代码

// Add services to the container.
builder.Services.AddRazorPages(options =>
{
    // decorate all page routes with {culture} e.g. @page "/{culture}..."

    // 注释下面这一行后,页面本地化失效,但资源加载的错误会消失
    options.Conventions.Add(new CultureTemplatePageRouteModelConvention());
});

解决方案:自定义CookieRouteDataRequestCultureProvider

通过自定义CookieRouteDataRequestCultureProvider类解决问题,该类会优先从路由中获取文化代码;若路由未提供,则从URL路径中解析;如果都没有,则从Cookie读取已保存的文化信息,同时避免修改静态资源的路径。

完整代码如下:

public class CookieRouteDataRequestCultureProvider : RequestCultureProvider
{
    public override Task<ProviderCultureResult> DetermineProviderCultureResult(HttpContext httpContext)
    {
        string previousRouteCulture;
        string routeCulture = (string)httpContext.Request.RouteValues["culture"];
        string urlCulture = httpContext.Request.Path.Value.Split('/')[1];

        // 从路由参数获取文化代码
        if (IsSupportedCulture(routeCulture))
        {
            previousRouteCulture = routeCulture;
            RequestCulture requestCulture = new RequestCulture(routeCulture, routeCulture);

            // 取消注释后,左侧导航菜单在部分导航操作后会失效
            SetThreadCulture(routeCulture);

            string cookieName = CookieRequestCultureProvider.DefaultCookieName;
            string cookieValue = CookieRequestCultureProvider.MakeCookieValue(requestCulture);
            httpContext.Response.Cookies.Append(cookieName, cookieValue);

            return Task.FromResult(new ProviderCultureResult(routeCulture));
        }
        // 从URL路径解析文化代码
        else if (IsSupportedCulture(urlCulture))
        {
            SetThreadCulture(urlCulture);

            return Task.FromResult(new ProviderCultureResult(urlCulture));
        }
        // 从Cookie读取或使用默认文化
        else
        {
            CookieCultureProvider cookieCultureProvider = new CookieCultureProvider(Options.SupportedCultures.ToList());
            string cultureFromCookieOrDefault = cookieCultureProvider.GetCultureFromCookie(httpContext);
            SetThreadCulture(cultureFromCookieOrDefault);

            return Task.FromResult(new ProviderCultureResult(cultureFromCookieOrDefault));
        }
    }

    private static void SetThreadCulture(string routeCulture)
    {
        CultureInfo cultureInfo = CultureInfo.GetCultureInfo(routeCulture);
        Thread.CurrentThread.CurrentCulture = cultureInfo;
        Thread.CurrentThread.CurrentUICulture = CultureInfo.GetCultureInfo(routeCulture);
    }

    /**
     * 验证文化代码是否在支持列表中
     */
    private bool IsSupportedCulture(string cultureCode) =>
        !string.IsNullOrEmpty(cultureCode)
        && Options.SupportedCultures.Any(x =>
            x.TwoLetterISOLanguageName.Equals(
                cultureCode,
                StringComparison.InvariantCultureIgnoreCase
            )
        );
}

内容的提问来源于stack exchange,提问作者Tom

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.15 12:40:56