我可以设置一个单元测试运行多次并返回成功百分比吗

本文关键字:返回 成功 百分比 测试运行 单元 设置 一个 我可以 | 更新日期: 2023-09-27 18:30:05

我是单元测试的新手,一直在网上搜索,试图找出如何进一步自动化我的单元测试。我正在构建一个注册方案,我想做的是用各种硬盘序列号、应用程序编号等进行测试。我想生成一个注册密钥,然后检查它以确保它正确解码。我希望通过各种输入自动运行测试(使用集成的Visual Studio测试环境),并在数千次运行后,找出成功和不成功的测试百分比。这可能吗?以下是我的测试方法:

[TestMethod]
    public void GeneratingValidKeyTest()
    {
        int numReadDevices;
        string appNum = "123";
        string hddSerial = "1234567890";
        string numDevices = "12";
        string regNumber = Registration.GenerateKey(appNum, numDevices, hddSerial);
        Assert.IsTrue(Registration.CheckKey(regNumber, appNum, out numReadDevices, hddSerial), "Generated key does not pass check.");
        Assert.AreEqual(int.Parse(numDevices), numReadDevices,"Number of registered devices does not match requested number");
    }

我可以设置一个单元测试运行多次并返回成功百分比吗

就我个人而言,我发现"向该方法抛出大量随机数据并确保其全部工作"的方法几乎没有价值。

如果你给这个方法500个不同的序列号,它们都有效,那没关系。但是他们在您的代码中测试了哪些特定的场景?如果您不能回答这个问题,那么您可能正在复制测试场景,更重要的是,缺少测试场景。

与其把测试用例扔到墙上,看看有什么问题,不如分析你的代码,确定关键的成功和失败标准,并制定符合这些标准的测试。这还有一个附带的好处,那就是让您的测试更加详细,并让您的团队成员通过读取测试名称更好地了解代码应该做什么。您的测试应该命名为它们正在测试的,而不是GeneratingValidKeyTest

举个例子,假设你正在构建一个计算器。用你的方法,你会抛出大量的加法案例——1+1、1+3、5+30等。但你很可能会错过1+Int32.MaxValue。或者你可能不会尝试加负数。或者测试如果输入不是有效数字会发生什么。等等。

好的测试会迫使你在写这些场景时仔细思考。

如果您使用NUnit,您可以设置一系列ValueSources来提供给您的方法。

如果你有一个单独的appNum、hddSerial和numDevices的值源,你会得到appNum*hddSerial*numDevices的测试数量。

不过,你不应该以找到通过测试的百分比为目标。单元测试的目的是确保所有测试场景都通过

以Max为例,使其成为ValueSources:

[Test]
public void DivideTest([ValueSource("AppNums")]string appNum, [ValueSource("Serials")]string hddSerial, [ValueSource("NumDevices")]string numDevices)
{
    string regNumber = Registration.GenerateKey(appNum, numDevices, hddSerial);
    Assert.IsTrue(Registration.CheckKey(regNumber, appNum, out numReadDevices, hddSerial), "Generated key does not pass check.");
    Assert.AreEqual(int.Parse(numDevices), numReadDevices,"Number of registered devices does not match requested number");
}
static object[] AppNums =
{
    "1", "2", "3", "4", "5", "6", "7"
};
static object[] Serials =
{
    "EXAMPLE", "ANOTHER", "AND AGAIN"
};
static object[] NumDevices =
{
    "1", "2", "3", "4", "5", "6", "7"
};

在NUnit中,它看起来像

[Test, TestCaseSource("DivideCases")]
public void DivideTest(string appNum, string hddSerial, string hddSerial)
{
    string regNumber = Registration.GenerateKey(appNum, numDevices, hddSerial);
    Assert.IsTrue(Registration.CheckKey(regNumber, appNum, out numReadDevices, hddSerial),              "Generated key does not pass check.");
    Assert.AreEqual(int.Parse(numDevices), numReadDevices,"Number of registered devices does not match requested number");
}
static object[] DivideCases =
{
    new object[] { "123", "3", "4" },
    new object[] { "12223", "35", "54" },
    new object[] { "12123123", "23", "14" }
};

您可以使用Microsoft的单元测试框架,并使其从数据源读取测试数据。使用MSTest的优点是它将在Visual Studio的速成版上运行。

不过,你不会得到一定百分比的错误,我同意@DanielMann的观点,相反,你必须确保你的测试涵盖了所有可能性,并且都通过了。

因此,考虑到您已经完成了这项工作,现在您有了要测试的案例列表,您可以使用下面的代码。它使用DataSourceAttribute:

[TestClass]
public class RegistrationTests
{
    public TestContext TestContext { get; set; }
    [TestMethod]
    [DataSource(
        "System.Data.OleDb", 
        @"Provider=Microsoft.Jet.OLEDB.4.0;Data Source=""C:'MySolution'Serial numbers.mdb""",
        "Serials",
        DataAccessMethod.Sequential
    )]
    public void GeneratingValidKeyTest()
    {
        // Arrange
        int numReadDevices;
        var appNum = TestContext.DataRow["appNum"].ToString();
        var hddSerial = TestContext.DataRow["hddSerial"].ToString();
        var numDevices = TestContext.DataRow["numDevices"].ToString();
        // Act
        var regNumber = Registration.GenerateKey(appNum, numDevices, hddSerial);
        // Assert
        Assert.IsTrue(
            Registration.CheckKey(regNumber, appNum, out numReadDevices, hddSerial), 
            "Generated key does not pass check."
        );
        Assert.AreEqual(
            int.Parse(numDevices), numReadDevices, 
            "Number of registered devices does not match requested number"
        );
    }
}

在测试资源管理器窗口中,您将得到这样的输出(首先显示失败的测试):

Test Name:  GeneratingValidKeyTest
Test FullName:  MySolution.UnitTest.RegistrationTests.GeneratingValidKeyTest
Test Source:    C:'MySolution'MySolution.UnitTest'RegistrationTests.cs : line 15
Test Outcome:   Failed
Test Duration:  0:00:00,017832
Result1 Name:   GeneratingValidKeyTest (Data Row 1)
Result1 Outcome:    Failed
Result1 Duration:   0:00:00,0082728
Result1 StackTrace: at MySolution.UnitTest.RegistrationTests.GeneratingValidKeyTest() in C:'MySolution'MySolution.UnitTest'RegistrationTests.cs:line 27
Result1 Message:    Assert.AreEqual failed. Expected:<11>. Actual:<12>. Number of registered devices does not match requested number
Result3 Name:   GeneratingValidKeyTest (Data Row 0)
Result3 Outcome:    Passed
Result3 Duration:   0:00:00,0089332
Result3 StackTrace:
Result3 Message: