When attempting to follow the article on mocking the htmlhelper with Moq I ran in to the following problem. The exception is thrown on creation of the htmlhelper. I am only guessing that castle windsor is being used (by seeing the error message).
The exception:
MissingMethodException occurred
Constructor on type 'Castle.Proxies.ViewContextProxy' not found.
Stack Trace:
at System.RuntimeType.CreateInstanceImpl(BindingFlags bindingAttr, Binder binder, Object[] args, CultureInfo culture, Object[] activationAttributes)
The Code:
public static HtmlHelper CreateHtmlHelper(ViewDataDictionary vd)
{
Mock<ViewContext> mockViewContext = new Mock<ViewContext>(
new ControllerContext(
new Mock<HttpContextBase>().Object,
new RouteData(),
new Mock<ControllerBase>().Object),
new Mock<IView>().Object,
vd,
new TempDataDictionary());
Mock<IViewDataContainer> mockViewDataContainer = new Mock<IViewDataContainer>();
mockViewDataContainer.Setup(v => v.ViewData).Returns(vd);
return new HtmlHelper(mockViewContext.Object, mockViewDataContainer.Object);
}
I am using ASP MVC 2, Moq 4.0 beta 3, VS2010, using the IDE's testing framework.
How do I resolve the issue and return an instance of HtmlHelper?
You get MissingMethodException
when MOQ can't match parameters to Mock<>()
to the parameters on the mocked class's constructor.
Looking at ViewContext
explains why. There is only one constructor overload and it is this:
public ViewContext(ControllerContext controllerContext, IView view, ViewDataDictionary viewData, TempDataDictionary tempData, TextWriter writer);
This setup(includes missing TextWriter
mock) should work:
Mock<ViewContext> mockViewContext = new Mock<ViewContext>(
new ControllerContext(
new Mock<HttpContextBase>().Object,
new RouteData(),
new Mock<ControllerBase>().Object),
new Mock<IView>().Object,
vd,
new TempDataDictionary()
new Mock<TextWriter>().Object);
PS MOQ uses Castle Dynamic Proxy to create mocked classes at runtime, hence the name Castle in the exception that you are seeing. Castle Windsor uses Dynamic Proxy project, but they are quite distinct projects.
I've reproduced your issue with the code from my blog post. The following updated method works for me:
public static HtmlHelper CreateHtmlHelper(ViewDataDictionary vd)
{
Mock<ViewContext> mockViewContext = new Mock<ViewContext>(
new ControllerContext(
new Mock<HttpContextBase>().Object,
new RouteData(),
new Mock<ControllerBase>().Object),
new Mock<IView>().Object,
vd,
new TempDataDictionary(),
new Mock<TextWriter>().Object);
mockViewContext.Setup(vc => vc.ViewData).Returns(vd);
var mockViewDataContainer = new Mock<IViewDataContainer>();
mockViewDataContainer.Setup(v => v.ViewData)
.Returns(vd);
return new HtmlHelper(mockViewContext.Object,
mockViewDataContainer.Object);
}
I have posted an update on my blog as well.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With