--- title: Localization Extensibility author: hishamco description: Learn how to extend the localization APIs in ASP.NET Core apps. monikerRange: '>= aspnetcore-2.1' ms.author: riande ms.custom: mvc ms.date: 08/03/2019 uid: fundamentals/localization-extensibility --- # Localization Extensibility [!INCLUDE[](~/includes/not-latest-version.md)] By [Hisham Bin Ateya](https://github.com/hishamco) This article: * Lists the extensibility points on the localization APIs. * Provides instructions on how to extend ASP.NET Core app localization. ## Extensible Points in Localization APIs ASP.NET Core localization APIs are built to be extensible. Extensibility allows developers to customize the localization according to their needs. For instance, [OrchardCore](https://github.com/orchardCMS/OrchardCore/) has a `POStringLocalizer`. `POStringLocalizer` describes in detail using [Portable Object localization](xref:fundamentals/portable-object-localization) to use `PO` files to store localization resources. This article lists the two main extensibility points that localization APIs provide: * * ## Localization Culture Providers ASP.NET Core localization APIs have four default providers that can determine the current culture of an executing request: * * * * The preceding providers are described in detail in the [Localization Middleware](xref:fundamentals/localization) documentation. If the default providers don't meet your needs, build a custom provider using one of the following approaches: ### Use CustomRequestCultureProvider provides a custom that uses a simple delegate to determine the current localization culture: :::moniker range=">= aspnetcore-3.0" ```csharp 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); })); ``` :::moniker-end :::moniker range="< aspnetcore-3.0" ```csharp 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); })); ``` :::moniker-end ### Use a new implementation of RequestCultureProvider A new implementation of can be created that determines the request culture information from a custom source. For example, the custom source can be a configuration file or database. The following example shows `AppSettingsRequestCultureProvider`, which extends the to determine the request culture information from `appsettings.json`: ```csharp public class AppSettingsRequestCultureProvider : RequestCultureProvider { public string CultureKey { get; set; } = "culture"; public string UICultureKey { get; set; } = "ui-culture"; public override Task DetermineProviderCultureResult(HttpContext httpContext) { if (httpContext == null) { throw new ArgumentNullException(); } var configuration = httpContext.RequestServices.GetService(); 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); } } ``` ## Localization resources ASP.NET Core localization provides . is an implementation of that uses `resx` to store localization resources. You aren't limited to using `resx` files. By implementing `IStringLocalizer`, any data source can be used. The following example projects implement : * [EFStringLocalizer](https://github.com/aspnet/Entropy/tree/master/samples/Localization.EntityFramework) * [JsonStringLocalizer](https://github.com/hishamco/My.Extensions.Localization.Json) * [SqlLocalizer](https://github.com/damienbod/AspNetCoreLocalization)