如果您不需要使用接口,则可以通过使用具体类型来获得:
using System;
using Microsoft.Practices.Unity;
using Newtonsoft.Json;
namespace TestGrounds
{
public class TestClass
{
#region Properties
public int TestIntegerProperty { get; set; }
public string TestStringProperty { get; set; }
#endregion
}
internal class Program
{
#region Static Methods
private static void Main(string[] args)
{
const string json =
@"{ TestIntegerProperty: 1, TestStringProperty: 'Hello', AnotherTestPropertyToIgnore: 'Sup' }";
registerDependencyFromJson<TestClass>(json);
Console.ReadKey();
}
private static void registerDependencyFromJson<T>(string json) where T: class, new()
{
var deserializedObject = JsonConvert.DeserializeObject<T>(json);
var type = deserializedObject.GetType();
var container = new UnityContainer();
container.RegisterInstance(type, type.Name, deserializedObject, new ContainerControlledLifetimeManager());
}
#endregion
}
}
无论如何,这可能会更好,因为接口可能需要方法实现,任何代理都不能很好地处理(不过,我认为 Castle 有某种方法拦截器)。具体类型摆脱了那里的任何假设。唯一真正的要求是new()。
更新:
这是从字符串名称创建类型的示例,并且还显示了无效类型:
using System;
using Microsoft.Practices.Unity;
using Newtonsoft.Json;
namespace TestGrounds
{
public class TestClass
{
#region Properties
public int TestIntegerProperty { get; set; }
public string TestStringProperty { get; set; }
#endregion
}
public class BadTestClass : TestClass
{
#region Properties
public double TestDoubleProperty { get; set; }
#endregion
#region Constructors
public BadTestClass(double testDouble)
{
TestDoubleProperty = testDouble;
}
#endregion
}
internal class Program
{
#region Static Methods
private static void Main(string[] args)
{
const string json =
@"{ TestIntegerProperty: 1, TestStringProperty: 'Hello', AnotherTestPropertyToIgnore: 'Sup' }";
var type = Type.GetType("TestGrounds.TestClass", true);
var badType = Type.GetType("TestGrounds.BadTestClass", true);
registerDependencyFromJson(type, json);
try
{
registerDependencyFromJson(badType, json);
}
catch(Exception ex)
{
Console.WriteLine(ex.Message);
}
Console.ReadKey();
}
private static void registerDependencyFromJson(Type type, string json)
{
// type requires a default constructor for this to work
var constructor = type.GetConstructor(Type.EmptyTypes);
if(constructor == null)
{
throw new ArgumentException("Type must have a parameterless constructor.");
}
var deserializedObject = JsonConvert.DeserializeObject(json, type);
var container = new UnityContainer();
container.RegisterInstance(type, type.Name, deserializedObject, new ContainerControlledLifetimeManager());
}
#endregion
}
}