Daten mithilfe von DataAnnotations mit WPF & Entity Framework überprüfen?

.net data-annotations entity-framework validation wpf

Frage

Gibt es eine Möglichkeit, mithilfe von DataAnnotations in WPF & Entity Framework zu validieren?

Akzeptierte Antwort

Sie können die DataAnnotations.Validator-Klasse wie hier beschrieben verwenden:

http://johan.driessen.se/archive/2009/11/18/testing-dataannotation-based-validation-in-asp.net-mvc.aspx

Wenn Sie jedoch eine Buddy-Klasse für die Metadaten verwenden, müssen Sie diese Tatsache vor dem Validieren registrieren, wie hier beschrieben:

http://forums.silverlight.net/forums/p/149264/377212.aspx

TypeDescriptor.AddProviderTransparent(
  new AssociatedMetadataTypeTypeDescriptionProvider(typeof(myEntity), 
    typeof(myEntityMetadataClass)), 
  typeof(myEntity));

List<ValidationResult> results = new List<ValidationResult>();
ValidationContext context = new ValidationContext(myEntity, null, null)
bool valid = Validator.TryValidateObject(myEntity, context, results, true);

[Fügte Folgendes hinzu, um auf Shimmys Kommentar zu antworten]

Ich habe eine generische Methode geschrieben, um die obige Logik zu implementieren, damit jedes Objekt sie aufrufen kann:

// If the class to be validated does not have a separate metadata class, pass
// the same type for both typeparams.
public static bool IsValid<T, U>(this T obj, ref Dictionary<string, string> errors)
{
    //If metadata class type has been passed in that's different from the class to be validated, register the association
    if (typeof(T) != typeof(U))
    {
        TypeDescriptor.AddProviderTransparent(new AssociatedMetadataTypeTypeDescriptionProvider(typeof(T), typeof(U)), typeof(T));
    }

    var validationContext = new ValidationContext(obj, null, null);
    var validationResults = new List<ValidationResult>();
    Validator.TryValidateObject(obj, validationContext, validationResults, true);

    if (validationResults.Count > 0 && errors == null)
        errors = new Dictionary<string, string>(validationResults.Count);

    foreach (var validationResult in validationResults)
    {
        errors.Add(validationResult.MemberNames.First(), validationResult.ErrorMessage);
    }

    if (validationResults.Count > 0)
        return false;
    else
        return true;
}

In jedem Objekt, das überprüft werden muss, füge ich dieser Methode einen Aufruf hinzu:

[MetadataType(typeof(Employee.Metadata))]
public partial class Employee
{
    private sealed class Metadata
    {
        [DisplayName("Email")]
        [Email(ErrorMessage = "Please enter a valid email address.")]
        public string EmailAddress { get; set; }
    }

    public bool IsValid(ref Dictionary<string, string> errors)
    {
        return this.IsValid<Employee, Metadata>(ref errors);
        //If the Employee class didn't have a buddy class,
        //I'd just pass Employee twice:
        //return this.IsValid<Employee, Employee>(ref errors);
    }
}

Beliebte Antwort

Ich denke, was bei Craigs Antwort fehlt, ist, wie man tatsächlich prüfen kann, ob Validierungsfehler vorliegen. Dies ist der DataAnnotation-Validierungsläufer, der von Steve Sanderson für diejenigen geschrieben wurde, die eine Validierungsprüfung in einer anderen Ebene und anschließend in einer Präsentation durchführen möchten ( http://blog.codeville.net/category/xval/ , der Code ist in einem Beispielprojekt):

public static IEnumerable<ErrorInfo> GetErrors(object instance)
{
    var metadataAttrib = instance.GetType().GetCustomAttributes
        (typeof(MetadataTypeAttribute), true).
            OfType<MetadataTypeAttribute>().FirstOrDefault();
    var buddyClassOrModelClass = 
        metadataAttrib != null ? 
        metadataAttrib.MetadataClassType : 
        instance.GetType();
    var buddyClassProperties = TypeDescriptor.GetProperties
        (buddyClassOrModelClass).Cast<PropertyDescriptor>();
    var modelClassProperties = TypeDescriptor.GetProperties
        (instance.GetType()).Cast<PropertyDescriptor>();

    return from buddyProp in buddyClassProperties
           join modelProp in modelClassProperties
               on buddyProp.Name equals modelProp.Name
           from attribute in buddyProp.Attributes.
               OfType<ValidationAttribute>()
           where !attribute.IsValid(modelProp.GetValue(instance))
           select new ErrorInfo(buddyProp.Name, 
               attribute.FormatErrorMessage(string.Empty), instance);
}

Ich bin nicht mit WPF vertraut (nicht sicher, ob es eine Out-of-the-Box-Lösung für Ihre Frage gibt), aber vielleicht können Sie sie verwenden.

Es gibt auch einige Kommentare in seinem Blog, dass die Validierungsregel in einigen Fällen nicht richtig ausgewertet wird, aber es ist mir nie gelungen.



Lizenziert unter: CC-BY-SA with attribution
Nicht verbunden mit Stack Overflow
Ist diese KB legal? Ja, lerne warum
Lizenziert unter: CC-BY-SA with attribution
Nicht verbunden mit Stack Overflow
Ist diese KB legal? Ja, lerne warum