2009-09-21 44 views
0
var mockedService = new Mock<IService>(); 
mockedService.Setup(x => x.InterfaceMethod(args)).Returns(value); 
_Service = mockedService.Object; 
MyController controller =new MyController(_Service); 

var result = (ViewResult)controller.Foo(); 

现在这个富()方法包含下列API调用如何绕过HTTPContext的使用。

HttpContext.GetGlobalResourceObject(...,..); 

但HttpContext的是空,因为我只是单元测试,我没有验证。因此不会填充HTTPContext对象。

因为HTTPContext是密封的,所以我不能设置这个类的期望值。

我一直在寻找中网,但只有样品假冒HTTPContextBase

现在怎么让我的单元测试通过。有什么建议么。?

感谢,

维杰

+1

第二个代码块肯定有问题... – 2009-09-21 09:37:54

+1

我的意思是,首先制作一个新的控制器实例,下一行通过重新分配控制器变量将其扔掉。 – 2009-09-21 09:38:57

+0

在第二个代码片段中,为什么要将控制器变量分配两次?第一行似乎是多余的。 – 2009-09-21 09:39:00

回答

1

问题是你不设置为“中心”的方法的期望。当你嘲笑一个对象时,所有的实现都会被Noop替代,除非你使用Expectation指定。

我猜你嘲笑GetValueFromResource而不是Centres因为Centres电话GetValueFromResource。如果是这种情况,嘲笑GetValueFromResource可能是一个多余的假,你不需要它。另外,正如在Moq的其他几篇帖子中指出的那样,你需要确保你不是在嘲笑你正在测试的东西。如果你真的试图测试MyController,你会想要嘲笑它的任何依赖,但不是MyController本身。这会导致你无法结束混乱。

编辑

在此基础上的反馈,似乎你已经知道你真正的问题是,你需要模拟的HttpContext。嘲笑HTTPContext并不重要。有一些工具可以在本地执行,例如Type Mock,但问题是环境上下文不可测试。

应该正在做的是请求依赖关系,这些依赖关系为您提供所需的信息,同时抽象出它们的实现。例如,在你的情况下,你似乎使用HTTPContext来访问资源。如果你需要这样的事情,你可以使用一个很好的接口将是:

public interface IResourceStore 
{ 
    object GetGlobalResource(string classKey, string resourceKey); 
} 

你的默认实现将使用的HttpContext,但现在您可以直接让你可以模拟接口,让您的myController的类的使用,而不是HttpContext的。

Mock<IResourceStore> resourceStore = new Mock<IResourceStore>(); 
//setup resourceStore expectations here 

MyController testingTarget = new MyController(_Service, resourceStore.Object); 
//target assertions here 

希望这会有所帮助。

+0

@Anderson GetValueFromResource()方法使用HTTPContext,所以当遇到该API调用时,会引发空引用异常。现在我该怎么做。 ?有什么建议么。? – vijaysylvester 2009-09-21 14:32:21

+0

我通常创建一个帮助类,它为我访问HTTPContext,我从需要HTTPContext的类中使用它。这样你可以避免从任何地方引用HTTPContext。另外,在互联网上嘲笑HTTPContext也有不少教程。无论我希望你已经知道,嘲笑你正在测试的东西并不是一个好主意。 – 2009-09-21 14:35:10

+0

我们可以手动设置HTTPCOntext对象吗? 像这样HTTPcontext context = new HTTPCOntext(Req,Res)。 手动构建Req和Res对象之后。 – vijaysylvester 2009-09-22 03:45:32