Can I run Setup, Test and Teardown separately?

Hi All,

I have been reading through the API Documentation but can’t seem to figure out how to achieve what I’m wanting to do.

Basically what I’d like to do is

  1. load robot file
  2. run suite setup
  3. run test setup
  4. run test a
  5. run test a
  6. run test a
  7. run test teardown
  8. run test teardown

but regardless if I use robot.run or robot.run_cli I can only do

  1. load robot file, run suite setup, run test setup, run test a, run test teardown, run test teardown

So I’m hoping someone can point me in the right direction, am I missing something?

Dave.

You cannot do this directly. Each suite and test you run has whatever setup/teardown that was specified for them in the data. Good news is that you can pretty easily create a pre-run modifier to adjust setups and teardowns as needed.

Hi Pekka,

Thanks, can you elaborate how I would approach this? I’ve not seen mention of pre-run modifiers anywhere in the documentation (if you can point to it would be great as I often refer back to the doco).

Basically I want to run the Setup once then run the test in a while loop until the while condition is met (in my case end of test run) then run the Teardown.

I would be ok with the suite setup and suite teardown being once and the test setup and test teardown being with every test run.

Dave.

Pre-run modifiers are explained in the User Guide:
http://robotframework.org/robotframework/latest/RobotFrameworkUserGuide.html#programmatic-modification-of-test-data

For details about the model objects you are editing and the visitor interface, you need to study the API docs. Relevant sections ought to be linked from the User Guide

Hi Pekka,

Thanks, that was really helpful I’m getting the hang of it now.

Dave.

Great! You can use the same API to rename your tests so you don’t get that warning about duplicate tests. That said, I’m not certain is that a useful warning in general. If you don’t like it, please submit an issue and we can consider removing it or making it configurable.

I’m not so worried about the warning, when I get to it i’ll probably rename the tests with iteration nn (nn being the number).

Another question, end_test and end_suite seem to get called before the first test is actually run, is this how it’s supposed to work? the documentation says:

end_suite ( suite )[source]
Called when a suite ends. Default implementation does nothing.

end_test ( test )[source]
Called when a test ends. Default implementation does nothing.

but when I actually run:

% robot --prerunmodifier Repeat.py repeatme.robot
suite: Repeatme
suite.tests: [robot.running.TestCase(name='Repeat Me')]
suite.tests[0]: Repeat Me
test: Repeat Me
test.parent: Repeatme
test.parent.tests: [robot.running.TestCase(name='Repeat Me')]
end suite: Repeatme
==============================================================================
Repeatme                                                                      
==============================================================================

These were in my end_test

test: Repeat Me
test.parent: Repeatme
test.parent.tests: [robot.running.TestCase(name='Repeat Me')]

and this was in my end_suite

end suite: Repeatme

Docs seem to be a bit misleading. Visitor is executed for the whole model at once so that start methods are called before visiting possible children and end methods are called after that. Pre-run modifiers are run before test execution starts.

If you want to do something during execution, you need to use listeners. Listener API v3 operates with same model objects as modifiers so similar code works there as well. The major limitation of listener API v3 is that it doesn’t support start/end_keyword methods.

1 Like

Ok thanks,

I already have a V2 listener, do I need a V3 listener to access the API for adding tests to the test suite? Or can that be done in the V2 API as well? It doesn’t look like end_test has the test object or end_suite has the tests list object, so I guess I need V3 for this.

Also I know I can pass multiple listeners to the same test but mix a V2 and V3 listener on the same test, or do they all have to be the same version? I guess I’ll find out when I try it.

Dave.

I successfully ran the V2 and V3 listeners together, and got the trigger to add the test running from end_test which brings me to the next question.

From end_test I have the test object, and from the parent I can get the suite object, which has a metadata object. But how do I access the variables?

I pass some variables in on the command line, when I run the test again I would like to update one of these variables. I looked at the config object of the test but couldn’t see how to get the variables?

Dave.

I do not think you can do this directly.

You need to use v3 listeners for this. In the end_test method you ought to be able to use something like this to create a new test:

new = test.parent.tests.create(name='New test')
new.body.create_keyword(name='Log', args=['Example'])

Or something like this to copy an existing test:

copy = test.copy(name='New name')
test.parent.tests.append(copy)

Same stuff works also with modifiers. You are working with same model objects in both cases.

1 Like

Thanks Pekka, I’ll give it a try.

Dave.

I was revisiting this and decided to post a full working example incase it helps someone else.

BTW Thanks @pekkaklarck for all your help with this.

Run Command:

robot --listener TestRepeater.py repeatme.robot

TestRepeater.py

from robot.api import SuiteVisitor
import time

class TestRepeater(SuiteVisitor):
	ROBOT_LISTENER_API_VERSION = 3

	testname = None
	count = 1

	def end_test(self, test, result):
		# print("test:", test)
		# print("test.parent:", test.parent)
		# print("test.parent.tests:", test.parent.tests)

		if self.count < 5:
			self.count += 1
			if self.testname is None:
				self.testname = test.name
			newname = "{} {}".format(self.testname, self.count)
			copy = test.copy(name=newname)
			test.parent.tests.append(copy)
			# test.parent.tests.append(test)

	def end_suite(self, suite, result):
		# This prevents the error:
		# [ ERROR ] Calling method 'end_suite' of listener 'TestRepeater.py' failed: TypeError: end_suite() takes 2 positional arguments but 3 were given
		pass

	def start_suite(self, suite, result):
		# This prevents the error:
		# [ ERROR ] Calling method 'start_suite' of listener 'TestRepeater.py' failed: TypeError: start_suite() takes 2 positional arguments but 3 were given
		pass

	def start_test(self, test, result):
		# This prevents the error:
		# [ ERROR ] Calling method 'start_test' of listener 'TestRepeater.py' failed: TypeError: start_test() takes 2 positional arguments but 3 were given
		pass

repeatme.robot

*** Settings ***
Suite Setup			SS keyword
Suite Teardown		ST keyword
Test Setup 			TS keyword
Test Teardown 		TT keyword

*** Test Cases ***
Repeat Me
	${time} =	Get Time
	Log 	Repeat Me ${time}
	Log To Console 	Repeat Me ${time}
	Sleep 	5

*** Keywords ***

SS keyword
	Log 	Suite Setup
	Log To Console 	Suite Setup

TS keyword
	Log 	Test Setup
	Log To Console 	Test Setup

ST keyword
	Log 	Suite Teardown
	Log To Console 	Suite Teardown

TT keyword
	Log 	Test Teardown
	Log To Console 	Test Teardown

Result

==============================================================================
Repeatme                                                                      
==============================================================================
Suite Setup
Repeat Me                                                             Test Setup
...Repeat Me 2023-03-06 11:36:24
..Test Teardown
Repeat Me                                                             | PASS |
------------------------------------------------------------------------------
Repeat Me 2                                                           Test Setup
...Repeat Me 2023-03-06 11:36:29
..Test Teardown
Repeat Me 2                                                           | PASS |
------------------------------------------------------------------------------
Repeat Me 3                                                           Test Setup
...Repeat Me 2023-03-06 11:36:34
..Test Teardown
Repeat Me 3                                                           | PASS |
------------------------------------------------------------------------------
Repeat Me 4                                                           Test Setup
...Repeat Me 2023-03-06 11:36:39
..Test Teardown
Repeat Me 4                                                           | PASS |
------------------------------------------------------------------------------
Repeat Me 5                                                           Test Setup
...Repeat Me 2023-03-06 11:36:44
..Test Teardown
Repeat Me 5                                                           | PASS |
------------------------------------------------------------------------------
Suite Teardown
Repeatme                                                              | PASS |
5 tests, 5 passed, 0 failed
==============================================================================
Output:  /Users/dave/tmp/RepeatTest/output.xml
Log:     /Users/dave/tmp/RepeatTest/log.html
Report:  /Users/dave/tmp/RepeatTest/report.html
2 Likes