使用IoC容器作为HttpHandler的服务定位器

时间:2010-08-23 21:07:45

标签: nunit inversion-of-control castle-windsor moq httphandler

这个问题与我的其他post有关。

好的,所以经过一番混乱我决定这样做。虽然我在NUnit中遇到以下错误:但无法加载文件或程序集'Castle.Core,Version = 1.0.3.0,Culture = neutral,PublicKeyToken = 407dd0808d44fbdc'或其中一个依赖。定位的程序集的清单定义与程序集引用不匹配。 (HRESULT的异常:0x80131040)所以不确定那里发生了什么?

只是想知道其他人对设计的看法,以及是否有任何明显的“禁忌”或改进。即基本处理程序的构造函数是实例化windsor组件的好地方,还是有更好的地方可以做到这一点?正如我在原帖中所说的那样,以这种方式做事的想法是保持组件很好地解耦并使单元测试变得容易。我还应该补充一点我是单元测试的新手,嘲笑。谢谢!

public abstract class BaseHttpHandler : IHttpHandler
{
    private HttpContext _httpContext;
    private ILogger _logger;
    private IDataRepository _dataRepository;
    protected HttpRequest Request { get { return _httpContext.Request; } }
    protected HttpResponse Response { get { return _httpContext.Response; } }
    protected bool IsRequestFromUAD { get { return Request.UserAgent == null ? false : Request.UserAgent.Equals("UAD"); } }
    protected ILogger Logger { get { return _logger; } }
    protected IDataRepository DataRepository { get { return _dataRepository; } }
    public virtual bool IsReusable { get { return false; } }

    public BaseHttpHandler()
    {
        var container = new WindsorContainer(new XmlInterpreter(new ConfigResource("castle")));
        _logger = container.Resolve<ILogger>();
        _dataRepository = container.Resolve<IDataRepository>();
    }

    public void ProcessRequest(HttpContext context)
    {
        _httpContext = context;
        ProcessRequest(new HttpContextWrapper(context));
    }

    public abstract void ProcessRequest(HttpContextBase context);
}

public class UADRecordHttpHandler : BaseHttpHandler
{
    public override void ProcessRequest(HttpContextBase context)
    {
        if (IsRequestFromUAD)
        {
            using (var reader = new StreamReader(context.Request.InputStream))
            {
                string data = reader.ReadToEnd();

                if (Logger != null)
                    Logger.Log(data);

                if(DataRepository != null)
                    DataRepository.Write(data);

                context.Response.Write(data);
            }
        }
        else
            ReturnResponse(HttpStatusCode.BadRequest);
    }
}

2 个答案:

答案 0 :(得分:1)

这是一件非常糟糕的事情,你在这里做什么。每个应用程序应该有一个容器实例,而使用此代码,每个请求都有一个。

答案 1 :(得分:1)

关于NUnit中的错误:确保GAC中没有其他版本的Castle程序集。如果是,请卸载它们。

关于您的BaseHttpHandler:此实现的问题在于您正在创建一个新容器。相反,每个应用程序使用一个容器,如Krzysztof所说。使用静态服务定位器,例如CommonServiceLocator。 (我从不推荐这个,但它是少数确实有意义的地方之一。)