.net 无依赖属性的统一构建

.net 无依赖属性的统一构建,.net,dependency-injection,unity-container,.net,Dependency Injection,Unity Container,我有一个第三方图书馆返回一个类instace。它不在我的控制范围内,但我想使用Unity插入它的公共属性。由于类既不是部分的,也不是继承的,所以我无法将DependecyAttribute添加到它的属性中,我想知道是否可以使用UnityXML配置来执行inyection 是否可以使用Unity的XML配置来配置构建依赖项?如果答案是肯定的。如何配置XML来实现这一点 我试过: <register type="IService" mapTo="Service"> <!--Serv

我有一个第三方图书馆返回一个类instace。它不在我的控制范围内,但我想使用
Unity
插入它的公共属性。由于类既不是部分的,也不是继承的,所以我无法将
DependecyAttribute
添加到它的属性中,我想知道是否可以使用
Unity
XML配置来执行inyection

是否可以使用Unity的XML配置来配置构建依赖项?如果答案是肯定的。如何配置XML来实现这一点

我试过:

<register type="IService" mapTo="Service"> <!--Service has public constructor-->
</register>

<!--ThirdPartyObj has no interface and no public constructor-->
<register type="ThirdPartyObj " mapTo="ThirdPartyObj">
    <!-- Inject the property "Service" -->
    <property name="Service" /> //type of the property is IService
</register>

为此创建一个统一友好的包装:

public interface IThirdpartyWrapper
{
   ThirdpartyObj ConfiguredObject{get;}
}
public class ThirdpartyWrapper:IThirdpartyWrapper
{
    private ThirdpartyObject _thirdPartyObject;
     public ThirdpartyWrapper(IService myService)
    {
         _thirdPartyObject=ThirdPartyLibrary.getFooInstance();
         _thirdPartyObject.Service=myService;
    }
     public ThirdpartyObj ConfiguredObject
    {
      get{return _thirdPartyObject;}
    }

}
现在我们有了一个团结友好的班级

Unity Xml配置:

<register type="IService" mapTo="Service"> <!--Service has public constructor-->
</register>

<!--ThirdPartyObj has no interface and no public constructor-->
<register type="IThirdpartyWrapper" mapTo="IThirdpartyWrapper">
</register>

当我执行以下操作时:

var wrapper=_container.Resolve<IThirdpartyWrapper>();
var configuredObject=wrapper.ConfiguredObject;
var wrapper=\u container.Resolve();
var configuredObject=wrapper.configuredObject;
包装器实例化第三方对象的副本,然后将服务注入适当的属性(或者可以通过方法调用等传递)


这不需要太多的代码,是单元可测试的,可以满足您的需要

根据您发布的代码,应该没有问题

我创建了两个项目:一个控制台应用程序和一个名为ThirdPartyLibrary的类库

第三方数据库由以下内容组成(根据发布的代码推断):

XML配置如下所示:

<?xml version="1.0"?>
<configuration>
  <configSections>
    <section name="unity" type="Microsoft.Practices.Unity.Configuration.UnityConfigurationSection, Microsoft.Practices.Unity.Configuration"/>
  </configSections>

  <unity xmlns="http://schemas.microsoft.com/practices/2010/unity">

    <container>
      <register type="ThirdPartyLibrary.IService, ThirdPartyLibrary" mapTo="ThirdPartyLibrary.Service, ThirdPartyLibrary">
      </register>

      <register type="ThirdPartyLibrary.IThirdPartyObj, ThirdPartyLibrary" mapTo="ThirdPartyLibrary.ThirdPartyObj, ThirdPartyLibrary">
        <!-- Inject the property "Service" -->
        <property name="Service" />
      </register>
    </container>

  </unity>
  <startup>
    <supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.5"/>
  </startup>
</configuration>

这工作正常,并输出
消息如预期。也许,确切的场景与您发布的(我假设是虚构的)示例不同,或者其他一些配置不正确

您好,谢谢您的回答,但我想要的是在第三方服务,而不是三方服务。在我的最后一段代码中获取一个战利品来检查我想要的结果。修复。撤销了DI,但仍然适用。只需创建一个包装器,使DI不友好的代码DI友好。在上面的示例中,我们将IService实例注入包装器并将其传递给第三方对象。谢谢Tuzo!至少我确认了我的方法是对的。这一定是因为我正在尝试您的示例,而我的调试器中的foo.Service为Null。这很奇怪。在我接受你的回答之前,给我一些时间检查一下配置中的错误。我刚刚创建了一个新的项目副本粘贴我的代码和配置,一切都很好。
namespace ThirdPartyLibrary
{
    public interface IService
    {
        string GetServiceMessage { get; }
    }

    public class Service : IService
    {
        public Service() { }

        public string GetServiceMessage
        {
            get { return "The message!"; }
        }
    }

    public static class ThirdPartyLibrary
    {
        public static ThirdPartyObj GetFooInstance()
        {
            return new ThirdPartyObj();
        }
    }

    public interface IThirdPartyObj { }
    public class ThirdPartyObj : IThirdPartyObj
    {
        internal ThirdPartyObj() { }
        public IService Service { get; set; }
    }
}
<?xml version="1.0"?>
<configuration>
  <configSections>
    <section name="unity" type="Microsoft.Practices.Unity.Configuration.UnityConfigurationSection, Microsoft.Practices.Unity.Configuration"/>
  </configSections>

  <unity xmlns="http://schemas.microsoft.com/practices/2010/unity">

    <container>
      <register type="ThirdPartyLibrary.IService, ThirdPartyLibrary" mapTo="ThirdPartyLibrary.Service, ThirdPartyLibrary">
      </register>

      <register type="ThirdPartyLibrary.IThirdPartyObj, ThirdPartyLibrary" mapTo="ThirdPartyLibrary.ThirdPartyObj, ThirdPartyLibrary">
        <!-- Inject the property "Service" -->
        <property name="Service" />
      </register>
    </container>

  </unity>
  <startup>
    <supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.5"/>
  </startup>
</configuration>
class Program
{
    static void Main(string[] args)
    {
        IUnityContainer container = new UnityContainer(); //create container
        container.LoadConfiguration(); // load from XML config
        ThirdPartyObj foo = ThirdPartyLibrary.ThirdPartyLibrary.GetFooInstance(); //get third party instance
        container.BuildUp(foo.GetType(), foo); //inyect dependencies
        Console.WriteLine(foo.Service.GetServiceMessage);
    }
}