Единичный код тестирования, который вызывает VirtualPathUtility.ToAbsolute

Я пытаюсь использовать unit test код, который вызывает VirtualPathUtility.ToAbsolute.

Возможно ли это с помощью инструментов тестирования модулей, поставляемых с VS 2008? Если нет, возможно ли это с более поздней версией Visual Studio?

Ответ 1

Статические классы и методы действительно сложно работать в модульных тестах (это одна из причин, почему я стараюсь их избегать). В этом случае я, вероятно, разработал обертку вокруг статического класса, содержащий только те методы, которые я использую. Затем я использовал бы свой класс-оболочку вместо реального класса. Класс-оболочка будет сконструирован таким образом, чтобы его легко было издеваться.

Пример (сорт) с помощью RhinoMocks. Обратите внимание, что он использует инъекцию зависимости, чтобы дать тестируемому классу копию обертки. Если поставляемая оболочка имеет значение null, она создает один.

public class MyClass
{
     private VPU_Wrapper VPU { get; set; }

     public MyClass() : this(null) {}

     public MyClass( VPU_Wrapper vpu )
     {
         this.VPU = vpu ?? new VPU_Wrapper();
     }

     public string SomeMethod( string path )
     {
         return this.VPU.ToAbsolute( path );
     }
}

public class VPU_Wrapper
{
    public virtual string ToAbsolute( string path )
    {
         return VirtualPathUtility.ToAbsolute( path );
    }
}

[TestMethod]
public void SomeTest()
{
     string path = "~/path";
     string expected = "/app/path";

     var vpu = MockRepository.GenerateMock<VPU_Wrapper>();
     vpu.Expect( v => v.ToAbsolute( path) ).Return( expected );

     MyClass class = new MyClass( vpu );

     string actual = class.SomeMethod( path );

     Assert.AreEqual( expected, actual );

     vpu.VerifyAllExpectations();
}

Ответ 2

Мы хорошо прошли VS 2008, но для тех, кто все еще борется с этой проблемой, я нашел решение на: http://forums.asp.net/t/995143.aspx?Mocking+HTTPContext+object.

Используйте следующий код в тестовом init, чтобы переопределить значения AppDomain по умолчанию. (Статические методы VirutalPathUtility будут использовать ваши новые значения.)

[TestInitialize]
public void Initialize()
{
    // Fake out env for VirtualPathUtility.ToAbsolute(..)
    string path = AppDomain.CurrentDomain.BaseDirectory; 
    const string virtualDir = "/";
    AppDomain.CurrentDomain.SetData(".appDomain", "*");
    AppDomain.CurrentDomain.SetData(".appPath", path);
    AppDomain.CurrentDomain.SetData(".appVPath", virtualDir);
    AppDomain.CurrentDomain.SetData(".hostingVirtualPath", virtualDir);
    AppDomain.CurrentDomain.SetData(".hostingInstallDir", HttpRuntime.AspInstallDirectory);
    TextWriter tw = new StringWriter();
    HttpWorkerRequest wr = new SimpleWorkerRequest("default.aspx", "", tw);
    HttpContext.Current = new HttpContext(wr);
}

Ответ 3

Используя Microsoft Fakes, мы можем легко подделать метод VirtualPathUtility ToAbsolute.

  • Обзор System.Web в ссылках > Щелкните правой кнопкой мыши > Добавить сборку подделок.

Использовать следующий код

using Microsoft.QualityTools.Testing.Fakes;
using Microsoft.VisualStudio.TestTools.UnitTesting;
using System.Web.Fakes;

 public class TestCode
    {
        [TestMethod]
        public void TestSummaryTabLinks()
        {
            using (ShimsContext.Create())
            {
                //Fake VirtualPathUtility ToAbsolute method to Work properly in case of Unit Test Project
                //For Finding Relative url.
                ShimVirtualPathUtility.ToAbsoluteString = (string s) => { return s; };

                MyClass class = new MyClass( vpu );

                string actual = class.SomeMethod( path );

                Assert.AreEqual( expected, actual );

            }
      }

}