2010-02-23 72 views
5

我有下面的代码,它在运行时出现故障......如何模拟ASP.NET ServerVariables [“HTTP_HOST”]的值?

var mock = new Mock<ControllerContext>(); 
mock.SetupGet(x => x.HttpContext.Request 
    .ServerVariables["HTTP_HOST"]).Returns(domain); 

** RunTime Error: Invalid setup on non-overridable property

我有我的控制器,它需要检查用户请求/去域一些代码。

我不确定如何模拟它?有任何想法吗?

PS。我在上面的例子中使用了Moq framewoke ..所以我不确定这是一个问题,等等?

回答

6

您不能模拟NameValueCollection上的索引器,因为它不是虚拟的。我会做的是模拟ServerVariables属性,因为它是虚拟的。你可以填写你自己的NameValueCollection。见下面

这里是我会做:

var context = new Mock<ControllerContext>(); 
NameValueCollection variables = new NameValueCollection(); 
variables.Add("HTTP_HOST", "www.google.com"); 
context.Setup(c => c.HttpContext.Request.ServerVariables).Returns(variables); 
//This next line is just an example of executing the method 
var domain = context.Object.HttpContext.Request.ServerVariables["HTTP_HOST"]; 
Assert.AreEqual("www.google.com", domain); 
+0

哈!当然!! <3 ..另外,你使用了'context.Setup'。我正在使用'context.SetupGet' ...你为什么使用它? (我对Moq真的很陌生......) – 2010-02-23 01:48:51

+0

可能存在某种差异,但我也不是错综复杂的专家,所以我只是使用安装程序()来保持一致性:)本文似乎稍微解释一下这些差异,尽管我很乐意听到这个问题的专家:http://stackoverflow.com/questions/1073846/need-help-understand-moq-better – Eric 2010-02-23 01:59:01

1

您可以覆盖HttpContext的接口和在测试中嘲笑它:

interface IHttpContextValues 
{ 
    string HttpHost { get; } 
} 

class HttpContextValues : IHttpContextValues 
{ 
    public string HttpHost 
    { 
     get { return HttpContext.Current.Request.ServerVariables["HTTP_HOST"]; } 
    } 
} 

class BaseController : Controller 
{ 
    public IHttpContextValues HttpContextValues; 
    BaseController() 
    { 
     HttpContextValues = new HttpContextValues(); 
    } 
} 

然后你在使用HttpContextValues而不是ControllerContext.HttpContext你控制器代码。你不必嘲笑任何组合。