سؤال

أحاول دمج nhibernate.validator مع عمليات التحقق من جانب عميل ASP.NET MVC ، والمشكلة الوحيدة التي وجدتها هي أنه لا يمكنني ببساطة تحويل الرسالة غير المتكافئة إلى رسالة قابلة للقراءة البشرية. اعتقدت أن هذه ستكون مهمة سهلة ، ولكن تبين أنها الجزء الأصعب من التحقق من صحة من جانب العميل. المشكلة الرئيسية هي أنه نظرًا لأنه ليس من جانب الخادم ، فأنا في الواقع بحاجة فقط إلى سمات التحقق من الصحة التي يتم استخدامها ، وليس لديّ مثيل أو أي شيء آخر في متناول اليد.

إليك بعض المقتطفات مما كنت أحاول بالفعل:

// Get the the default Message Interpolator from the Engine
IMessageInterpolator interp = _engine.Interpolator;
if (interp == null)
{
  // It is null?? Oh, try to create a new one
  interp = new NHibernate.Validator.Interpolator.DefaultMessageInterpolator();
}

// We need an instance of the object that needs to be validated, se we have to create one
object instance = Activator.CreateInstance(Metadata.ContainerType);

// we enumerate all attributes of the property. For example we have found a PatternAttribute
var a = attr as PatternAttribute;

// it seems that the default message interpolator doesn't work, unless initialized
if (interp is NHibernate.Validator.Interpolator.DefaultMessageInterpolator)
{
  (interp as NHibernate.Validator.Interpolator.DefaultMessageInterpolator).Initialize(a);
}

// but even after it is initialized the following will throw a NullReferenceException, although all of the parameters are specified, and they are not null (except for the properties of the instance, which are all null, but this can't be changed)
var message = interp.Interpolate(new InterpolationInfo(Metadata.ContainerType, instance, PropertyName, a, interp, a.Message));

أعلم أن ما سبق هو رمز معقد إلى حد ما لسؤال يبدو بسيطًا ، لكنني ما زلت عالقًا بدون حل. هل هناك أي طريقة لإخراج السلسلة المحرف من NHValidator؟

هل كانت مفيدة؟

المحلول

حسنًا ، لذلك أعلم أن هذا سؤال قديم ، لكنني تعثرت في هذا الأمر عند محاولة فعل نفس الشيء ، وقد ساعدني ذلك في البدء - لذلك اعتقدت أنني سأقدم إجابة.

أعتقد أن الكود في السؤال كان على المسار الصحيح ولكن هناك بعض المشكلات. لم يتم تهيئة interpolator بالكامل مع ResourceManager و Culture التفاصيل ، ولا يبدو أنها تسمح بحقيقة أنه يمكنك الحصول على واحدة فقط DefaultMessageInterpolator لكل سمة التحقق من الصحة. أيضًا ، لا تحتاج إلى مثيل للكائن الذي تقوم بالتحقق منه للحصول على رسالة محرف.

في الرمز في السؤال ، حيث تقوم بتهيئة interpolator بقيمة السمة ، تحتاج أيضًا إلى تهيئة interpolator مع تفاصيل ResourceManager لاستخدامها.

يمكن القيام بذلك باستخدام الحمولة الزائدة Initialize طريقة على DefaultMessageInterpolator الذي لديه التوقيع التالي:

    public void Initialize(ResourceManager messageBundle, 
                           ResourceManager defaultMessageBundle, 
                           CultureInfo culture)

المعلمة الأولى هي لعبة ResourceManager المعرفة من قبل المستخدم في حال كنت ترغب في استخدام ملف الموارد الخاص بك لرسائل الخطأ ، يمكنك تمرير خالية إذا كنت ترغب فقط في استخدام Resoucemanager الافتراضي ، فإن المعلمة الثانية هي ResourceManager الافتراضية - يمكنك المرور

  new ResourceManager( 
      NHibernate.Validator.Cfg.Environment.BaseNameOfMessageResource,
      Assembly.GetExecutingAssembly());

لهذا ، فإن المعلمة الأخيرة هي الثقافة التي يجب استخدامها ، (nhibernate.validator تأتي مع ملفات موارد تحتوي على رسائل التحقق من الصحة بعدة لغات) - إذا قمت بتمرير خالية من هذا ، فستستخدمها فقط CultureInfo.CurrentCulture

أخيرًا ، يمكنك الحصول على واحدة فقط DefaultMessageInterpolator لكل سمة ، لذلك ستحتاج إلى إنشاء جديد DefaultMessageInterpolator لكل سمة التحقق من الصحة. يمكنك الاستفادة من DefaultMessageInterpolatorAggregator للتعامل مع هذا ، أو فقط لفة الخاصة بك.

آمل أن يساعد هذا شخص ما.

نصائح أخرى

شكرا لمساعدتكم كل شيء-كنت أرفع التصويت إذا استطعت. أردت فقط أن أضيف أنه بالإضافة إلى أول مكالمة تهيئة على DefaultMessageInterPolator التي يوضحها ستانك ، كان علي أيضًا إجراء مكالمة تهيئة أخرى مختلفة لتهيئتها بالكامل (كنت أحصل على بعض الاستثناءات المرجعية الخالية باستخدام المكالمة الأولى فقط). قانون بلدي على النحو التالي:

string interpolatedMessage = "";
DefaultMessageInterpolator interpolator = new DefaultMessageInterpolator();

interpolator.Initialize(null,
    new ResourceManager(
        NHibernate.Validator.Cfg.Environment.BaseNameOfMessageResource,
        Assembly.Load("NHibernate.Validator")),
        CultureInfo.CurrentCulture);

interpolator.Initialize(attribute as Attribute);

if (attribute is IValidator && attribute is IRuleArgs)
{
    IValidator validator = attribute as IValidator;
    IRuleArgs ruleArgs = attribute as IRuleArgs;

    InterpolationInfo interpolationInfo = new InterpolationInfo(
        validatableType, 
        null, 
        propertyName, 
        validator,
        interpolator, 
        ruleArgs.Message);

    interpolatedMessage = interpolator.Interpolate(interpolationInfo);
}
مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top