Technology Blog Posts by Members
cancel
Showing results for 
Search instead for 
Did you mean: 
sharathtm
Explorer
0 Likes
129

Introduction:


Modern SAP applications often need to execute time-consuming operations such as external service calls, heavy calculations, or mass data creation. Running such logic sequentially can slow down user interaction and block dialog processes. ABAP Cloud offers a clean and powerful way to distribute workload using parallel processing via the class CL_ABAP_PARALLEL.

In this blog, we will see:

  1. What a parallel class is in ABAP Cloud
  2. How to implement IF_ABAP_PARALLEL
  3. How to execute RAP EML inside a parallel task
  4. How to commit inside the task and return results

What is parallel class?


A parallel class is a normal ABAP class that implements the interface IF_ABAP_PARALLEL.
This interface provides the method: IF_ABAP_PARALLEL-DO

which represents the logic that will run in a separate work process. Each instance of this class becomes an independent task executed by the framework.

The advantages are:

  • Multiple tasks run concurrently
  • Main session is not blocked
  • Each task has its own transactional context
  • You can perform COMMIT inside the task

Business scenario:

  • Billing Document Header, which represents the main business document
  • Billing Document Item, which contains detailed line-level data including materials
  • Task BO (a separate RAP Business Object with managed implementation) used to store task-related information.

Requirement:

  • Read the billing document item data from the system using RAP EML
  • Fetch the corresponding Material ID from each billing item for further processing
  • Create a Task record using RAP EML based on the extracted Material
  • Perform the commit operation inside the parallel task to ensure independent transaction handling
  • Retrieve the generated Task UUID from the managed Task BO after successful creation
  • Update the billing item description field with the returned UUID to reflect the processing result
  • Ensure all these steps are executed efficiently using parallel processing for better performance and scalability.

Implementing Steps:

Step 1: Create parallel task class
This class:

  • Receives Material ID in constructor
  • Implements IF_ABAP_PARALLEL
  • Creates Task using EML
  • Performs COMMIT ENTITIES inside the task
  • Returns the created UUID
CLASS zsrt_cl_parallel_task DEFINITION
PUBLIC
FINAL
CREATE PUBLIC .

PUBLIC SECTION.
INTERFACES if_serializable_object . " Required for parallel execution
INTERFACES if_abap_parallel . " Enables parallel processing logic

METHODS :
constructor IMPORTING iv_material TYPE string, " Receive input material
get_result RETURNING VALUE(rt_result) TYPE string. " Return generated UUID

PRIVATE SECTION.
DATA: mv_material TYPE string. " Stores material passed to task
DATA mv_result TYPE string. " Stores generated Task UUID

ENDCLASS.



CLASS zsrt_cl_parallel_task IMPLEMENTATION.

METHOD constructor.
mv_material = iv_material. " Initialize material for this task instance
ENDMETHOD.

METHOD get_result.
RETURN mv_result. " Return UUID result to caller
ENDMETHOD.


METHOD if_abap_parallel~do.

DATA:
lt_task_create TYPE TABLE FOR CREATE zsrt_i_task_head, " Input structure for CREATE
ls_task_create LIKE LINE OF lt_task_create,
lt_reported TYPE RESPONSE FOR REPORTED EARLY zsrt_i_task_head,
lt_mapped TYPE RESPONSE FOR MAPPED EARLY zsrt_i_task_head, " Holds generated values (UUID)
lt_failed TYPE RESPONSE FOR FAILED EARLY zsrt_i_task_head. " Holds failed entries

" Prepare Task data using material
lt_task_create = VALUE #(
(
%cid = 'MY_CID_1' " Correlation ID
taskid = |TASK-{ mv_material }| " Dynamic Task ID
title = |New task for { mv_material }| " Task title
description = 'Test Description'
overallstatus = 'O'
%control = VALUE #( " Mark fields for update
taskid = if_abap_behv=>mk-on
title = if_abap_behv=>mk-on
description = if_abap_behv=>mk-on
overallstatus = if_abap_behv=>mk-on )
)
).

" Create Task record using RAP EML
MODIFY ENTITIES OF zsrt_i_task_head
ENTITY zsrt_i_task_head
CREATE FROM lt_task_create
MAPPED lt_mapped " Contains generated UUID
FAILED lt_failed
REPORTED lt_reported.

" Process only if creation is successful
IF lt_failed IS INITIAL.

COMMIT ENTITIES. " Commit inside parallel task (separate LUW)

" Read generated UUID from mapped structure
READ TABLE lt_mapped-zsrt_i_task_head INTO DATA(ls_map) INDEX 1.

IF sy-subrc = 0.
mv_result = ls_map-taskuuid. " Store UUID for returning
ENDIF.

ENDIF.

ENDMETHOD.

ENDCLASS.


Key Points:

  • EML is executed inside the parallel session
  • COMMIT ENTITIES is allowed here
  • Result is stored in instance attribute
  • get_result method exposes the value

Step 2: Calling the Parallel Class
To keep the example simple, we call it from a local class implementing IF_OO_ADT_CLASSRUN.

Execution Flow

  • Read billing item using EML
  • Extract Material ID
  • Create instance of parallel task
  • Run using CL_ABAP_PARALLEL
  • Collect result
  • Update billing item description
CLASS zsrt_cl_process DEFINITION
  PUBLIC
  FINAL
  CREATE PUBLIC .

  PUBLIC SECTION.
    INTERFACES if_oo_adt_classrun.   " Entry point for execution in ADT

ENDCLASS.



CLASS zsrt_cl_process IMPLEMENTATION.

  METHOD if_oo_adt_classrun~main.

    DATA: 
      lt_processes TYPE cl_abap_parallel=>t_in_inst_tab,  " Holds parallel task instances
      lt_results   TYPE STANDARD TABLE OF sysuuid_x16.    " Stores returned UUID results

    " Read all Billing Items from DB table
    SELECT *
      FROM zsrt_bill_item
      INTO TABLE @DATA(lt_items).


    " Create one parallel task instance per item
    LOOP AT lt_items INTO DATA(ls_item).

      INSERT NEW zsrt_cl_parallel_task(
        CONV #( ls_item-materialid )   " Pass material to parallel class
      ) INTO TABLE lt_processes.

    ENDLOOP.


    " Execute all tasks in parallel (max 5 at a time)
    NEW cl_abap_parallel( p_num_tasks = 5 )->run_inst(
      EXPORTING
        p_in_tab  = lt_processes       " Input: task instances
      IMPORTING
        p_out_tab = DATA(lt_finished)  " Output: completed instances
    ).


    " Collect UUID results from each parallel execution
    LOOP AT lt_finished INTO DATA(ls_finished).

      DATA(lv_uuid) =
        CAST zsrt_cl_parallel_task(
          ls_finished-inst )->get_result( ).  " Get UUID from each task

      APPEND lv_uuid TO lt_results.

    ENDLOOP.


    DATA idx TYPE sy-tabix.
    idx = 0.


    " Update billing items with respective UUIDs
    LOOP AT lt_items INTO ls_item.

      idx = idx + 1.

      READ TABLE lt_results INTO DATA(lv_uuid2) INDEX idx.

      IF sy-subrc = 0.

        MODIFY ENTITIES OF zsrt_i_bill_head
          ENTITY zsrt_i_bill_item
          UPDATE FROM VALUE #(
            ( billid               = ls_item-billid       " Key field
              itemno               = ls_item-itemno       " Key field
              description          = lv_uuid2             " Store UUID
              %control-description = if_abap_behv=>mk-on  " Enable update
            )
          ).

      ENDIF.

    ENDLOOP.


    " Save all updates to database
    COMMIT ENTITIES.

  ENDMETHOD.

ENDCLASS.

 

Result:

sharathtm_0-1780569186267.png

sharathtm_1-1780569239404.png


Conclusion:
Parallel processing in ABAP Cloud enables faster and efficient handling of large data by executing tasks simultaneously. Using CL_ABAP_PARALLEL with RAP EML, we can process multiple records independently and improve performance. This approach ensures better scalability and optimal use of system resources for real-time business scenarios.