默认错误消息:

MissingBindRequiredValueAccessor    A value for the '{0}' property was not provided.
MissingKeyOrValueAccessor A value is required.
ValueMustNotBeNullAccessor The value '{0}' is invalid.
AttemptedValueIsInvalidAccessor The value '{0}' is not valid for {1}.
UnknownValueIsInvalidAccessor The supplied value is invalid for {0}.
ValueIsInvalidAccessor The value '{0}' is invalid.
ValueMustBeANumberAccessor The field {0} must be a number.
MissingRequestBodyRequiredValueAccessor       A non-empty request body is required.
NonPropertyAttemptedValueIsInvalidAccessor The value '{0}' is not valid.
NonPropertyUnknownValueIsInvalidAccessor The supplied value is invalid.
NonPropertyValueMustBeANumberAccessor The field must be a number.

若要本地化ASP.NET Core 模型绑定错误消息,请按照下列步骤操作:

  1. 创建资源文件 - 在解决方案的Resources文件夹下创建资源文件,并将文件命名为ModelBindingMessages.resx。名称可以是其他任何名称,但我们将使用它来创建本地化程序。

  2. 添加资源键 - 打开资源文件并添加要用于本地化错误消息的键和值。我使用了键和值

  3. 配置选项 - 在ConfigureServices方法中,添加时Mvc,配置其选项以设置以下内容的消息访问者ModelBindingMessageProvider

  4.     services.AddMvc(options =>
    {
    IStringLocalizerFactory F = services.BuildServiceProvider().
    GetService<IStringLocalizerFactory>();
    IStringLocalizer L = F.Create("ModelBindingMessages",
    "AspNetCoreLocalizationSample");
    options.ModelBindingMessageProvider.
    SetValueIsInvalidAccessor((x) => L["The value '{0}' is invalid."]);
    options.ModelBindingMessageProvider.SetValueMustBeANumberAccessor(
    (x) =>L["The field {0} must be a number."]);
    options.ModelBindingMessageProvider.SetMissingBindRequiredValueAccessor(
    (x) => L["A value for the '{0}' property was not provided.", x]);
    options.ModelBindingMessageProvider.SetAttemptedValueIsInvalidAccessor(
    (x, y) => L["The value '{0}' is not valid for {1}.", x, y]);
    options.ModelBindingMessageProvider.SetMissingKeyOrValueAccessor(
    () => L["A value is required."]);
    options.ModelBindingMessageProvider.SetUnknownValueIsInvalidAccessor(
    (x) => L["The supplied value is invalid for {0}.", x]);
    options.ModelBindingMessageProvider.SetValueMustNotBeNullAccessor(
    (x) => L["Null value is invalid.", x]);
    }).AddDataAnnotationsLocalization()
    .AddViewLocalization();
    services.Configure<RequestLocalizationOptions>(options =>
    {
    var supportedCultures = new[]{new CultureInfo("en"), new CultureInfo("zh-cn")};
    options.DefaultRequestCulture = new RequestCulture("en", "en");
    options.SupportedCultures = supportedCultures;
    options.SupportedUICultures = supportedCultures;
    });
  5. 还要在Configure方法开头添加此代码:

     var supportedCultures = new[] { new CultureInfo("en"), new CultureInfo("zh-CN") };
    app.UseRequestLocalization(new RequestLocalizationOptions()
    {
    DefaultRequestCulture = new RequestCulture(new CultureInfo("en")),
    SupportedCultures = supportedCultures,
    SupportedUICultures = supportedCultures
    });
  6. 关于属性DisplayAttribute 

    通过查看源码 在 Microsoft.AspNetCore.Mvc.DataAnnotations.Internal.DataAnnotationsMetadataProvider中有IDisplayMetadataProvider的实现
    主要是判断DisplayName不为空和ResourceType为空的时候使用IStringLocalizerFactory 
    代码片段如下:

        var dataTypeAttribute = attributes.OfType<DataTypeAttribute>().
    if (displayFormatAttribute == null && dataTypeAttribute != null)
    {
    displayFormatAttribute = dataTypeAttribute.DisplayFormat;
    }
    var displayMetadata = context.DisplayMetadata; // ConvertEmptyStringToNull
    if (displayFormatAttribute != null)
    {
    displayMetadata.ConvertEmptyStringToNull = displayFormatAttribute.
    ConvertEmptyStringToNull;
    }
    // DataTypeName
    if (dataTypeAttribute == null)
    {
    if (displayFormatAttribute != null && !displayFormatAttribute.HtmlEncode)
    {
    displayMetadata.DataTypeName = DataType.Html.ToString();
    }
    }
    else
    {
    displayMetadata.DataTypeName = dataTypeAttribute.GetDataTypeName();
    } var containerType = context.Key.ContainerType ?? context.Key.ModelType;
    IStringLocalizer localizer = null;
    if (_stringLocalizerFactory != null && _localizationOptions.DataAnnotationLocalizerProvider != null)
    {
    localizer = _localizationOptions.DataAnnotationLocalizerProvider(containerType, _stringLocalizerFactory);
    } // Description
    if (displayAttribute != null)
    {
    if (localizer != null &&
    !string.IsNullOrEmpty(displayAttribute.Description) &&
    displayAttribute.ResourceType == null)
    {
    displayMetadata.Description = () => localizer[displayAttribute.Description];
    }
    else
    {
    displayMetadata.Description = () => displayAttribute.GetDescription();
    }
    } // DisplayFormatString
    if (displayFormatAttribute != null)
    {
    displayMetadata.DisplayFormatString = displayFormatAttribute.DataFormatString;
    } // DisplayName
    // DisplayAttribute has precedence over DisplayNameAttribute.
    if (displayAttribute?.GetName() == null)
    {
    if (displayNameAttribute != null)
    {
    if (localizer != null &&
    !string.IsNullOrEmpty(displayNameAttribute.DisplayName))
    {
    displayMetadata.DisplayName = () => localizer[displayNameAttribute.DisplayName];
    }
    else
    {
    displayMetadata.DisplayName = () => displayNameAttribute.DisplayName;
    }
    }
    }
    else
    {
    if (localizer != null &&
    !string.IsNullOrEmpty(displayAttribute.Name) &&
    displayAttribute.ResourceType == null)
    {
    displayMetadata.DisplayName = () => localizer[displayAttribute.Name];
    }
    else
    {
    displayMetadata.DisplayName = () => displayAttribute.GetName();
    }
    } // EditFormatString
    if (displayFormatAttribute != null && displayFormatAttribute.ApplyFormatInEditMode)
    {
    displayMetadata.EditFormatString = displayFormatAttribute.DataFormatString;
    } // IsEnum et cetera
    var underlyingType = Nullable.GetUnderlyingType(context.Key.ModelType) ?? context.Key.ModelType;
    var underlyingTypeInfo = underlyingType.GetTypeInfo(); if (underlyingTypeInfo.IsEnum)
    {
    // IsEnum
    displayMetadata.IsEnum = true; // IsFlagsEnum
    displayMetadata.IsFlagsEnum = underlyingTypeInfo.IsDefined(typeof(FlagsAttribute), inherit: false); // EnumDisplayNamesAndValues and EnumNamesAndValues
    //
    // Order EnumDisplayNamesAndValues by DisplayAttribute.Order, then by the order of Enum.GetNames().
    // That method orders by absolute value, then its behavior is undefined (but hopefully stable).
    // Add to EnumNamesAndValues in same order but Dictionary does not guarantee order will be preserved. var groupedDisplayNamesAndValues = new List<KeyValuePair<EnumGroupAndName, string>>();
    var namesAndValues = new Dictionary<string, string>(); IStringLocalizer enumLocalizer = null;
    if (_localizationOptions.AllowDataAnnotationsLocalizationForEnumDisplayAttributes)
    {
    if (_stringLocalizerFactory != null && _localizationOptions.DataAnnotationLocalizerProvider != null)
    {
    enumLocalizer = _localizationOptions.DataAnnotationLocalizerProvider(underlyingType, _stringLocalizerFactory);
    }
    }
    else
    {
    enumLocalizer = _stringLocalizerFactory?.Create(underlyingType);
    } var enumFields = Enum.GetNames(underlyingType)
    .Select(name => underlyingType.GetField(name))
    .OrderBy(field => field.GetCustomAttribute<DisplayAttribute>(inherit: false)?.GetOrder() ?? ); foreach (var field in enumFields)
    {
    var groupName = GetDisplayGroup(field);
    var value = ((Enum)field.GetValue(obj: null)).ToString("d"); groupedDisplayNamesAndValues.Add(new KeyValuePair<EnumGroupAndName, string>(
    new EnumGroupAndName(
    groupName,
    () => GetDisplayName(field, enumLocalizer)),
    value));
    namesAndValues.Add(field.Name, value);
    } displayMetadata.EnumGroupedDisplayNamesAndValues = groupedDisplayNamesAndValues;
    displayMetadata.EnumNamesAndValues = namesAndValues;
    } // HasNonDefaultEditFormat
    if (!string.IsNullOrEmpty(displayFormatAttribute?.DataFormatString) &&
    displayFormatAttribute?.ApplyFormatInEditMode == true)
    {
    // Have a non-empty EditFormatString based on [DisplayFormat] from our cache.
    if (dataTypeAttribute == null)
    {
    // Attributes include no [DataType]; [DisplayFormat] was applied directly.
    displayMetadata.HasNonDefaultEditFormat = true;
    }
    else if (dataTypeAttribute.DisplayFormat != displayFormatAttribute)
    {
    // Attributes include separate [DataType] and [DisplayFormat]; [DisplayFormat] provided override.
    displayMetadata.HasNonDefaultEditFormat = true;
    }
    else if (dataTypeAttribute.GetType() != typeof(DataTypeAttribute))
    {
    // Attributes include [DisplayFormat] copied from [DataType] and [DataType] was of a subclass.
    // Assume the [DataType] constructor used the protected DisplayFormat setter to override its
    // default. That is derived [DataType] provided override.
    displayMetadata.HasNonDefaultEditFormat = true;
    }
    } // HideSurroundingHtml
    if (hiddenInputAttribute != null)
    {
    displayMetadata.HideSurroundingHtml = !hiddenInputAttribute.DisplayValue;
    } // HtmlEncode
    if (displayFormatAttribute != null)
    {
    displayMetadata.HtmlEncode = displayFormatAttribute.HtmlEncode;
    } // NullDisplayText
    if (displayFormatAttribute != null)
    {
    displayMetadata.NullDisplayText = displayFormatAttribute.NullDisplayText;
    } // Order
    if (displayAttribute?.GetOrder() != null)
    {
    displayMetadata.Order = displayAttribute.GetOrder().Value;
    } // Placeholder
    if (displayAttribute != null)
    {
    if (localizer != null &&
    !string.IsNullOrEmpty(displayAttribute.Prompt) &&
    displayAttribute.ResourceType == null)
    {
    displayMetadata.Placeholder = () => localizer[displayAttribute.Prompt];
    }
    else
    {
    displayMetadata.Placeholder = () => displayAttribute.GetPrompt();
    }
    }
  7.   

												

本地化ASP.NET core模型绑定错误消息的更多相关文章

  1. 理解ASP.NET Core - 模型绑定&验证(Model Binding and Validation)

    注:本文隶属于<理解ASP.NET Core>系列文章,请查看置顶博客或点击此处查看全文目录 模型绑定 什么是模型绑定?简单说就是将HTTP请求参数绑定到程序方法入参上,该变量可以是简单类 ...

  2. ASP.NET Core应用的错误处理[3]:ExceptionHandlerMiddleware中间件如何呈现“定制化错误页面”

    DeveloperExceptionPageMiddleware中间件利用呈现出来的错误页面实现抛出异常和当前请求的详细信息以辅助开发人员更好地进行纠错诊断工作,而ExceptionHandlerMi ...

  3. ASP.NET Core应用的错误处理[2]:DeveloperExceptionPageMiddleware中间件如何呈现“开发者异常页面”

    在<ASP.NET Core应用的错误处理[1]:三种呈现错误页面的方式>中,我们通过几个简单的实例演示了如何呈现一个错误页面,这些错误页面的呈现分别由三个对应的中间件来完成,接下来我们将 ...

  4. ASP.NET Core应用的错误处理[1]:三种呈现错误页面的方式

    由于ASP.NET Core应用是一个同时处理多个请求的服务器应用,所以在处理某个请求过程中抛出的异常并不会导致整个应用的终止.出于安全方面的考量,为了避免敏感信息的外泄,客户端在默认的情况下并不会得 ...

  5. ASP.NET MVC模型绑定的6个建议(转载)

    ASP.NET MVC模型绑定的6个建议 发表于2011-08-03 10:25| 来源博客园| 31 条评论| 作者冠军 validationasp.netmvc.netasp 摘要:ASP.NET ...

  6. ASP.NET没有魔法——ASP.NET MVC 模型绑定

    在My Blog中已经有了文章管理功能,可以发布和修改文章,但是对于文章内容来说,这里缺少最重要的排版功能,如果没有排版的博客很大程度上是无法阅读的,由于文章是通过浏览器查看的,所以文章的排版其实与网 ...

  7. ASP.NET没有魔法——ASP.NET MVC 模型绑定解析(下篇)

    上一篇<ASP.NET没有魔法——ASP.NET MVC 模型绑定解析(上篇)>文章介绍了ASP.NET MVC模型绑定的相关组件和概念,本章将介绍Controller在执行时是如何通过这 ...

  8. [转] ASP.NET MVC 模型绑定的功能和问题

    摘要:本文将与你深入探究 ASP.NET MVC 模型绑定子系统的核心部分,展示模型绑定框架的每一层并提供扩展模型绑定逻辑以满足应用程序需求的各种方法. 同时,你还会看到一些经常被忽视的模型绑定技术, ...

  9. ASP.NET Core 异常和错误处理 - ASP.NET Core 基础教程 - 简单教程,简单编程

    原文:ASP.NET Core 异常和错误处理 - ASP.NET Core 基础教程 - 简单教程,简单编程 ASP.NET Core 异常和错误处理 上一章节中,我们学习了 ASP.NET Cor ...

随机推荐

  1. 第十七章 Velocity优化实践(待续)

    现实存在的问题 优化的理论基础 一个高效的模版引擎实现思路 优化成果 其他优化手段

  2. Linux 对mysql远程授权连接操作 和 查看mysql数据库和表 基本命令

    Linux 对mysql远程连接的授权操作 首先linux连接mysql数据库 授权: grant all on *.* to ' with grant option; //允许账户root从任何主机 ...

  3. openGL一些概念01

    顶点数据: 顶点数据是一系列顶点的集合. 一个顶点(Vertex)是一个3d坐标的数据的集合. 而顶点数据是用顶点属性(Vertex Attribute)表示的,它可以包含任何我们想用的数据. (但是 ...

  4. ffmpeg一揽子

    avformat_alloc_output_context2().在基于FFmpeg的视音频编码器程序中,该函数通常是第一个调用的函数(除了组件注册函数av_register_all()).avfor ...

  5. WKWebView的15条应用指南

    1.让一个web view充满屏幕 有时候你会看到有人向viewDidLoad()中添加代码,创建一个web view并让它充满整个可用区域.但这样效率很低,用起来很麻烦. 一个简单的方法是在你的视图 ...

  6. Executor线程池

    Executor线程池框架: 使用线程池的优点: 1.重用存在的线程 2.减少对象创建.消亡的开销 3.性能佳 4.可有效控制最大并发线程数,提高系统资源的使用率 5.避免过多资源竞争,避免堵塞 6. ...

  7. 中华人民共和国建筑工业行业标准—IFC详细解读 第五篇

  8. Windows系统 为 QT5软件 搭建 OpenCV2 开发环境

    Windows系统 为 QT5软件 搭建 OpenCV2 开发环境 我们的电脑系统:Windows 10 64位 Qt5 软件:Qt 5. 7. 0 OpenCV2 版本:OpenCV2.4.10 1 ...

  9. 3.文档视图:从gui分割状态

    为了解决一个类实现所有功能的缺陷,我们把application分为2个部分.一个部分业务逻辑,一个部分视觉渲染和交互.这2个类在学术上被称为document view 或者 model delegat ...

  10. jquery 的插件 extend

      让我们来讲解  jquery中的插件机制  $.fn.extend and()  $.extend()这两个方法都接受一个参数,类型为Object.Object对象的“名/值对”分别代表“函数或方 ...