如何使用Castle Windsor创建客户端版本的RavenDB会话> 3.0.3660?

时间:2017-07-12 09:57:38

标签: castle-windsor ravendb factory

我使用Castle Windsor v3.4.0创建RavenDB文档会话实例但是当我使用晚于3.0.3660的RavenDB客户端版本时,我在调用Store方法时遇到此错误:

Castle.MicroKernel.ComponentNotFoundException: 'No component for supporting the service System.Net.Http.HttpMessageHandler was found'

这是我能想出的最小的代码,它可以重现错误:

using Castle.Facilities.TypedFactory;
using Castle.MicroKernel.Registration;
using Castle.Windsor;
using Raven.Client;
using Raven.Client.Document;

public class Program
{
    public static void Main()
    {
        var container = new WindsorContainer();
        container.AddFacility<TypedFactoryFacility>();

        container.Register(
            Component
                .For<IDocumentStore>()
                .ImplementedBy<DocumentStore>()
                .DependsOn(new { Url = "http://localhost:8081", DefaultDatabase = "Test" })
                .OnCreate(x => x.Initialize())
                .LifeStyle.Singleton,
            Component
                .For<IDocumentSession>()
                .UsingFactoryMethod(x => x.Resolve<IDocumentStore>().OpenSession())
                .LifeStyle.Transient);

        using (var documentSession = container.Resolve<IDocumentSession>())
        {
            documentSession.Store(new object());
            documentSession.SaveChanges();
        }
    }    
}

以下是我认为正在发生的事情。在v3.0.3660之后对RavenDB客户端进行了更改,改变了在HttpJsonRequest类中创建HttpMessageHandler的方式:

https://github.com/ravendb/ravendb/commit/740ad10d42d50b1eff0fc89d1a6894fd57578984

我相信这种改变与我在Windsor容器中使用TypedFactoryFacility相结合,导致RavenDB请求HttpJsonRequestFactory的实例及其与Windsor的依赖关系,而不是使用它自己的内部实例。

如何更改代码以避免此问题,以便我可以使用更新版本的RavenDB客户端?

1 个答案:

答案 0 :(得分:3)

鉴于您的MVCE,Windsor设置为注入对象的属性。因此,在创建DocumentStore时,Castle正在尝试查找HttpMessageHandlerFactory属性的值,并且由于没有为该特定类型配置任何内容而失败。

我能够让你的例子工作(至少,它必须将数据插入到我的不存在的服务器中),只需过滤掉该属性:

container.Register(
    Component.For<IDocumentStore>()
            .ImplementedBy<DocumentStore>()
            .DependsOn(new { Url = "http://localhost:8081", DefaultDatabase = "Test" })
            .OnCreate(x => x.Initialize())
            .PropertiesIgnore(p => p.Name == nameof(DocumentStore.HttpMessageHandlerFactory))
            .LifeStyle.Singleton);

或者,如果您有值,则可以将其添加到传递给DependsOn()的对象。