Skip to Content
Technical Articles
Author's profile photo Rajendra Prabhu

SAP SuccessFactors EC-ECP Employee Data Replications – Part VI

Continuing on from Part V, in this blog post let’s discuss one specific limitation with the existing SAP config set-up, and how to circumvent that. May be in the future, SAP fixes it in the standard code, and you don’t have to follow this solution.

In Part III we mentioned about Config ID in table T77SFEC_PTP_CONF, and it’s nomenclature: <Company Code>_<Payroll Area>. You would assume that: (a) it would be one of the key fields on all other mapping tables so that you have subsequent configurations tied to it; (b) it shall be available as an import parameter in the BADI methods; (c) it shall be available on SLG1 logs for better tracking of replication statuses. However, none of these are in-place at the moment, and thus, a concern when you have a multi-tenant environment where-in there could be config deviations for each company in the landscape. To address this, we would implement some implicit enhancements. But first, re-sharing the overall process flow from Part I for easy reference.

PTP%20Process%20Flow%20Diagram

PTP Process Flow Diagram

 

Using implicit enhancements at appropriate locations in the code, we shall EXPORT TO MEMORY the Config ID being referred by the standard replication framework. We shall then IMPORT FROM MEMORY in our BADI implementations.

  1. In Class CL_HRSFEC_PTP_EE_REPLICATION, Method: CONSTRUCTOR. This method is executed during the main replication program execution before individual processing threads are generated. Implement implicit enhancement spot at the end of the method. Leverage a static method of your custom class ZCL_HRSFEC_CE_ITMAP_HELPER to export to memory the Config ID available in mv_sfapi_config_id. We shall later on use this information to capture Config ID in the SLG1 log.
    *$*$-Start: (1)---------------------------------------------------------------------------------$*$*
    ENHANCEMENT 1  ZENH_HRSFEC_PTP_EE_REPLICATION.    "active version
    " Store the Config ID in Memory. This shall be read in the BADIs and other custom codes.
    " This memory id shall be read in CONSTRUCTOR of Class ZCL_HRSFEC_CE_ITMAP_HELPER.
    
      ZCL_HRSFEC_CE_ITMAP_HELPER=>STORE_CONFIG_IN_MEMORY( mv_sfapi_config_id ).
    
    ENDENHANCEMENT.
    *$*$-End:   (1)---------------------------------------------------------------------------------$*$*​

    Sample code in the static method: ZCL_HRSFEC_CE_ITMAP_HELPER=>STORE_CONFIG_IN_MEMORY:

        " Store the Config ID in Memory. This shall be read in the BADIs and other custom codes.
        " This value shall be useful in determining the Company code, as each config id has first 4 digits
        " for Company Code. This way, we dont have to redetermine an employee's company code for 
        " each BADI implementation.
    
        EXPORT p1  = iv_config_id
          TO MEMORY ID mc_memid_ptp_configid. "MEM ID: 'ZHRSFEC_CE_CONFIG'
    ​

     

  2. In Class CL_HRSFEC_EE_MDR_BNDL_PROC, Method: PROCESS. This method is called for each employee record to be processed (i.e., each thread in the multi-thread framework in Step 3 of the process flow.) Implement implicit enhancement spot at the start of the method. Leverage a static method of your custom class ZCL_HRSFEC_CE_ITMAP_HELPER to export to memory the Config ID available in input-part_ee_mdr_rep_bndl_req-empl_master_data_repl_bndl_req-compound_employee_query_config.
    *$*$-Start: (1)---------------------------------------------------------------------------------$*$*
    ENHANCEMENT 1  ZPTP_HRSFEC_EE_MDR_BNDL_PROC.    "active version
    " Store the Config ID in Memory. This shall be read in the BADIs and other custom codes.
    " This value shall be useful in determining the Company Code, as each config id is meant for single Company.
    " This memory id shall be read in CONSTRUCTOR of Class ZCL_HRSFEC_CE_ITMAP_HELPER when an object of the class is created.
    
      ZCL_HRSFEC_CE_ITMAP_HELPER=>STORE_CONFIG_IN_MEMORY( input-part_ee_mdr_rep_bndl_req-empl_master_data_repl_bndl_req-compound_employee_query_config ).
    
    ENDENHANCEMENT.
    *$*$-End:   (1)---------------------------------------------------------------------------------$*$*​

     

  3. In Class CL_HRSFEC_APPLICATION_LOG, Method SAVE_APPL_LOG. This method is called when saving the SLG1 log at any time during the replication process (by main thread as well as spawned off child threads). Implement implicit enhancement spot at the start of the method. Sample code:
    *$*$-Start: (1)---------------------------------------------------------------------------------$*$*
    ENHANCEMENT 1  ZHRSFEC_APPLICATION_LOG.    "active version
    * Add Parameter to Application Log, to capture Config ID.
      DATA: lo_zzz_itmap_helper TYPE REF TO ZCL_HRSFEC_CE_ITMAP_HELPER.
      DATA: LS_ZZZ_PTP_CONFIG TYPE ZCL_HRSFEC_CE_ITMAP_HELPER=>TS_PTP_CONFIG.
      DATA: lt_zzz_para TYPE STANDARD TABLE OF SPAR.
      FIELD-SYMBOLS: <ls_zzz_para> TYPE spar.
      DATA: ls_zzz_log TYPE bal_s_log.
    
      CREATE OBJECT lo_zzz_itmap_helper. "This will set Config ID for the current run
                                         "in Constructor method by performing IMPORT FROM MEMORY.
    
      LS_ZZZ_PTP_CONFIG = lo_zzz_itmap_helper->get_ptp_config( ).
      IF NOT LS_ZZZ_PTP_CONFIG-config_id IS INITIAL.
        APPEND INITIAL LINE TO lt_zzz_para ASSIGNING <ls_zzz_para>.
        <ls_zzz_para>-param = ZCL_HRSFEC_CE_ITMAP_HELPER=>mc_logparam_configid. "CONFIGID
        <ls_zzz_para>-value = LS_ZZZ_PTP_CONFIG-config_id.
    
        CALL FUNCTION 'BAL_LOG_HDR_READ'
          EXPORTING
            i_log_handle = gv_log_handle
         IMPORTING
           E_S_LOG      = ls_zzz_log
         EXCEPTIONS
           LOG_NOT_FOUND                  = 1
           OTHERS       = 2
          .
        IF sy-subrc EQ 0.
          ls_zzz_log-params-t_par = lt_zzz_para. "Update parameters.
    
    "     Set callback routine for log header parameters
          ls_zzz_log-params-callback-userexitt = space. "Use 'F' in case of FM.
          ls_zzz_log-params-callback-userexitp = ZCL_HRSFEC_CE_ITMAP_HELPER=>MC_LOG_CALLBACK_PROGRAM. "E.g. ZHRSFEC_SLG1_PARAMS
          ls_zzz_log-params-callback-userexitf = ZCL_HRSFEC_CE_ITMAP_HELPER=>MC_LOG_CALLBACK_ROUTINE. "E.g. BAL_CALLBACK_DETAIL_LOG
    
          CALL FUNCTION 'BAL_LOG_HDR_CHANGE'
            EXPORTING
              i_log_handle = gv_log_handle
              i_s_log      = ls_zzz_log
            EXCEPTIONS
              LOG_NOT_FOUND                 = 1
              LOG_HEADER_INCONSISTENT       = 2
              OTHERS       = 3
            .
    
        ENDIF.
    
      ENDIF.
    
    
    ENDENHANCEMENT.
    *$*$-End:   (1)---------------------------------------------------------------------------------$*$*​

    In Program ZHRSFEC_SLG1_PARAMS, write a FORM routine, with following code:

    *--------------------------------------------------------------------
    * FORM BAL_CALLBACK_DETAIL_LOG
    *--------------------------------------------------------------------
    FORM bal_callback_detail_log                                "#EC CALLED
           TABLES
             i_t_params  STRUCTURE spar.
    * We have enhanced (via Enhancement ZHRSFEC_APPLICATION_LOG) the class method: CL_HRSFEC_APPLICATION_LOG->SAVE_APPL_LOG
    * by including CONFIGID as parameter in the Application Log Header. This way, we are able to
    * tie the App Log entries to Config ID. In there, we specify this Subroutine (BAL_CALLBACK_DETAIL_LOG)
    * as CALLBACK routine to view the parameter contents when displayed via SLG1 tcode.
    
    
      DATA: lv_config TYPE t77sfec_ptp_conf-config_id.
    
    * Get the log parameters
      LOOP AT i_t_params ASSIGNING FIELD-SYMBOL(<ls_params>).
        CASE <ls_params>-param.
          WHEN zcl_hrsfec_ce_itmap_helper=>mc_logparam_configid. "CONFIGID
            lv_config = <ls_params>-value.
        ENDCASE.
      ENDLOOP.
    
      IF NOT lv_config IS INITIAL.
        MESSAGE i001(zhrsfec_ptp) WITH lv_config. "Display in an info message Config ID contents
      ENDIF.
    
    ENDFORM.

    The result of this third enhancement is that when you view any of SLG1 logs generated by the replication program (refer the Object ID, SubObject ID and External ID captured in the process flow diagram), if you click on the Details button in the app bar (Cntrl+Shift+F3), you should see the Config ID in an information message. You can build a custom program as a wrapper to the SLG1 application to select message logs by Config ID, logged date and time, etc.

 

Of course, you might write to me with a query such as, “…but SAP doesn’t allow implicit enhancements in EC Payroll“. I unfortunately have no answer to that. It’s a risk you might have to take, given the limitation of existing replication framework for a multi-tenant scenario. If you have any other solution to address this requirement, kindly add as a comment for everyone to benefit from your experience. Thank you in advance.

With this, and a promise that I shall share more of my experiences in upcoming blog posts, ending this blog post. Until next time, abhīṣṭasiddhirastu.

Assigned tags

      Be the first to leave a comment
      You must be Logged on to comment or reply to a post.