Поделиться через


Управляемый данными класс

Прежде чем переходить к этому разделу, убедитесь, что вы знакомы с базовым выполнением TAEF и знаете, как создавать тесты с его помощью. Вы также можете ознакомиться с примером простого теста на основе данных. В этом разделе описано, как создать управляемый данными тест на основе таблиц , но тот же подход применяется к тестам на основе данных на основе WMI или PICT .

Когда следует использовать управляемый данными класс?

Бывают случаи, когда несколько тестов могут зависеть от одних и того же входных данных. При тестировании API может потребоваться выполнить несколько тестов API с одинаковыми данными, чтобы получить согласованное представление о поведении API. При выполнении тестов на уровне сценария может потребоваться убедиться, что все шаги в сценарии тестируются с одинаковыми данными. В это время полезно указать тестовые данные на уровне класса.

Создание управляемого данными класса

Вы указываете, что данный класс управляется данными аналогично тому, как вы указываете, что данный тест управляется данными. Метаданные DataSource применяются на уровне класса. Значение определяет конкретный интересующий источник данных. В следующем примере показано, как указать эти свойства для управляемых данными классов:

Машинный код

1     class 2     {
2         BEGIN_TEST_CLASS(DataDrivenClassExample)
3             TEST_CLASS_PROPERTY(L"DataSource", L"Table:DataDrivenClassExample.xml#ClassTable")
4         END_TEST_CLASS()
5
6         TEST_METHOD(Test1);
7       {
8         int size;
9           if (SUCCEEDED(<span class="style2">TestData::TryGetValue(L"size", size)</span>))
10          {
11              VERIFY_ARE_NOT_EQUAL(size, 0);
12              Log::Comment(String().Format(L"Size retrieved was %d", size));
13          }
14  
15          String color;
16          if (SUCCEEDED(<span class="style2">TestData::TryGetValue(L"color", color)</span>))
17          {
18              Log::Comment(L"Color retrieved was " + color);
19          }
20      }
21         TEST_METHOD(Test2);
22      {
23          int size;
24          if (SUCCEEDED(<span class="style2">TestData::TryGetValue(L"size", size)</span>))
25          {
26              VERIFY_ARE_NOT_EQUAL(size, 0);
27              Log::Comment(String().Format(L"Size retrieved was %d", size));
28          }
29  
30          String color;
31          if (SUCCEEDED(<span class="style2">TestData::TryGetValue(L"color", color)</span>))
32          {
33              Log::Comment(L"Color retrieved was " + color);
34          }
35      } 
36    };

Управляемый код

1     [TestClass]
2     public class CSharpDataDrivenClassExample
3     {
4         [ClassInitialize]
5         [DataSource("Table:CSharpDataDrivenClassExample.xml#ClassTable")]
6         public static void MyClassInitialize(Object testContext)
7         {
8         }
9
10        [TestMethod]
11        public void Test1()
12        {
13            int size = (int)m_testContext.DataRow["Size"];
14            Verify.AreNotEqual(size, 0);
15            Log.Comment("Size is " + size.ToString());
16
18            Log.Comment("Color is " + m_testContext.DataRow["Color"]);
19        }
20
21        [TestMethod]
22        public void Test2()
23        {
24            int size = (int)m_testContext.DataRow["Size"];
25            Verify.AreNotEqual(size, 0);
26            Log.Comment("Size is " + size.ToString());
27
28            Log.Comment("Color is " + m_testContext.DataRow["Color"]);
29        }
30
31        public TestContext TestContext
32        {
33            get { return m_testContext; }
34            set { m_testContext = value; }
35        }
36
37        private TestContext m_testContext;
38    }

В этих примерах строка 3 в примере машинного кода и строка 5 в примере управляемого кода являются рекомендуемыми способами указания источника данных для управляемого данными тестового класса в TAEF.

В приведенном выше примере управляемого кода строки 13, 18, 24 и 28 показывают, как данные предоставляются методам тестирования для управляемого кода.

В следующем примере кода строки 4, 11, 20 и 27 показывают, как данные предоставляются методам тестирования для машинного кода. Обратите внимание, что вы делаете данные, определенные в таблице управляемого данными класса (строки), доступными для методов теста в классе (Test1 и Test2), точно так же, как и для теста, управляемого данными.

Xml-файл DataSource для управляемого данными класса создается точно так же, как и для теста на основе данных. В следующих примерах показаны XML-файлы для собственных и управляемых классов.

Родной

1 <?xml version="1.0"?>
2 <Data>
3   <Table Id="ClassTable">
4     <ParameterTypes>
5       <ParameterType Name="Size">int</ParameterType>
6     </ParameterTypes>
7     <Row>
8       <Parameter Name="Size">4</Parameter>
9       <Parameter Name="Color">White</Parameter>
10    </Row>
11    <Row>
12      <Parameter Name="Size">10</Parameter>
13      <Parameter Name="Color">Black</Parameter>
14    </Row>
15    <Row>
16      <Parameter Name="Size">9</Parameter>
17      <Parameter Name="Color">Orange</Parameter>
18    </Row>
19    <Row>
20      <Parameter Name="Size">9</Parameter>
21      <Parameter Name="Color">Blue</Parameter>
22    </Row>
23  </Table>
24</Data>

Управляемых

1 <?xml version="1.0"?>
2 <Data>
3   <Table Id="ClassTable">
4     <ParameterTypes>
5       <ParameterType Name="Size">Int32</ParameterType>
6       <ParameterType Name="Color">String</ParameterType>
7     </ParameterTypes>
8     <Row>
9      <Parameter Name="Size">4</Parameter>
10      <Parameter Name="Color">White</Parameter>
11    </Row>
12    <Row>
13      <Parameter Name="Size">10</Parameter>
14      <Parameter Name="Color">Black</Parameter>
15    </Row>
16    <Row>
17      <Parameter Name="Size">9</Parameter>
18      <Parameter Name="Color">Orange</Parameter>
19    </Row>
20    <Row>
21      <Parameter Name="Size">9</Parameter>
22      <Parameter Name="Color">Blue</Parameter>
23    </Row>
24  </Table>
25</Data>

За кулисами ИЛИ чего ожидать?

По умолчанию при создании тестов в TAEF порядок выполнения в классе совпадает с порядком, в котором вы закодировали методы теста в классе . Таким образом, в предыдущих примерах Test1 всегда будет выполняться перед Test2. Поскольку класс, содержащий Test1 и Test2 , является управляемым данными классом, все методы класса будут выполняться один раз для каждой строки данных, определенной в DataSource. Другими словами, test1 и Test2 выполняются для строки 0. Затем эти методы выполняются в том же порядке для строки 1 и т. д., пока TAEF не выполнит все строки.

Выполнение тестов в классе, управляемом данными

При выполнении примера тестовых двоичных файлов с параметром команды /list порядок выполнения из предыдущего раздела становится ясным.

Родной

TE.exe Examples\CPP.AdvancedDataDriven.Examples.dll /name:*class* /list
Test Authoring and Execution Framework v2.9.3k for x86

        F:\ Examples\CPP.AdvancedDataDriven.Examples.dll
            WEX::TestExecution::Examples::DataDrivenClassExample#0
                WEX::TestExecution::Examples::DataDrivenClassExample#0::Test1
                WEX::TestExecution::Examples::DataDrivenClassExample#0::Test2
            WEX::TestExecution::Examples::DataDrivenClassExample#1
                WEX::TestExecution::Examples::DataDrivenClassExample#1::Test1
                WEX::TestExecution::Examples::DataDrivenClassExample#1::Test2
            WEX::TestExecution::Examples::DataDrivenClassExample#2
                WEX::TestExecution::Examples::DataDrivenClassExample#2::Test1
                WEX::TestExecution::Examples::DataDrivenClassExample#2::Test2
            WEX::TestExecution::Examples::DataDrivenClassExample#3
                WEX::TestExecution::Examples::DataDrivenClassExample#3::Test1
                WEX::TestExecution::Examples::DataDrivenClassExample#3::Test2

Управляемых

TE.exe Examples\CSharp.AdvancedDataDriven.Examples.dll /name:*class* /list
Test Authoring and Execution Framework v2.9.3k for x86

        F:\ Examples\CSharp.AdvancedDataDriven.Examples.dll
            WEX.Examples.CSharpDataDrivenClassExample#0
                WEX.Examples.CSharpDataDrivenClassExample#0.Test1
                WEX.Examples.CSharpDataDrivenClassExample#0.Test2
            WEX.Examples.CSharpDataDrivenClassExample#1
                WEX.Examples.CSharpDataDrivenClassExample#1.Test1
                WEX.Examples.CSharpDataDrivenClassExample#1.Test2
            WEX.Examples.CSharpDataDrivenClassExample#2
                WEX.Examples.CSharpDataDrivenClassExample#2.Test1
                WEX.Examples.CSharpDataDrivenClassExample#2.Test2
            WEX.Examples.CSharpDataDrivenClassExample#3
                WEX.Examples.CSharpDataDrivenClassExample#3.Test1
                WEX.Examples.CSharpDataDrivenClassExample#3.Test2

Обратите внимание, что индексы в приведенных выше примерах похожи на тесты на основе данных. Каждая строка в управляемом данными классе определяется индексом. Как и в тестах на основе данных, можно присвоить любой строке более понятное короткое имя , указав метаданные на уровне строки в XML-файле и распечатав это имя вместо индекса при перечислении или выполнении тестов.

Аналогичным образом используйте параметр /listproperties , чтобы убедиться, что данные действительно указаны и доступны на уровне класса.

Родной

F:\ Examples\CPP.AdvancedDataDriven.Examples.dll
    WEX::TestExecution::Examples::DataDrivenClassExample#0
            Property[DataSource] =  Table:DataDrivenClassExample.xml#ClassTable

            Data[Color] = White
            Data[Size] = 4
        WEX::TestExecution::Examples::DataDrivenClassExample#0::Test1
        WEX::TestExecution::Examples::DataDrivenClassExample#0::Test2

    WEX::TestExecution::Examples::DataDrivenClassExample#1
            Property[DataSource] =  Table:DataDrivenClassExample.xml#ClassTable

            Data[Color] = Black
            Data[Size] = 10
        WEX::TestExecution::Examples::DataDrivenClassExample#1::Test1
        WEX::TestExecution::Examples::DataDrivenClassExample#1::Test2

    WEX::TestExecution::Examples::DataDrivenClassExample#2
            Property[DataSource] =  Table:DataDrivenClassExample.xml#ClassTable

            Data[Color] = Orange
            Data[Size] = 9
        WEX::TestExecution::Examples::DataDrivenClassExample#2::Test1
        WEX::TestExecution::Examples::DataDrivenClassExample#2::Test2

    WEX::TestExecution::Examples::DataDrivenClassExample#3
            Property[DataSource] =  Table:DataDrivenClassExample.xml#ClassTable

            Data[Color] = Blue
            Data[Size] = 9
        WEX::TestExecution::Examples::DataDrivenClassExample#3::Test1
        WEX::TestExecution::Examples::DataDrivenClassExample#3::Test2

Управляемых

F:\ Examples\CSharp.AdvancedDataDriven.Examples.dll
    WEX.Examples.CSharpDataDrivenClassExample#0
            Setup: MyClassInitialize
            Property[DataSource] =  Table:CSharpDataDrivenClassExample.xml#ClassTable

            Data[Color] = White
            Data[Size] = 4
        WEX.Examples.CSharpDataDrivenClassExample#0.Test1
        WEX.Examples.CSharpDataDrivenClassExample#0.Test2

    WEX.Examples.CSharpDataDrivenClassExample#1
            Setup: MyClassInitialize
            Property[DataSource] =  Table:CSharpDataDrivenClassExample.xml#ClassTable

            Data[Color] = Black
            Data[Size] = 10
        WEX.Examples.CSharpDataDrivenClassExample#1.Test1
        WEX.Examples.CSharpDataDrivenClassExample#1.Test2

    WEX.Examples.CSharpDataDrivenClassExample#2
            Setup: MyClassInitialize
            Property[DataSource] =  Table:CSharpDataDrivenClassExample.xml#ClassTable

            Data[Color] = Orange
            Data[Size] = 9
        WEX.Examples.CSharpDataDrivenClassExample#2.Test1
        WEX.Examples.CSharpDataDrivenClassExample#2.Test2

    WEX.Examples.CSharpDataDrivenClassExample#3
            Setup: MyClassInitialize
            Property[DataSource] =  Table:CSharpDataDrivenClassExample.xml#ClassTable

            Data[Color] = Blue
            Data[Size] = 9
        WEX.Examples.CSharpDataDrivenClassExample#3.Test1
        WEX.Examples.CSharpDataDrivenClassExample#3.Test2

К управляемому данным классу можно применить все правила выполнения. Запрос на выбор можно создать на основе всего, что можно перечислить в параметре /listproperties .

Управляемые данными тесты в классе, управляемом данными

Вы ни в коем случае не ограничены наличием управляемых данными тестов в классе, управляемом данными. Этот подход может быть полезен при написании тестов API. Общие данные для всех тестов в классе можно хранить на уровне класса DataSource. Вы указываете данные, относящиеся к методу теста, в метаданных DataSource для метода, который помечается как управляемый данными.

ПРИМЕЧАНИЕ. В таких случаях порядок выполнения немного больше задействован.

В следующих примерах показано, как два предыдущих примера двоичных файлов отображаются с помощью параметра команды /list .

Родной

TE.exe Examples\CPP.AdvancedDataDriven.Examples.dll /name:*nested* /list
Test Authoring and Execution Framework v2.9.3k for x86

        F:\ Examples\CPP.AdvancedDataDriven.Examples.dll
            WEX::TestExecution::Examples::NestedDataDrivenExample#0
                WEX::TestExecution::Examples::NestedDataDrivenExample#0::Test1
                WEX::TestExecution::Examples::NestedDataDrivenExample#0::Test2#0
                WEX::TestExecution::Examples::NestedDataDrivenExample#0::Test2#1
                WEX::TestExecution::Examples::NestedDataDrivenExample#0::Test2#2
                WEX::TestExecution::Examples::NestedDataDrivenExample#0::Test2#3
            WEX::TestExecution::Examples::NestedDataDrivenExample#1
                WEX::TestExecution::Examples::NestedDataDrivenExample#1::Test1
                WEX::TestExecution::Examples::NestedDataDrivenExample#1::Test2#0
                WEX::TestExecution::Examples::NestedDataDrivenExample#1::Test2#1
                WEX::TestExecution::Examples::NestedDataDrivenExample#1::Test2#2
                WEX::TestExecution::Examples::NestedDataDrivenExample#1::Test2#3
            WEX::TestExecution::Examples::NestedDataDrivenExample#2
                WEX::TestExecution::Examples::NestedDataDrivenExample#2::Test1
                WEX::TestExecution::Examples::NestedDataDrivenExample#2::Test2#0
                WEX::TestExecution::Examples::NestedDataDrivenExample#2::Test2#1
                WEX::TestExecution::Examples::NestedDataDrivenExample#2::Test2#2
                WEX::TestExecution::Examples::NestedDataDrivenExample#2::Test2#3
            WEX::TestExecution::Examples::NestedDataDrivenExample#3
                WEX::TestExecution::Examples::NestedDataDrivenExample#3::Test1
                WEX::TestExecution::Examples::NestedDataDrivenExample#3::Test2#0
                WEX::TestExecution::Examples::NestedDataDrivenExample#3::Test2#1
                WEX::TestExecution::Examples::NestedDataDrivenExample#3::Test2#2
                WEX::TestExecution::Examples::NestedDataDrivenExample#3::Test2#3

Управляемых

TE.exe Examples\CSharp.AdvancedDataDriven.Examples.dll /name:*nested* /list
Test Authoring and Execution Framework v2.9.3k for x86

        F:\ Examples\CSharp.AdvancedDataDriven.Examples.dll
            WEX.Examples.CSharpDataDrivenNestedExample#0
                WEX.Examples.CSharpDataDrivenNestedExample#0.Test1
                WEX.Examples.CSharpDataDrivenNestedExample#0.Test2#0
                WEX.Examples.CSharpDataDrivenNestedExample#0.Test2#1
                WEX.Examples.CSharpDataDrivenNestedExample#0.Test2#2
                WEX.Examples.CSharpDataDrivenNestedExample#0.Test2#3
            WEX.Examples.CSharpDataDrivenNestedExample#1
                WEX.Examples.CSharpDataDrivenNestedExample#1.Test1
                WEX.Examples.CSharpDataDrivenNestedExample#1.Test2#0
                WEX.Examples.CSharpDataDrivenNestedExample#1.Test2#1
                WEX.Examples.CSharpDataDrivenNestedExample#1.Test2#2
                WEX.Examples.CSharpDataDrivenNestedExample#1.Test2#3
            WEX.Examples.CSharpDataDrivenNestedExample#2
                WEX.Examples.CSharpDataDrivenNestedExample#2.Test1
                WEX.Examples.CSharpDataDrivenNestedExample#2.Test2#0
                WEX.Examples.CSharpDataDrivenNestedExample#2.Test2#1
                WEX.Examples.CSharpDataDrivenNestedExample#2.Test2#2
                WEX.Examples.CSharpDataDrivenNestedExample#2.Test2#3
            WEX.Examples.CSharpDataDrivenNestedExample#3
                WEX.Examples.CSharpDataDrivenNestedExample#3.Test1
                WEX.Examples.CSharpDataDrivenNestedExample#3.Test2#0
                WEX.Examples.CSharpDataDrivenNestedExample#3.Test2#1
                WEX.Examples.CSharpDataDrivenNestedExample#3.Test2#2
                WEX.Examples.CSharpDataDrivenNestedExample#3.Test2#3

ПРИМЕЧАНИЕ: Единственное ограничение в этом случае заключается в том, что таблицы для двух примеров не могут находиться в одном файле DataSource. Иными словами, dataSource для управляемого данными класса и метод теста на основе данных, который он содержит, должны отличаться.

Обратите внимание, что метод Test2 в наших примерах является управляемым данными тестом в классе, управляемом данными. Например, в строке WEX. Examples.CSharpDataDrivenNestedExample#3.Test2#0, #3 — индекс класса, а #0 — индекс для управляемого данными теста в этом классе. Test2 может получить доступ к обеим таблицам: к данным в строке экземпляра класса, которому он принадлежит, и к данным в текущей строке для собственной таблицы DataSource . Иными словами, данные на уровне класса и данные на уровне метода теста объединяются и доступны во время выполнения метода теста.

Что происходит в случае конфликта данных, если одно и то же имя данных указано как на уровне класса, так и на уровне метода? TAEF обрабатывает это условие так же, как и свойства метаданных. Данные, указанные в строке на уровне метода, переопределяют данные, указанные в строке на уровне класса.

Например, рассмотрим случай, когда у вас есть параметр Size , который указан как на уровне класса, так и на уровне метода теста. На уровне класса Size определяется как тип массива строк , но на уровне метода теста он определяется как int. В этом случае тип int переопределяет тип String Array на уровне метода теста, а также в методах Setup и Teardown для теста. Однако в методах Setup и Teardown на уровне класса размер имеет тип данных Массив строк .

Если в коде есть такие конфликтующие данные, TAEF отображает предупреждение во время выполнения и перечисляет свойства, но конфликтующие данные не приведут к сбою.