2012-05-15 25 views
2

我使用nBuilder为我的应用程序生成一些Testdata。 首先我测试它,它工作正常。 一个简单的例子:nBuilder Testdatagenerator和Reflection

Customer customer = Builder<Customer> 
        .CreateNew() 
        .Build(); 

创建一个对象,并自动填充的所有属性。 通过举例来说,如果客户包含属性:,它将与名1 等填充...

嗯,这一切工作正常,但我有麻烦做整个事情现在动态。

我现在正在做的是反射,我遍历所有实体在我的类和foreach他们应该产生一些Testdata,甚至查找和儿童名单应该填充,但多数民众赞成在一个问题..我的问题是,我如何使用以上代码与任何类型?

ANYTYPE object = Builder<ANYTYPE> ...

我试了一下:

object entity = null; //The object/Entity 
Assembly assembly = Assembly.GetAssembly(typeof(EMI_ERPContext)); //Getting Assembly 
Type type = assembly.GetType(entityName); //I know the Type 
//entity = Activator.CreateInstance(type); Do I must create an Instance here? 
object entity = Builder<dynamic> //The above code.. Tried to put dynamic as Type, but doesnt work 
       .CreateNew() 
       .Build(); 

回答

2

我有一个控制台应用程序测试(完成这里),伪造nBuilder的类/接口/方法。

所以这个工作,但没有在真正的情况下尝试。

您可以重复使用的方法是“TryToReflectBuilder”。它可能不那么冗长,但我让“一步一步”的代码,因为它可能更明确。 ReflectionConsole.Test被用作“反映的实体”。

namespace ReflectionConsole { 
    class Program { 
     static void Main(string[] args) 
     { 

      object test = TryToReflectBuilder("ReflectionConsole.Test"); 
      Console.ReadKey(); 
     } 

     public static object TryToReflectBuilder(string type) 
     { 
      //getting the assembly : not same as your way, but... that wasn't a problem for you 
      var assembly = Assembly.GetAssembly(typeof(Test)); 

      //getting the entityType by name. 
      var entityType = assembly.GetType(type); 

      //The interesting (I hope) part is starting (yeah) 
      //get the Builder<T> type 
      var builderClassType = typeof(Builder<>); 

      //create generic argument for Builder<T> will take the type of our entity (always an array) 
      Type[] args = {entityType}; 

      //pass generic arguments to Builder<T>. Which becomes Builder<entityType> 
      var genericBuilderType = builderClassType.MakeGenericType(args); 

      //create a new instance of Builder<entityType> 
      var builder = Activator.CreateInstance(genericBuilderType); 

      //retrieve the "CreateNew" method, which belongs to Builder<T> class 
      var createNewMethodInfo = builder.GetType().GetMethod("CreateNew"); 

      //invoke "CreateNew" from our builder instance which gives us an ObjectBuilder<T>, so now an ObjectBuilder<entityType> (well as an ISingleObjectBuilder<entityType>, but... who minds ;)) 
      var objectBuilder = createNewMethodInfo.Invoke(builder, null); 

      //retrieve the "Build" method, which belongs to ObjectBuilder<T> class 
      var buildMethodInfo = objectBuilder.GetType().GetMethod("Build"); 

      //finally, invoke "Build" from our ObjectBuilder<entityType> instance, which will give us... our entity ! 
      var result = buildMethodInfo.Invoke(objectBuilder, null); 

      //it would be sad to return nothing after all these efforts, no ?? 
      return result; 
     } 
    } 

    public class Builder<T> 
    { 
     public static ISingleObjectBuilder<T> CreateNew() 
     { 
      Console.WriteLine(string.Format("{0} creating new",typeof(T))); 
      return new ObjectBuilder<T>(); 
     } 
    } 

    public interface ISingleObjectBuilder<T> : IBuildable<T> 
    { 
    } 
    public interface IObjectBuilder<T> : ISingleObjectBuilder<T> 
    { 

    } 
    public interface IBuildable<T> 
    { 
     T Build(); 
    } 

    public class ObjectBuilder<T> : ISingleObjectBuilder<T> 
    { 
     public T Build() 
     { 
      Console.WriteLine(string.Format("{0} building myself", typeof(T))); 
      return Activator.CreateInstance<T>(); 
     } 
    } 

    public class Test 
    { 
    } 
}