Reputation: 14791
I am developing an Asp.net mvc web application. I am doing Unit Test to my application. I am using Moq to mock objects. I am trying to mock Url helper class. I found this link- asp.net mvc: how to mock Url.Content("~")?. Using that class, I can mock UrlHelper
class in unit test.
I created a BaseController
like this
public class BaseController : Controller
{
private IUrlHelper _urlHelper;
public new IUrlHelper Url
{
get { return _urlHelper; }
set { _urlHelper = value; }
}
}
Here is the IUrlHelper
interface/abstraction
public interface IUrlHelper
{
string Action(string actionName);
string Action(string actionName, object routeValues);
string Action(string actionName, string controllerName);
string Action(string actionName, RouteValueDictionary routeValues);
string Action(string actionName, string controllerName, object routeValues);
string Action(string actionName, string controllerName, RouteValueDictionary routeValues);
string Action(string actionName, string controllerName, object routeValues, string protocol);
string Action(string actionName, string controllerName, RouteValueDictionary routeValues, string protocol, string hostName);
string Content(string contentPath);
string Encode(string url);
string RouteUrl(object routeValues);
string RouteUrl(string routeName);
string RouteUrl(RouteValueDictionary routeValues);
string RouteUrl(string routeName, object routeValues);
string RouteUrl(string routeName, RouteValueDictionary routeValues);
string RouteUrl(string routeName, object routeValues, string protocol);
string RouteUrl(string routeName, RouteValueDictionary routeValues, string protocol, string hostName);
}
I mock the Url.Content()
in the unit test like this
Mock<IUrlHelper> urlHelperMock = new Mock<IUrlHelper>();
urlHelperMock
.Setup(x => x.Content(It.IsAny<string>()))
.Returns<string>(x => "~/" + x);// Mock Content method of Url Helper
Test run successfully and working fine. The problem is I cannot use it in real time application. I mean when I run my app and call Url.Content("path"), it throws null exception.
For example
public class ExampleController : BaseController
{
public string GetPath()
{
return Url.Content("~/Path/To/File");
}
}
Url.Content
in this code throws null exception. It is working fine in unit test. How can I fix that code?
Upvotes: 3
Views: 1251
Reputation: 247098
In this case there really isn't a need to abstract the UrlHelper
. Just mock up the helper for the test to do what is required.
For example, assuming
public class ExampleController : Controller {
public string GetContent() {
return Url.Content("~/Path/To/File");
}
}
Here is a test that mocks the UrlHelper
using moq to work just like in original example
[TestClass]
public class UrlHelperTest {
[TestMethod]
public void MockUrlHelper() {
//Arrange
var expectedPath = "~/Path/To/File";
var expectedContent = "<p>Fake content here<p>";
var urlHelperMock = new Mock<UrlHelper>();
urlHelperMock
.Setup(m => m.Content(expectedPath))
.Returns(expectedContent)
.Verifiable();
var sut = new ExampleController();
sut.Url = urlHelperMock.Object; //Set mock UrlHelper
//Act
var actualContent = sut.GetContent();
//Assert
urlHelperMock.Verify();
Assert.AreEqual(expectedContent, actualContent);
}
}
So now the test can be performed and also the framework will populate the necessary controller properties in production because technically nothing was changed from the original framework to custom abstractions.
Upvotes: 5