Skip to Content

Introduction

This is the second part of the ‘How to setup file upload planning sequence from SAPUI5’ blog series. You can read the first part of the blog here: How to setup file upload planning sequence from SAPUI5 – Part 1

In the first part, we successfully sent the file upload data to the OData gateway service and I also mentioned how we can call a planning sequence from a UI5 app. The next step is to create a custom Planning Function type so we can execute our own logic to do a CSV file upload into BW-Integrated Planning

Prerequisites

The file uploader for planning sequence only works with CSV files for now. It also expects that the order of the columns in the CSV file is the same as we have in the aggregation level. The sample working CSV format can be seen here.

Planning Function Type Creation

Before creating a new planning function type, we need to create a new ABAP class where we can implement the logic for the planning function type.

To create a new ABAP class, go to tcode SE24. Enter class name  ‘ZPF_FILE_UPLOAD’  and click create. Select the object type as class. Activate the newly created class.

After activation, go to the Interfaces tab and enter IF_RSPLFA_SRVTYPE_IMP_EXEC entry. Save and activate the class.

Until now, we have a custom ABAP class which we can use in our planning function type.

Go to transaction ‘RSPLF1’ and enter the function type name ‘ZPF_FILE_UPLOAD’ and description and click on Create.

In the properties tab, enter the name of our custom ABAP class and activate the planning function type.

Implementing the EXECUTE method

Go to transaction SE24 again and display the ‘ZPF_FILE_UPLOAD’ class which we created earlier. Go to the Methods tab and click on the EXECUTE method.

We will write the logic to read the data from the uploaded file from SAPUI5 here. The following code reads the data from a CSV file which was converted to xstring in the gateway service and can be accessed globally from the memory id ‘z_upload_data’.

method IF_RSPLFA_SRVTYPE_IMP_EXEC~EXECUTE.
    DATA:
      l_data            TYPE string,
      l_file_content    TYPE xstring,
      l_t_column        TYPE string,
      l_r_converter     TYPE REF TO cl_abap_conv_in_ce,
      l_r_output_line   TYPE REF TO data,
      l_t_data          TYPE TABLE OF string,
      l_t_header        TYPE TABLE OF string,
      l_t_line          TYPE TABLE OF string.

    DATA:
      BEGIN OF crlf,
        cr  TYPE c,
        lf  TYPE c,
      END OF crlf,
      l_s_data          TYPE string.

    FIELD-SYMBOLS:
      <l_s_data>        TYPE any,
      <l_s_output>      TYPE any,
      <l_field>         TYPE any,
      <l_tab_data>      TYPE any.

*   Read xstring containing file content
    import base64_xstring to l_file_content from memory id 'z_upload_data'.

*   Convert file content to string
      TRY.
          CALL METHOD cl_abap_conv_in_ce=>create
            EXPORTING
              input       = l_file_content
              encoding    = 'DEFAULT'
              replacement = '#'
              ignore_cerr = abap_false
            RECEIVING
              conv        = l_r_converter.

          CALL METHOD l_r_converter->read
            IMPORTING
              data = l_data.

        CATCH cx_root.
        EXIT.
      ENDTRY.

    crlf = cl_abap_char_utilities=>cr_lf.

*   Convert CRLF to LF
    REPLACE ALL OCCURRENCES OF crlf IN l_data WITH crlf-lf.

*   Convert CR to LF
    TRANSLATE l_data USING crlf.

*   Split into table lines
    SPLIT l_data AT crlf-lf INTO TABLE l_t_data.

*   Make copy of data
    create data l_r_output_line LIKE LINE OF c_th_data.
    ASSIGN l_r_output_line->* to <l_s_output>.

*   Read first line of table
    READ TABLE l_t_data INTO l_s_data INDEX 1.

*   Split the first line (header) of the table
    SPLIT l_s_data AT ',' INTO TABLE l_t_header.

*   Loop remaining lines except the file header
    LOOP AT l_t_data assigning <l_s_data> FROM 2.
      "split current line
      SPLIT <l_s_data> AT ',' INTO TABLE l_t_line.

      "loop over the header split
      LOOP AT l_t_header assigning <l_tab_data>.
        read table l_t_line index SY-tabix into l_t_column.
        ASSIGN COMPONENT <l_tab_data> of structure <l_s_output> to <l_field>.
        <l_field> = l_t_column.
      ENDLOOP.
*     Modify c_th_data from internal structure
      MODIFY table c_th_data from <l_s_output>.
    ENDLOOP.

  endmethod.

The complete code for the class can be found on this link.

The next step is to do the following things:

  • Create an aggregation level for InfoCube
  • Create filter on InfoObjects
  • Create a planning function
    • Select function type as ZPF_FILE_UPLOAD (custom function type that we created)
  • Create a planning sequence and select the aggregation level, filter and planning function created above.

Executing the planning sequence from SAPUI5

Until now, we have an implementation of a custom planning function which is now being used in the planning sequence we created. We will now call the planning sequence from the gateway service and execute the planning sequence. The following code executes the planning sequence and returns the messages/errors in the lt_bapiret table.

We will format the returned messages from the ‘RSPLSSE_PLSEQ_EXECUTE’ function and then return them to SAPUI5 and save the data to our InfoCube.

The complete code can be found here.

After executing a planning sequence, the returned messages will look like this on the SAPUI5 frontend.

Download

You can find the code in the consetto github repository: https://github.com/consetto/ui5-file-upload-planning 

Outlook

Further improvements/features can be added in the current solution for file upload. Some of them are:

  • Adding support for file upload from other file formats like excel, text file, etc.
  • Preview the file data before saving it in the InfoCube
  • Adding validations for correct order of columns in CSV file, InfoObject validations, correct file format/encoding, etc.

Conclusion

In this series of blogs, we looked at how to call a planning sequence in general and execute the underlying planning function from SAPUI5. I also explained how to do a CSV file upload into BW-Integrated Planning from SAPUI5 frontend. I hope it will help a lot of people who are looking for a solution to connect the SAPUI5 file upload for the plan data in BW-IP or BPC. I am looking forward to your feedback.

 

To report this post you need to login first.

1 Comment

You must be Logged on to comment or reply to a post.

Leave a Reply