0

Context

I am currently working on a .net Core 3.1 API that will replace an old .NET Framework and Delphi back-end. The API needs to supports globalization and localization to translate error messages and a few data values. The localization is passed in through the route for example: http://localhost/en-US/controller/action/params. So connected apps can quickly switch from localization. The API has a Resources folder with the following files:

Resources:
- SharedResources.resx default and fallback language file nl-NL)
- SharedResources.en-US.resx
- SharedResources.de-DE.resx

In the Startup.cs I use installers to seperate concerns.

 public class Startup
    {
        public Startup(IConfiguration configuration)
        {
            Configuration = configuration;
        }

        public IConfiguration Configuration { get; }

        // This method gets called by the runtime. Use this method to add services to the container.
        public void ConfigureServices(IServiceCollection services)
        {
            // Extensions method that execute the install function on all classes that implement 
            // IInstaller interface
            services.InstallServicesInAssembly(Configuration);
        }
}

And I made a specific installer for the localization:

  public class LocalizationInstaller : IInstaller
    {
        public void InstallServices(IServiceCollection services, IConfiguration configuration)
        {
            var localizationConfig = new LocalizationConfig();
            configuration.GetSection(nameof(LocalizationConfig)).Bind(localizationConfig);
            services.AddSingleton(localizationConfig);

            services.AddLocalization(options => options.ResourcesPath = LocalizationConfig.ResourcePath);

            services.Configure<RequestLocalizationOptions>(options =>
            {
                options.DefaultRequestCulture = LocalizationConfig.GetDefaultRequestCulture();
                options.SupportedCultures = LocalizationConfig.GetSupportedCultures();
                options.SupportedUICultures = LocalizationConfig.GetSupportedCultures();
                options.RequestCultureProviders = new[] { new RouteDataRequestCultureProvider { Options = options } };
            });

            services.Configure<RouteOptions>(options =>
            {
                options.ConstraintMap.Add("culture", typeof(LanguageRouteConstraint));
            });

        }

The Data of LocalizationConfig is from the appsettings.json file.

"LocalizationConfig": {
    "ResourcePath": "Resources",
    "SupportedCultures": [ "nl-NL", "en-US", "de-DE" ],
    "DefaultRequestCulture": "nl-NL"
  }

The problem

[HttpGet("{version}/{culture}/Index")]
public IActionResult Index()
{
  var culture = $"CurrentCulture{CultureInfo.CurrentCulture.Name},CurrentUICulture{CultureInfo.CurrentUICulture.Name}";
  var value = _localizer["HelloWorld"].Value;
  return Ok(value);
}

When I make a request to the API with the culture being nl-NL or a random value it returns the default value in the SharedResources.resx like it is supposed to do. For example:http://localhost/1/nl-NL/Controller/Index returns Hallo Wereld!.

But when I make a request with the culture being either en-US or de-DE it still returns the value from the SharedResources.rex file instead of the SharedResources.en-US.resx file or SharedResources.de-DE.resx file while the culture from my variable var culture is being set to en-US or de-DE.

Notes

When I name my SharedResoures.en-US.resx to SharedResources.en.resx it does seem to work and the application finds the translation files. But this does not solve my issue that I want to specify the region code so that i can support both en-GB and en-US.

The Question

Why can the application find the file without the region code and not the file that does contain the region code?

Microsoft docs: https://learn.microsoft.com/en-us/aspnet/core/fundamentals/localization?view=aspnetcore-3.1

Magnetron
  • 7,495
  • 1
  • 25
  • 41
  • I Added another resource file name ``SharedResources.en.resx`` besides ``SharedResources.en-US.resx`` with different values for HelloWorld but it still falls back on ``SharedResources.en.resx`` when I make a request with the en-US culture. – Joep Verhoeven Sep 24 '20 at 13:18
  • It seems that you don't tell ASP.NET to use the culture. When you call_localizer it uses the default culture that in your case is nl-NL – Jaska Oct 26 '20 at 02:37
  • @Jaska that could be a possible explanation. I will look into and see if can solve it by manually setting the culture within a controller function and possibly with middleware. – Joep Verhoeven Oct 26 '20 at 10:40

0 Answers0