2010-04-17 10 views
12

Estoy usando VS 2010 RTM y trato de realizar una validación básica en un tipo simple usando MetadataTypeAttribute. Cuando pongo el atributo de validación en la clase principal, todo funciona. Sin embargo, cuando lo puse en la clase de metadatos, parece ser ignorado. Debo extrañar algo trivial, pero he estado atascado en esto por un tiempo..NET 4 RTM MetadataType atributo ignorado al usar Validator

Eché un vistazo al bloque de validación de la Biblioteca Empresarial como una solución, pero no admite la validación de propiedades únicas de fábrica. ¿Algunas ideas?

class Program 
{ 
    static void Main(string[] args) 
    { 
     Stuff t = new Stuff(); 

     try 
     { 
      Validator.ValidateProperty(t.X, new ValidationContext(t, null, null) { MemberName = "X" }); 
      Console.WriteLine("Failed!"); 
     } 
     catch (ValidationException) 
     { 
      Console.WriteLine("Succeeded!"); 
     } 
    } 
} 

[MetadataType(typeof(StuffMetadata))] 
public class Stuff 
{ 
    //[Required] //works here 
    public string X { get; set; } 
} 

public class StuffMetadata 
{ 
    [Required] //no effect here 
    public string X { get; set; } 
} 

Respuesta

23

Parece que el validador no respeta MetadataTypeAttribute:

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

La relación debe ser explícitamente registrado:

TypeDescriptor.AddProviderTransparent(
     new AssociatedMetadataTypeTypeDescriptionProvider(
      typeof(Stuff), 
      typeof(StuffMetadata)), 
     typeof(Stuff)); 

Esta clase de ayuda registrará todas las relaciones de metadatos en una asamblea:

public static class MetadataTypesRegister 
{ 
    static bool installed = false; 
    static object installedLock = new object(); 

    public static void InstallForThisAssembly() 
    { 
     if (installed) 
     { 
      return; 
     } 

     lock (installedLock) 
     { 
      if (installed) 
      { 
       return; 
      } 

      foreach (Type type in Assembly.GetExecutingAssembly().GetTypes()) 
      { 
       foreach (MetadataTypeAttribute attrib in type.GetCustomAttributes(typeof(MetadataTypeAttribute), true)) 
       { 
        TypeDescriptor.AddProviderTransparent(
         new AssociatedMetadataTypeTypeDescriptionProvider(type, attrib.MetadataClassType), type); 
       } 
      } 

      installed = true; 
     } 
    } 
} 
+1

Gracias por esta excelente propaganda de código !! – aikeru

+0

¿Por qué no se menciona esto en la lista MetadataTypeAttribute en MSDN? Me han colgado durante un par de horas b/c en mi proyecto MVC todo funciona bien, pero cuando creo mi aplicación de Windows necesito ser explicado –

2

Proporcionar una instancia de la clase de metadatos en lugar de la clase principal al constructor ValidationContext parece funcionar para mí.

+0

Esto funcionó para mí en 'TryValidateProperty' pero no' TryValidateObject' desafortunadamente. –

+0

@Andy Solo necesitaba ValidateProperty, así que usé este truco en lugar de la solución completa de la respuesta aceptada por el bien de código más corto. – SlimShaggy

+0

Obtengo una 'ArgumentException' que' la instancia proporcionada coincide con la ObjectInstance en el validationcontext supplied'. –

Cuestiones relacionadas