简体   繁体   English

在 C#/NUnit 测试用例中从 Excel 连续读取数据,返回第二个用例的空白数据

[英]Consecutively reading data from Excel in C#/NUnit test cases, returns blank data for 2nd Case

I'm trying to write a parameterized NUnit test that executes twice.我正在尝试编写一个执行两次的参数化 NUnit 测试。 Each time it runs, it references a different row in a spreadsheet and gets the username and password based on int rowNum .每次运行时,它都会引用电子表格中的不同,并根据 int rowNum获取用户名和密码。

    class Test
    {
        //Run the test twice
        [Test,TestCase(1),TestCase(2)]
        public void T101_LoginTestSuite_Valid(int rowNum)
        {
            Console.WriteLine(TestContext.CurrentContext.Test.MethodName); //Test Name 
            Console.WriteLine("Row number "+rowNum);// Value of rowNum

            ExcelDataFactory.GetTestDataSet(TestContext.CurrentContext.Test.MethodName);

            //Print out the credentials
            Console.WriteLine(ExcelDataFactory.ReadData(rowNum,"username")); 
            Console.WriteLine(ExcelDataFactory.ReadData(rowNum, "password"));
        }
    }

Here is the excel这是 excel

Excel电子表格

The first test case gets username and password correctly.第一个测试用例正确获取用户名和密码。

测试1

However the second test case returns blank (If I run this individually it will work!)但是第二个测试用例返回空白(如果我单独运行它会起作用!)

测试2

Below is the ExcelDataFactory code:下面是ExcelDataFactory代码:

    class ExcelDataFactory
    {
        //Get data from excel
        private static DataTable ExcelToDataTable(String filename, String sheetName)
        {
            //Open file and returns as Stream
            FileStream stream = File.Open(filename, FileMode.Open, FileAccess.Read);

            //CreateOpenXmlReader via ExcelReaderFactory 
            IExcelDataReader excelReader = ExcelReaderFactory.CreateOpenXmlReader(stream); //.xlsx

            //Return as DataSet and set the frist row as column name
            DataSet result = excelReader.AsDataSet(new ExcelDataSetConfiguration()
            {
                ConfigureDataTable = (_) => new ExcelDataTableConfiguration()
                {
                    UseHeaderRow = true
                }
            });

            DataTableCollection table = result.Tables;


            DataTable resultTable = table[sheetName];

            //Close FileStream
            stream.Close();

            //Return
            return resultTable; 
        }

        //Put data into a collection 
        static List<DataCollection> dataCollection = new List<DataCollection>();

        public static void PopulateInCollection(string fileName, String sheetName)
        {
            DataTable table = ExcelToDataTable(fileName,sheetName);

            //Iterate through the rows and columns of the Table
            for(int row = 1; row <= table.Rows.Count; row++)
            {
                for (int column = 0; column < table.Columns.Count; column++)
                {
                    DataCollection dataTable = new DataCollection()
                    {
                        rowNumber = row,
                        columnName = table.Columns[column].ColumnName,
                        columnValue = table.Rows[row - 1][column].ToString()
                    };
                    //Add all the details for each row
                    dataCollection.Add(dataTable);
                }
            }
        }

        //Find the correct excel file and sheet
        public static void GetTestDataSet(String testName)
        {
            String[] testNameSplit = testName.Split('_');
            String filePath = MyProps.Default.TestData //Add path
                    + testNameSplit[1]
                    + "."
                    + "xlsx";
            PopulateInCollection(filePath, testNameSplit[0]);
        }

        public static string ReadData(int rowNumber, string columnName)
        {
            try 
            {
                //Retriving Data using LINQ to reduce amount of iterations
                string data = (from collectionData in dataCollection
                               where collectionData.columnName == columnName && collectionData.rowNumber == rowNumber
                               select collectionData.columnValue).SingleOrDefault();

                //var data   = dataCollection.Where(collectionData => collectionData.columnName == columnName && collectionData.rowNumber == rowNumber).SingleOrDefault().columnValue; 
                return data.ToString();
            } 
            catch (Exception e)
            {
                e.StackTrace.ToString();
                return null;
            }
        }

    }  

    class DataCollection
    {
        public int rowNumber { get; set; }

        public string columnName { get; set; }

        public string columnValue { get; set; }
    }

I suspect that the ExcelDataFactory.GetTestDataSet method is called in the wrong place, but I really am stumped as to why this is happening.我怀疑ExcelDataFactory.GetTestDataSet方法在错误的地方被调用,但我真的很难理解为什么会这样。 Any ideas would be greatly appreciated.任何想法将不胜感激。

I did some quick changes to ExcelDataFactory class, I removed the static references and now PopulateInCollection method returns a List that is declared and initialized at the start of the class.我对ExcelDataFactory class 做了一些快速更改,我删除了static引用,现在PopulateInCollection方法返回一个在 class 开始时声明和初始化的列表

using ExcelDataReader;
using NUnit.Framework;
using System;
using System.Collections.Generic;
using System.Data;
using System.IO;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace Wizuda_Selenium_Test_Automation
{
    class ExcelDataFactory
    {
        List<DataCollection> dataCollection = new List<DataCollection>();

        private static DataTable ExcelToDataTable(String filename, String sheetName)
        {
            //Open file and returns as Stream
            FileStream stream = File.Open(filename, FileMode.Open, FileAccess.Read);

            //CreateOpenXmlReader via ExcelReaderFactory 
            IExcelDataReader excelReader = ExcelReaderFactory.CreateOpenXmlReader(stream); //.xlsx

            //Return as DataSet and set the frist row as column name
            DataSet result = excelReader.AsDataSet(new ExcelDataSetConfiguration()
            {
                ConfigureDataTable = (_) => new ExcelDataTableConfiguration()
                {
                    UseHeaderRow = true
                }
            });

            DataTableCollection table = result.Tables;


            DataTable resultTable = table[sheetName];

            //Close FileStream
            stream.Close();

            //Return
            return resultTable; 
        }

        //static List<DataCollection> dataCollection = new List<DataCollection>();

        public List<DataCollection> PopulateInCollection(string fileName, String sheetName)
        {
            dataCollection = new List<DataCollection>();

            DataTable table = ExcelToDataTable(fileName,sheetName);

            //Iterate through the rows and columns of the Table
            for(int row = 1; row <= table.Rows.Count; row++)
            {
                for (int column = 0; column < table.Columns.Count; column++)
                {
                    DataCollection dataTable = new DataCollection()
                    {
                        rowNumber = row,
                        columnName = table.Columns[column].ColumnName,
                        columnValue = table.Rows[row - 1][column].ToString()
                    };

                    //Add all the details for each row
                    dataCollection.Add(dataTable);
                }
            }

            return dataCollection;
        }

        public string ReadData(int rowNumber, string columnName)
        {
            try 
            {
                //Retriving Data using LINQ to reduce amount of iterations
                string data = (from collectionData in dataCollection
                               where collectionData.columnName == columnName && collectionData.rowNumber == rowNumber
                               select collectionData.columnValue).SingleOrDefault();

                //var data   = dataCollection.Where(collectionData => collectionData.columnName == columnName && collectionData.rowNumber == rowNumber).SingleOrDefault().columnValue; 
                return data.ToString();
            } 
            catch (Exception e)
            {
                e.StackTrace.ToString();
                return null;
            }
        }

        public void GetTestDataSet(String testName)
        {
            String[] testNameSplit = testName.Split('_');
            String filePath = MyProps.Default.TestData //Add path
                    + testNameSplit[1] //LoginTestSuite
                    + "."
                    + "xlsx";              //T101
            PopulateInCollection(filePath, testNameSplit[0]);
        }
    }  

    class DataCollection
    {
        public int rowNumber { get; set; }

        public string columnName { get; set; }

        public string columnValue { get; set; }
    }
}

I updated the test to create new instance of ExcelDataFactory我更新了测试以创建ExcelDataFactory的新实例

        [Test,TestCase(1),TestCase(2)]
        public void T101_LoginTestSuite_Valid(int rowNum)
        {
            ExcelDataFactory excelDataFactory = new ExcelDataFactory();

            Console.WriteLine(TestContext.CurrentContext.Test.MethodName);
            Console.WriteLine("Row number "+rowNum);
            excelDataFactory.GetTestDataSet(TestContext.CurrentContext.Test.MethodName);

            Console.WriteLine("username= "+ excelDataFactory.ReadData(rowNum,"username"));
            Console.WriteLine("password= "+ excelDataFactory.ReadData(rowNum, "password"));
        }

And now the test passes现在测试通过了

测试1 测试2

I guess I need to go back and re-learn about the use static methods, thanks Kritner我想我需要返回 go 并重新学习使用 static 方法,谢谢Kritner

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM