Current Situation in SAP Policy Management (FS-PM)
FS-PM is the SAP for Insurance module to handle the management of policies. It has a quite flexible and elaborate business object lying underneath with a lot of entities that connected to each other with different cardinalities. This flexibility can lead to an quite extensive i. e. large business object consisting of a lot of entities depending on how the insurance product is modeled. Everyone who wants to do an implementation of business logic in this module has to interact with this object tree using the so called Unified Business Object Interface (UBOI). This interface allows the fetching or updating of information stored in the business object. And exactly here comes the problem with FS-PM with respect to unit tests: If you want to do unit testing you have to introduce test doubles exactly for the UBOI as they are one of the central sources of the data your business logic depends on. Unfortunately the UBOI layer up to now "refused" to be mocked up with a reasonable effort due to several reasons (although a few brave developers tried to do so in the past). As a consequence the usual FS-PM developer was locked out from using unit-tests in FS-PM.
In order to make the story more complicated there is also one second important source of data within FS-PM the so called journal. This journal contains all the information about historical actions that took place on a policy. So at many places you also have to introduce a test double for this part of FS-PM, which proved to be as complicated as the mocking of the UBOI interface itself.
Up to now only bad news for developers who would like to benefit from a test-driven development approach in FS-PM. But with SP09 of Netweaver 7.40 the situation changes ...
The ABAP Test Double Framework
With SP09 SAP offers as a new out-of-the-box functionality in order to deal with the most annoying part of writing unit test namely the mocking up of dependent objects (like the UBOI interface in FS-PM). This functionality is called ABAP Test Double Framework which makes writing unit-tests easier or maybe, speaking for FS-PM, possible for the very first time. The blog ABAP Test Double Framework - An Introduction by Prajul Meyana gives a quite comprehensive introduction into the topic in general. Therefore I will not dive into the depth of the technical description of the framework, but throw a light on how this framework enables unit testing in FS-PM for the very first time without relying on FS-PM "infrastructure" to do so.
So dear FS-PM developer community fasten your seat belts as we will now ...
...tame the FS-PM beast
Although FS-PM up to now nearly completely denied the developer the option to do test driven development the infrastructure of FS-PM is very well prepared to allow the usage of the ABAP Test Double Framework without a lot of adoptions of the existing code or established patterns in the FS-PM code. The two big advantages are:
- the UBOI and also of the journal object in FS-PM is represented by classes with interfaces. So all the relevant methods for the fetching of information from the business object policy are located in these interfaces. This is a very good starting point as the ABAP Test Double Framework has some limitations but it can perfectly deal with the mocking of interfaces.
- a lot of classes already fetch the reference to the UBOI/journal object in the constructor of these classes and store the references as private instance attributes e. g. all timemodel functions or the classes of the cashflow component. This is very well fitting in order to allow the injection of the test double references into the classes under test.
So the central question is: What steps have to be done in order to enable the unit testing in FS-PM?
Let us a take a look at a concrete example: we want to write a class with one method that checks if all coverages underneath a specific contract have the same end date as the contract itself. If this is the case a flag is returned with the value ABAP_TRUE if not the flag has the value ABAP_FALSE. The importing parameter of the method is the UBOI key of the contract. As the goal of the blog is to show the feasibility of unit tests in FS-PM I will not do that in a test driven way (test first) but start with the regular coding as I want to show that even existing classes can now be covered with unit tests.
Step 1: Enable the Class for the Injection of the Test Double
As mentioned above we follow the FS-PM best practice and fetch the UBOI references in the constructor of the class using the corresponding factory call and store them in private instance attributes. We adopt the usual procedure in FS-PM as this time we allow in addition the importing of these references in case that the creator of the class wants to inject them. These parameters are marked as optional and if they are not bound the "classical" FS-PM style of fetching the references is used. The class definition looks like this:
The implementation part of the class with respect to the constructor is depicted in the following screenshot:
As mentioned before if the UBOI references are given to the constructor they are stored in instance attributes, if not the references are fetched using a factory call. When classes are created from scratch this procedure is straight forward. But even for existing classes the adjustment (i. e. adding optional parameters in the constructor of the class and enhancing the logic in the constructor with the IF...ELSE logic shown above) is not a cumbersome task that may result in severe problems for existing business logic.
Next we add the method that checks if the end dates of the coverages belonging to one contract are in sync or not. The definition of the method looks like this:
The implementation is shown in the following screenshot:
This is something like a typical piece of FS-PM code:
- You fetch the contract data into LT_POLPR using the fully qualified key so the table can contain only one entry (code in the red box)
- Then you fetch the coverages that are beneath the contract into LT_COV (code in the green box)
- After that you compare the end date of the coverages to the one of the contract (code in the blue box)
As you can also see there are real specifics in order to prepare the class for unit testing, all the coding is done "as usual" in FS-PM. Now let us see how easily this class can be unit tested although we are using the UBOI to fetch the data from the business object policy.
Step 2: Mock up the UBOI
We now create the test class. The definition of the test class contains one method TEST_FOR_SYNC that will test the method we have just created:
The implementation of the test method consists of three parts:
(1) We create the test double for the UBOI of the contract in order to provide a contract end date for the unit test:
This is done by calling the test double framework CL_ABAP_TESTDOUBLE=>CREATE and hand over the interface that shall be mocked. Be aware to cast the returned reference back to this interface. Next we fill the data that shall be stored in the test double. As you can see you do not have to specify all fields of the contract structure but only the relevant ones. After that we set the test data into the test double using the method CL_ABP_TESTDOUBLE=>CONFIGURE_CALL. Last but not least we specify the method (GET_POLPR) that has to be mocked. I did not specify any key for that call (LS_POLPR_KEY is initial). This is just for the sake of this demo, in real life unit testing you can of course transfer a key here and this key is afterwards considered when executing the unit test.
(2) We create the test double for the UBOI of the coverage as we did it for the UBOI of the contract
(3) Implement the test i. e. create an instance of the class under test and inject the created test doubles into the constructor of the class. After that call the method and check the result using the standard ABAP unit test framework.
For the parameters that we chose the expected result of the method call is ABAP_FALSE, which is what we assert.
Step 3: You are done :-)
That is it - you can now run the ABAP unit test or to be more precise you can now run a unit test in FS-PM on a class that uses the UBOI interface ... be aware that that nearly impossible up to now.
Within this blog I presented you the application of the ABAP Test Double Framework delivered with SP09 of the SAP Netweaver in the insurance module FS-PM. I did this because since the birth of this module it was nearly impossible to do unit testing in FS-PM. This is now definitly a story of the past. No matter if it is standard or customer development the technical foundation is now given for unit tests and in consequence for test-driven development in FS-PM.
So enjoy unit testing and test driven development ... even in modules where boldly no unit test has gone before
P.S. Be aware of the fact that the central class CL_ABAP_TESTDOUBLE exists already in 7.40 SPs prior to SP09 but it is not released in them. So when you use the class this will result in an error.
P.P.S. If you want to get an overview on test driven development and its benefits AND a little glimpse into the future developments of that topic with respect to SAP Netweaver the slides of Christian Drumm and Thomas Fiedler that you find here might be worth a look.