【问题标题】:Localization is working fine with Data Annotations and Views but not with Identity Pages ASP.NET Core MVC 3.1本地化适用于数据注释和视图,但不适用于身份页面 ASP.NET Core MVC 3.1
【发布时间】:2021-01-15 16:56:28
【问题描述】:

我必须在 ASP.NET Core MVC 3.1 的应用程序中实现本地化。我能够本地化模型验证和视图。但是,我无法本地化模型验证的身份页面。为了实现本地化,我在 startup.cs 文件中进行了如下更改:

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)
        {
            services.AddLocalization(opt => { opt.ResourcesPath = "Resources"; });
            services.Configure<RequestLocalizationOptions>(options =>
            {
                var supportedCultures = new List<CultureInfo>
                {
                    new CultureInfo("en-GB"),                  
                    new CultureInfo("da-DK")
                };

                options.DefaultRequestCulture = new RequestCulture("en-GB");
                options.SupportedCultures = supportedCultures;
                options.SupportedUICultures = supportedCultures;

                options.RequestCultureProviders.Clear();
                options.RequestCultureProviders.Add(new LocalizationDemoCultureProvider());
            });
 

            services.AddDbContext<LocalizationDemoDbContext>(options =>
                  options.UseSqlServer(
                      Configuration.GetConnectionString("LocalizationDemoDbContextConnection")));

            services.AddDefaultIdentity<ApplicationUser>(options =>
            {
                options.SignIn.RequireConfirmedAccount = true;
                options.Password.RequireLowercase = true;
                options.Password.RequireUppercase = true;
                options.Password.RequireNonAlphanumeric = true;
                options.Password.RequireDigit = true;
                options.Password.RequiredLength = 8;
            }).AddRoles<IdentityRole>()
              .AddEntityFrameworkStores<LocalizationDemoDbContext>();


            services.AddControllersWithViews()
                .AddViewLocalization(LanguageViewLocationExpanderFormat.Suffix)
                .AddDataAnnotationsLocalization(); 

            services.AddRazorPages().AddViewLocalization(LanguageViewLocationExpanderFormat.Suffix)
                .AddDataAnnotationsLocalization();

        }

        // 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();
            }
            else
            {
                app.UseExceptionHandler("/Error");
                // The default HSTS value is 30 days. You may want to change this for production scenarios, see https://aka.ms/aspnetcore-hsts.
                app.UseHsts();
            }
            app.UseHttpsRedirection();
            app.UseStaticFiles();

            app.UseRouting();

            app.UseAuthentication();
            app.UseAuthorization();

            app.UseRequestLocalization(app.ApplicationServices.GetRequiredService<IOptions<RequestLocalizationOptions>>().Value);

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

    }

我的 LocalizationDemoCultureProvider.cs 类如下:

public class LocalizationDemoCultureProvider : RequestCultureProvider
    {

        public override async Task<ProviderCultureResult> DetermineProviderCultureResult(HttpContext httpContext)
        {
            await Task.Yield();

            CultureInfo cultureInfoToSet = null;

            cultureInfoToSet = GetRequestCultureById(1); // The Id values come from database in the real application

            if (cultureInfoToSet != null)
            {
                return new ProviderCultureResult(cultureInfoToSet.Name);
            }
            return null;
        }

        private CultureInfo GetRequestCultureById(int Id)
        {
            CultureInfo cultureInfo = null;

            if (Id == 1)
            {
                cultureInfo = new CultureInfo("da-DK");
            }
            else if (Id == 2)
            {
                cultureInfo = new CultureInfo("en-GB");
            }
            return cultureInfo;
        }
    }

在此之后,我可以在 IViewLocalizer 的帮助下获取 Views 中的资源键。例如,其中一个视图是 Create.cshtml,如下所示:

@inject Microsoft.AspNetCore.Mvc.Localization.IViewLocalizer localizer

@model LocalizationDemo.Models.EmployeeViewModel

@{
    ViewData["Title"] = "Create";
}

<h1>@localizer["EmployeeCreate"]</h1>

<hr />
<div class="row">
    <div class="col-md-4">
        <form asp-action="Create">
            <div asp-validation-summary="ModelOnly" class="text-danger"></div>
            <div class="form-group">
                <label asp-for="FirstName" class="control-label"></label>
                <input asp-for="FirstName" class="form-control" />
                <span asp-validation-for="FirstName" class="text-danger"></span>
            </div>
            <div class="form-group">
                <label asp-for="LastName" class="control-label"></label>
                <input asp-for="LastName" class="form-control" />
                <span asp-validation-for="LastName" class="text-danger"></span>
            </div>
            <div class="form-group">
                <label asp-for="Salary" class="control-label"></label>
                <input asp-for="Salary" class="form-control" />
                <span asp-validation-for="Salary" class="text-danger"></span>
            </div>
            <div class="form-group">
                <label asp-for="DOB" class="control-label"></label>
                <input asp-for="DOB" class="form-control" />
                <span asp-validation-for="DOB" class="text-danger"></span>
            </div>
            <div class="form-group">
                <input type="submit" value="Create" class="btn btn-primary" />
            </div>
        </form>
    </div>
</div>

<div>
    <a asp-action="Index">@localizer["BackToList"]</a>
</div>

@section Scripts {
    @{await Html.RenderPartialAsync("_ValidationScriptsPartial");}
}

我的EmployeeViewModel.cs如下添加DataAnnotations:

 public class EmployeeViewModel
    {
        [Required(ErrorMessage ="FirstNameErrorMessage")]
        [Display(Name ="FirstName")] 
        public string FirstName { get; set; }
        [Required(ErrorMessage = "LastNameErrorMessage")]
        [Display(Name = "LastName")]
        public string LastName { get; set; }
        [Required(ErrorMessage = "SalaryErrorMessage")]
        [Display(Name = "Salary"), DisplayFormat(DataFormatString = "{0:n}")]
        public decimal Salary { get; set; }
        [Required(ErrorMessage = "DOBErrorMessage")]
        [Display(Name = "DOB"), DisplayFormat(DataFormatString = "{0:MMMM dd, yyyy}")]
        public DateTime DOB { get; set; }
    }

这工作正常,但是当我根据登录页面的文件夹结构为身份页面添加资源文件时,DataAnnotations 不起作用。我需要一些帮助,因为我被困在这里。请帮忙。

工作正常的示例 EmployeeViewModel.resx 文件。

示例 Login.resx 不起作用。

下面是对应资源文件的文件夹结构。

【问题讨论】:

    标签: asp.net-core asp.net-core-mvc


    【解决方案1】:

    为了使身份页面可用,内部模型有不同的模式。 例如,对于 Login.cshtml,LoginModel 有一个名为 InputModel 的内部模型。所以资源文件应该是LoginModel+InputModel.resx。资源文件结构如下:

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2021-04-19
      • 1970-01-01
      • 2020-07-12
      • 2020-09-01
      • 1970-01-01
      • 2016-07-03
      • 1970-01-01
      相关资源
      最近更新 更多