Search code examples
asp.net-coreasp.net-core-localization

Localization in ASP.NET Core 3.0


I'm trying to make my project Localized, using .resx files.

For me it does not work, for my colleague, who is working on the project too it works.

Some details about the code: Startup.cs file

 public void ConfigureServices(IServiceCollection services)
        {
            .
            .
            .
            // Localization

            services.AddLocalization(options => options.ResourcesPath = "Lang/");

            services.AddMvc(option => option.EnableEndpointRouting = false)
                .AddViewLocalization(LanguageViewLocationExpanderFormat.Suffix)
                .AddDataAnnotationsLocalization();



            services.Configure<RequestLocalizationOptions>(options =>
            {
                var supportedCultures = new List<CultureInfo>
                    {
                        new CultureInfo("cs"),
                        //new CultureInfo("en")
                    };

                options.DefaultRequestCulture = new RequestCulture(culture: "cs", uiCulture: "cs");
                options.SupportedCultures = supportedCultures;
                options.SupportedUICultures = supportedCultures;
            });
            services.AddTransient<Messages>();
            // Localization end
        }

        // This method gets called by the runtime. Use this method to configure the HTTP request pipeline.
        public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
        {
            if (env.IsDevelopment())
            {
                app.UseDeveloperExceptionPage();
                app.UseDatabaseErrorPage();
            }
            else
            {
                app.UseExceptionHandler("/Home/Error");
                app.UseHsts();
            }

            // Localization
            var locOptions = app.ApplicationServices.GetService<IOptions<RequestLocalizationOptions>>();
            app.UseRequestLocalization(locOptions.Value);
            // Localization end

            .
            .
            .

            app.UseEndpoints(endpoints =>
            {
                endpoints.MapControllers();
                endpoints.MapControllerRoute(
                    name: "default",
                    pattern: "{controller=Home}/{action=Index}/{id?}");
            });
        }

My controller:

public class AccountController : BasicController
    {     
        private readonly UserManager<User> userManager;
        private readonly IPasswordHasher<User> passwordHasher;
        private IStringLocalizer<Default> _localizer;


        public AccountController(UserManager<User> userManager, SignInManager<User> signInManager, IPasswordHasher<User> passwordHasher,
            IStringLocalizer<Default> LangDefault, IDataProtectionProvider provider) : base(signInManager,provider)
        {
            this.userManager = userManager;
            this.passwordHasher = passwordHasher;
            _localizer = LangDefault;
        }

My Login View:

@using Microsoft.AspNetCore.Localization
@using Microsoft.AspNetCore.Mvc.Localization
@inject IViewLocalizer Localizer

@{
    Layout = "_LayoutLogin";
    ViewData["Title"] = Localizer["TitleLogin"];

My project structure

for me it returns "TitleLogin" and the value "ResourceNotFound" is true.

For my colleague it returns correct value with the same code...

Could you please help me - what I'm doing wrong?

Many thanks.


Solution

  • I do not know which resx file contains TitleLogin.For displaying correct localization data, it wroks when I modify services.AddLocalization(options => options.ResourcesPath = "Lang/"); to

    services.AddLocalization(options => options.ResourcesPath = "Lang");
    

    And then add a resx file named Views.Account.Login.cs.resx in Lang folder.

    Update 3/19/2020

    It turns out that in asp.net core 3.1, you need to place Default.cs out of Resources folder(your Lang folder here),see this github issue.

    If class Default.cs and Default.*.resx in same folder, the namespace will be error in compiled dll xxx.lang.dll.

    So, the solution is

    1.Delete original Default.cs and create a new one under the project directly:

    namespace MyApp
    {
        public class Default
        {
        }
    }
    

    2.Add Default.cs.resx in the Lang folder

    3._ViewImports.cshtml

    @using MyApp
    @using Microsoft.Extensions.Localization
    @inject IStringLocalizer<Default> LangDefault