在运行测试套件时动态创建机器人框架测试用例

问题描述 投票:0回答:2

我有一个非常具体的场景,我正在向数据库插入一些数据(例如,假设 3 次插入,每个插入都返回一些 ID),并且基于返回值,我想为这些返回值创建动态测试用例 例如

*** Variables ***
@{result}    ${EMPTY}

*** Test Cases ***
Some dummy sql inserts
    ${result}    Insert sql statements    dt1    dt2    dt3 #e.g. return ['123', '456', '789']

Verify some ids
    # NOPE, sorry i can't use [Template] because each iteration is not marked on a report as a "TEST" but as a "VAR"
    Verify if ids exist somewhere ${result} #This keyword execution should create another 3 test cases, one for each item from ${result} list

*** Keywords ***
Insert sql statement
    [Arguments]    @{data}
    Create List    ${result}
    FOR    ${elem}    IN    @{data}
        ${return_id}    SomeLib.Execute SQL    INSERT INTO some_table(some_id) VALUES (${elem})
        Append To List    ${result}    ${return_id}
    END
    [Return]    ${result}

Verify if ids exist somewhere
    [Arguments]    ${some_list_of_ids}
    FOR    ${id}    IN    @{some_list_of_ids}
        So some stuff on ${id}
    END

我试图通过参考机器人 API 文档来弄清楚如何做到这一点,但没有成功。 您能否告诉/建议这是否可行,如果可行,我该如何实现这一目标。
到目前为止,我发现可能有两种方法可以做到这一点:

  1. 通过创建监听器
  2. 通过创建自己的关键字

在这两种情况下,我都必须将逻辑放在那里,但无法弄清楚如何即时创建测试用例。
请帮助? :)

附注一些例子是非常受欢迎的。预先感谢

python robotframework
2个回答
2
投票

有一篇博文可以为您提供答案: https://gerg.dev/2018/09/dynamically-create-test-cases-with-robot-framework/

正如您所建议的,解决方案是创建一个侦听器,以便您可以动态添加测试。请仔细阅读这篇文章,因为存在一些限制,例如您何时可以和不能创建测试(在执行过程中)。 另外,这篇文章适用于 3.x 框架,对于 4.x,您需要在类中进行微小的更改,方法是替换: tc.keywords.create(name=kwname, args=args) 和: tc.body.create_keyword(name=kwname, args=args).

如何实施的示例:

演示机器人:

*** Settings ***
Library           DynamicTestCases.py

*** Test Cases ***
Create Dynamic Test Cases
    @{TestNamesList}    Create List    "Test 1"    "Test 2"    "Test 3"
    FOR    ${element}    IN    @{TestNamesList}
        Add Test Case    ${element}   Keyword To Execute
    END

*** Keywords ***
Keyword To Execute
    Log    This is executed for each test!

DynamicTestCases.py 内容(我发布的 url 的基本副本 + 更改的行):

from __future__ import print_function
from robot.running.model import TestSuite


class DynamicTestCases(object):
    ROBOT_LISTENER_API_VERSION = 3
    ROBOT_LIBRARY_SCOPE = 'TEST SUITE'

    def __init__(self):
        self.ROBOT_LIBRARY_LISTENER = self
        self.current_suite = None

    def _start_suite(self, suite, result):
        # save current suite so that we can modify it later
        self.current_suite = suite

    def add_test_case(self, name, kwname, *args):
        """Adds a test case to the current suite

        'name' is the test case name
        'kwname' is the keyword to call
        '*args' are the arguments to pass to the keyword

        Example:
            add_test_case  Example Test Case  
            ...  log  hello, world  WARN
        """
        tc = self.current_suite.tests.create(name=name)
        #tc.keywords.create(name=kwname, args=args) #deprecated in 4.0
        tc.body.create_keyword(name=kwname, args=args)

# To get our class to load, the module needs to have a class
# with the same name of a module. This makes that happen:
globals()[__name__] = DynamicTestCases

这是一个如何使其工作的小例子。 例如,如果您想为关键字赋予变量,只需添加参数:

*** Settings ***
Library           DynamicTestCases.py

*** Test Cases ***
Create Dynamic Test Cases
    @{TestNamesList}    Create List    "Test 1"    "Test 2"    "Test 3"
    FOR    ${element}    IN    @{TestNamesList}
        Add Test Case    ${element}   Keyword To Execute    ${element}
    END

*** Keywords ***
Keyword To Execute
    [Arguments]    ${variable}
    Log    The variable sent to the test was: ${variable}

0
投票

我不确定这是否应该是一个单独的答案,还是对现有已批准答案的编辑。我正在使用 Robot Framework 5.0,并且能够为不同的测试用例添加安装、拆卸和标签。以防万一其他用户出现并想知道如何操作:

*** Settings ***
Documentation   Test cases for dynamic test cases.

# Library files
Library     DynamicTestCases.py

*** Keywords ***
Keyword To Execute
    [Arguments]    ${variable}
    Log    The variable sent to the test was: ${variable}

Setup keyword
    ${variable}    Set Variable    This is from the setup keyword
    Log  ${variable}
    Log To Console  ${variable}

Teardown keyword
    ${variable}    Set Variable    This is from the teardown keyword
    Log  ${variable}
    Log To Console  ${variable}

*** Test Cases ***
Create Dynamic Test Cases
    @{TestNamesList}    Create List    "Test 1"    "Test 2"    "Test 3"
    FOR    ${element}    IN    @{TestNamesList}
        ${testCase} =  AddTestCase  ${element}  dynamic_tag_${element}
        AddKeywordToTestCase  ${testCase}  Keyword To Execute  ${element}
        AddSetupToTestCase  ${testCase}  Setup keyword
        AddTeardownToTestCase  ${testCase}  Teardown keyword
    END

还有 python 库,

DynamicTestCases.py
:

# While this import does not seem necessary, it was useful in the python console.
from robot.running.model import TestSuite, TestCase, Keyword


class DynamicTestCases(object):
    ROBOT_LISTENER_API_VERSION = 3
    ROBOT_LIBRARY_SCOPE = 'TEST SUITE'

    def __init__(self):
        self.ROBOT_LIBRARY_LISTENER = self
        self.currentSuite = None

    def _start_suite(self, suite, result):
        # Don't change the name of this method. 
        # save current suite so that we can modify it later
        self.currentSuite = suite

    def AddTestCase(self, name, tags):
        """
        Adds a test case to the current suite

        Args:
            - name: is the test case name
            - tags: is a list of tags to add to the test case

        Returns: The test case that was added
        """
        testCase = self.currentSuite.tests.create(name=name, tags=tags)
        return testCase

    def AddKeywordToTestCase(self, testCase, keywordName, *args):
        """
        Adds a keyword to the given test case.

        Args:
            - testCase: The test case to add the keyword to
            - keywordName: The name of the keyword to add
            - *args: The arguments to pass to the keyword
        """
        testCase.body.create_keyword(name=keywordName, args=args)

    def AddSetupToTestCase(self, testCase: TestCase, keywordName: str, *args):
        testCase.body.create_keyword(name=keywordName, args=args, type='setup')

    def AddTeardownToTestCase(self, testCase: TestCase, keywordName: str, *args):
        testCase.body.create_keyword(name=keywordName, args=args, type='teardown')
© www.soinside.com 2019 - 2024. All rights reserved.