ABAP Unit - Basics
This article covers the basics of implementing unit tests with ABAP. At this point we want to give you a brief overview.
The last article on ABAP Unit was about the general introduction to the topic of unit tests and how you can use them most effectively for yourself. So how is an ABAP unit test structured and how does it work in general with the execution, we want to bring this closer to you in this article.
In the following chapters we will repeatedly use abbreviations that refer to objects:
- CUT - Code under Test or Class under Test, is our object, that we want to test in the current unit test
- DOC - Dependent on Component describes a dependent component that can influence our test and that we actually don't want to test at all
- TDF - Test Double Framework provides tools to control dependent components
It takes very little effort and very few lines of code to create a test class. In our other examples, we will mainly bring you closer to working with Eclipse and how you can use it to implement the tests. In the first step we create a global class, as this is best suited for implementing test classes.
In the lower area of the window, you have several tabs, here you select the tab “Test Classes” and you are in the test include of the class, here you can implement your tests. For a template of a test class, you can use the pattern “testclass” from Eclipse and you will get the following result.
A test class looks like a normal class in the first comparison, but there are some differences. Let's first take a look at another example implementation:
CLASS ltc_basic_test DEFINITION FINAL FOR TESTING DURATION SHORT RISK LEVEL HARMLESS. PRIVATE SECTION. METHODS: my_first_unit_test FOR TESTING. ENDCLASS. CLASS ltc_basic_test IMPLEMENTATION. METHOD my_first_unit_test. ENDMETHOD. ENDCLASS.
The class is equipped with the addition FOR TESTING, which signals that it is a test class and that it cannot be instantiated directly. All test methods are also provided with this addition. A test class can therefore contain even more methods and data that can be used as an aid for executing the test cases.
The DURATION element in the class provides the ABAP Unit Runner with information on how long it will take to execute this test class. If the runtime is exceeded, a message is issued during execution and it should be checked again whether the test cases do not require a different classification. This restriction is also used to define what is to be started in global runs.
The adjustable options are:
- SHORT - Execution less than a minute
- MEDIUM - Execution between one and five minutes
- LONG - Execution longer than 5 minutes
The risk level determines the criticality of the unit tests for the system. Should the tests change data or lead to inconsistencies in the database, their risk level will be adjusted accordingly. It is possible to define the maximum number of tests that can be carried out in the current system using a system parameter. The setting also plays a role in global test runs.
The risk levels are:
- HARMLESS - No system settings or persistent data are affected by the tests
- CRITICAL - Persistent data is changed
- DANGEROUS - At least system settings are changed
The implementation of a test is not particularly difficult, for this only the instance of the global class has to be created in the method and the method to be tested must then be called from this. The result is compared against a method of the class CL_ABAP_UNIT_ASSERT. Here is a test method for the previously implemented class:
METHOD select_data_from_db. DATA(lo_cut) = NEW zcl_demo_test( ). DATA(ls_result) = lo_cut->select_some_data( ). cl_abap_unit_assert=>assert_not_initial( ls_result ). ENDMETHOD.
The comparison enables the final result to be set for the entire test and must be carried out in each method. Which of the methods you use is up to you and ultimately depends on the comparison and the data. Here is a brief overview of the methods that are available and relevant in the class:
In the most common cases, you will likely use the ASSERT_EQUALS method to compare the result directly.
The execution order of the test methods in a test class is not known in advance and this can vary. Test cases should therefore not be based on other test methods, but should always be considered separately. The ABAP unit tests are executed via the test runner, which creates an instance of the test class and calls the individual test methods.
Please note that there can be four other methods in a test class that are executed if they are available:
- CLASS_SETUP - Is called once before the test class is instantiated and can initialize static attributes
- SETUP - Called before a test method is called
- TEARDOWN - Called after a test method has been called
- CLASS_TEARDOWN - Called at the end of the test when all test methods have been processed
There is an execution plan for the test, which we want to show you again here:
At the end of the processing, a rollback work takes place so that all changes to the database can be undone. If a commit work occurred during processing, these changes are no longer undone because they have already been written to the database.
For this we have built the following test class that implements and calls the individual methods once. The entire output of the individual methods is logged in an internal table in the class.
CLASS ltc_basic_test DEFINITION FINAL FOR TESTING DURATION SHORT RISK LEVEL HARMLESS. PRIVATE SECTION. CLASS-DATA: gt_steps TYPE string_table. CLASS-METHODS: class_setup, class_teardown. METHODS: setup, teardown, method_number_one FOR TESTING, method_number_two FOR TESTING. ENDCLASS. CLASS ltc_basic_test IMPLEMENTATION. METHOD class_setup. INSERT `Class Setup` INTO TABLE gt_steps. ENDMETHOD. METHOD class_teardown. INSERT `Class Teardown` INTO TABLE gt_steps. BREAK-POINT. ENDMETHOD. METHOD method_number_one. INSERT `Test No. 1` INTO TABLE gt_steps. ENDMETHOD. METHOD method_number_two. INSERT `Test No. 2` INTO TABLE gt_steps. ENDMETHOD. METHOD setup. INSERT `Setup` INTO TABLE gt_steps. ENDMETHOD. METHOD teardown. INSERT `Teardown` INTO TABLE gt_steps. ENDMETHOD. ENDCLASS.
A breakpoint is also set in CLASS_TEARDOWN so that you can take a closer look at the content of the table. As you can see, the methods were called in the appropriate order.
The test class is executed via the actual main object and not via the test class itself. There are several ways to do this in Eclipse.
There is an option via the menu under “Run -> Run As -> ABAP Unit Test”.
Or in the action bar, directly via the run icon.
There is also an action in the context menu when you right-click on the object.
With today's basics you can write small unit tests and test your applications. But there is much more to testing, especially when it comes to tools and methods. But don't worry, you'll get this information in the next few articles.