asp.net mvc: как издеваться над Url.Content("~")?

Кто -нибудь знает, как издеваться Url.Content("~")?

(Кстати: я использую Moq)

4 ответа

Решение

Вы имеете в виду Url Я полагаю, что свойство в контроллерах имеет тип UrlHelper, Единственный способ, которым мы смогли высмеять это, это извлечь IUrlHelper интерфейс и создать UrlHelperWrapper класс, который реализует его и оборачивает нативный UrlHelper тип. Затем мы определяем новое свойство на нашем BaseController вот так:

public new IUrlHelper Url
{
    get { return _urlHelper; }
    set { _urlHelper = value; }
}

Это позволяет нам создавать издевательства IUrlHelper и внедрить их, но в случае по умолчанию использовать экземпляр нашего UrlHelperWrapper учебный класс. Извините, это долго наматывается, но, как вы обнаружили, это проблема в противном случае. Это, однако, заходит без необходимости менять какие-либо из ваших Url.Action и подобные звонки в ваших контроллерах.

Вот интерфейс:

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);
}

Я не буду давать вам определение UrlHelperWrapper - это просто глупая оболочка, которая реализует это и передает все вызовы UrlHelper,

controller.Url = Substitute.ForPartsOf<UrlHelper>();
controller.Url.Content("~").Returns("path");

Не стесняйтесь с ForPartsOf (Частичные сабвуферы и тестовые шпионы) в NUnit

Это мой метод, который высмеивает url.content (а также устанавливает IsAjaxRequest() в true)

public static void SetContextWithAjaxRequestAndUrlContent(this BaseController controller)
{
    var routes = new RouteCollection();
    RouteConfigurator.RegisterRoutesTo(routes);


    var httpContextBase = new Mock<HttpContextBase>();
    var request = new Mock<HttpRequestBase>();
    var respone = new Mock<HttpResponseBase>();


    httpContextBase.Setup(x => x.Request).Returns(request.Object);
    httpContextBase.Setup(x => x.Response).Returns(respone.Object);

    request.Setup(x => x.Form).Returns(new NameValueCollection());
    request.SetupGet(x => x.Headers).Returns(new System.Net.WebHeaderCollection {{"X-Requested-With", "XMLHttpRequest"}});
    request.Setup(o => o.ApplicationPath).Returns("/Account");
    request.Setup(o => o["X-Requested-With"]).Returns("XMLHttpRequest");

    respone.Setup(o => o.ApplyAppPathModifier("/Account")).Returns("/Account");

    controller.ControllerContext = new ControllerContext(httpContextBase.Object, new RouteData(), controller);

    controller.Url = new UrlHelper(new RequestContext(controller.HttpContext, new RouteData()), routes);
}

Я знаю, что этот контент старый, но вот как я это делаю сейчас:

IContentResolver.cs

using System.Web;

namespace Web.Controllers
{
    public interface IContentResolver
    {
        string Resolve(string imageLocation, HttpRequestBase httpRequestBase);
    }
}

ContentResolver.cs

using System.Web;
using System.Web.Mvc;

namespace Web.Controllers
{
    public class ContentResolver : IContentResolver
    {
        public string Resolve(string imageLocation, HttpRequestBase httpRequestBase)
        {
            return new UrlHelper(httpRequestBase.RequestContext).Content(imageLocation);
        }
    }
}

ContentResolverTests.cs

using System.Web;
using System.Web.Routing;
using Web.Controllers;
using Moq;
using NUnit.Framework;

namespace Web.Tests.Controllers
{
    public class ContentResolverTests
    {
        [TestFixture]
        public class when_resolving_the_content_images
        {
            [Test]
            public void then_should_resolve_to_proper_location()
            {
                // Arrange
                var resolver = new ContentResolver();

                // Act
                var httpContextBase = new Mock<HttpContextBase>();
                var httpRequestBase = new Mock<HttpRequestBase>();

                httpContextBase.Setup(@base => @base.Request).Returns(httpRequestBase.Object);

                httpRequestBase.Setup(@base => @base.ApplicationPath).Returns("/Test");


                var requestContext = new Mock<RequestContext>();
                requestContext.SetupGet(context => context.HttpContext).Returns(httpContextBase.Object);

                httpRequestBase.SetupGet(@base => @base.RequestContext).Returns(requestContext.Object);

                var url = resolver.Resolve("~/Content/loading.gif", httpRequestBase.Object);

                // Assert
                Assert.That(url, Is.EqualTo("/Test/Content/loading.gif"));
            }
        } 
    }
}
Другие вопросы по тегам