2012-06-21 54 views
3

我已经创建了一个Person类此C#扩展方法:C# - 如何测试扩展方法?

public static class PersonExtensions { 
    public static void Rename(this Person person, String newName) { 
     person.Name = newName; 
    } 
} 

我将如何单元测试这种方法?我试过了,但PersonAccessor对象不提供Rename方法。

错误是“私人访问的重命名未找到”

当我尝试PersonExtensions_Accessor.Rename(somePerson,newName)将,它说:“有一些无效参数”

+1

扩展方法是否存储在您未引用的名称空间中? –

+1

“PersonAccessor”类是否位于不同的名称空间中?如果是这样,您需要使用包含“PersonExtensions”的名称空间 – ean5533

+1

与任何扩展方法一样,您可以像访问任何静态方法一样访问该方法,因为这就是它的真正原因。你应该可以做一些像'PersonExtensions.Rename(myPersonInstance,myNewName)'。 –

回答

1

这里是我的生产代码:

using System; 
using System.Collections.Generic; 
using System.Linq; 
using System.Text; 

namespace ClassLibrary1 
{ 
    public class Person 
    { 
     public string Name { get; set; } 
    } 

    public static class PersonExtensions 
    { 
     public static void Rename(this Person person, String newName) 
     { 
     person.Name = newName; 
     } 
    } 
} 

这里生成的测试的编辑版本:

using ClassLibrary1; 
using Microsoft.VisualStudio.TestTools.UnitTesting; 
using System; 

namespace TestProject1 
{ 


    /// <summary> 
    ///This is a test class for PersonExtensionsTest and is intended 
    ///to contain all PersonExtensionsTest Unit Tests 
    ///</summary> 
    [TestClass()] 
    public class PersonExtensionsTest 
    { 


     private TestContext testContextInstance; 

     /// <summary> 
     ///Gets or sets the test context which provides 
     ///information about and functionality for the current test run. 
     ///</summary> 
     public TestContext TestContext 
     { 
     get 
     { 
      return testContextInstance; 
     } 
     set 
     { 
      testContextInstance = value; 
     } 
     } 

     #region Additional test attributes 
    // 
    //You can use the following additional attributes as you write your tests: 
    // 
    //Use ClassInitialize to run code before running the first test in the class 
    //[ClassInitialize()] 
    //public static void MyClassInitialize(TestContext testContext) 
    //{ 
    //} 
    // 
    //Use ClassCleanup to run code after all tests in a class have run 
    //[ClassCleanup()] 
    //public static void MyClassCleanup() 
    //{ 
    //} 
    // 
    //Use TestInitialize to run code before running each test 
    //[TestInitialize()] 
    //public void MyTestInitialize() 
    //{ 
    //} 
    // 
    //Use TestCleanup to run code after each test has run 
    //[TestCleanup()] 
    //public void MyTestCleanup() 
    //{ 
    //} 
    // 
    #endregion 


     /// <summary> 
     ///A test for Rename 
     ///</summary> 
     [TestMethod()] 
     public void RenameTest() 
     { 
     Person person = new Person(); // TODO: Initialize to an appropriate value 
     string newName = string.Empty; // TODO: Initialize to an appropriate value 
     PersonExtensions.Rename(person, newName); // this could also be written as person.Rename(newName); 
     Assert.AreEqual(person.Name, string.Empty); 
     } 
    } 
} 

测试通过。

+0

我无法创建一个'Person',只有一个'PersonAccessor'。同样,我不能直接访问'PersonExtensions',而必须使用'PersonExtensions_Accessor'。 – ryyst

+0

@ryyst我已经使用了Visual Studio 2010的生成测试功能,并且它生成了一个引发null-ref的测试。我编辑了我的答案,包括通过考试。 – GregC

+0

@ryyst代码中Person和PersonAccessor的声明有什么区别?什么是命名空间,什么是访问说明符? (尝试使用反射器或对象浏览器) – GregC

8

扩展方法只是用于引用静态方法的不同方法的语法糖。请在您的单元测试中拨打PersonExtensions.Rename(...)

+0

该方法扩展了Person,而不是PersonExtensions。 – ean5533

+1

如果您不使用正在扩展的类,它将无法创建扩展方法。如果它叫'新人(...),测试会更准确。重命名(newName)' – ean5533

+0

它说:“没有找到重命名的私人访问器”。那是什么意思? 当我尝试'PersonExtensions_Accessor.Rename(somePerson,newName)'时,它说“有一些无效的参数”。 – ryyst

3

我认为一个好的方法可以直接测试Person实例中的扩展方法。

考虑到你制定的方法,样本代码将是这样的:

using System; 
using Microsoft.VisualStudio.TestTools.UnitTesting; 
using PersonExtension; // Don't forget about reference it 

namespace UnitTest { 
    [TestClass] 
    public class UnitTest { 
     Person person; 
     [TestInitialize] 
     public void Init() { 
      person = new Person("Person name"); 
     } 

     [TestMethod] 
     public void TestRename() { 
      Assert.AreEqual("Person name", person.Name); 
      person.Rename("New name"); 
      Assert.AreEqual("New name", person.Name); 
     } 
    } 
} 

记住同时引用PersonPersonExtension类和有才能在实用类的正确隐藏的水平可以访问其方法