本地化可扩展性

作者:Hisham Bin Ateya

本文:

  • 列出本地化 API 上的可扩展性点。
  • 提供有关如何扩展 ASP.NET Core 应用本地化的说明。

本地化 API 中的可扩展点

ASP.NET Core 本地化 API 生成是可扩展的。 开发人员可利用可扩展性根据需求自定义本地化。 例如,OrchardCore 有一个 POStringLocalizerPOStringLocalizer 详细描述了如何使用可移植对象本地化来使用 PO 文件存储本地化资源。

本文列出了本地化 API 提供的两个主要扩展点:

本地化区域性提供程序

ASP.NET Core 本地化 API 有四个默认提供程序,可用于确定正在执行的请求的当前区域性:

本地化中间件文档中提供了对前面的提供程序的详细介绍。 如果默认提供程序无法满足需求,请使用以下一种方法生成自定义提供程序:

使用 CustomRequestCultureProvider

CustomRequestCultureProvider 提供了一个自定义 RequestCultureProvider,它使用简单的委托来确定当前的本地化区域性:

options.RequestCultureProviders.Insert(0, new CustomRequestCultureProvider(async context =>
{
    var currentCulture = "en";
    var segments = context.Request.Path.Value.Split(new char[] { '/' }, 
        StringSplitOptions.RemoveEmptyEntries);

    if (segments.Length > 1 && segments[0].Length == 2)
    {
        currentCulture = segments[0];
    }

    var requestCulture = new ProviderCultureResult(currentCulture);

    return Task.FromResult(requestCulture);
}));
options.AddInitialRequestCultureProvider(new CustomRequestCultureProvider(async context =>
{
    var currentCulture = "en";
    var segments = context.Request.Path.Value.Split(new char[] { '/' }, 
        StringSplitOptions.RemoveEmptyEntries);

    if (segments.Length > 1 && segments[0].Length == 2)
    {
        currentCulture = segments[0];
    }

    var requestCulture = new ProviderCultureResult(currentCulture);

    return Task.FromResult(requestCulture);
}));

使用 RequestCultureProvider 的新实现

可以创建 RequestCultureProvider 的新实现,以确定来自自定义源的请求区域性信息。 例如,自定义源可以是配置文件或数据库。

以下示例演示了 AppSettingsRequestCultureProvider,它扩展了 RequestCultureProvider 以确定来自 appsettings.json 的请求区域性信息:

public class AppSettingsRequestCultureProvider : RequestCultureProvider
{
    public string CultureKey { get; set; } = "culture";

    public string UICultureKey { get; set; } = "ui-culture";

    public override Task<ProviderCultureResult> DetermineProviderCultureResult(HttpContext httpContext)
    {
        if (httpContext == null)
        {
            throw new ArgumentNullException();
        }

        var configuration = httpContext.RequestServices.GetService<IConfigurationRoot>();
        var culture = configuration[CultureKey];
        var uiCulture = configuration[UICultureKey];

        if (culture == null && uiCulture == null)
        {
            return Task.FromResult((ProviderCultureResult)null);
        }

        if (culture != null && uiCulture == null)
        {
            uiCulture = culture;
        }

        if (culture == null && uiCulture != null)
        {
            culture = uiCulture;
        }
        
        var providerResultCulture = new ProviderCultureResult(culture, uiCulture);

        return Task.FromResult(providerResultCulture);
    }
}

本地化资源

ASP.NET Core 本地化提供 ResourceManagerStringLocalizerResourceManagerStringLocalizerIStringLocalizer 的实现,它使用 resx 来存储本地化资源。

不仅限于使用 resx 文件。 通过实现 IStringLocalizer,可以使用任何数据源。

以下示例项目实现 IStringLocalizer