Skip to Content
Technical Articles
Author's profile photo Törehan Gören

AES Decryption in Fiori & Encryption in ABAP

Introduction

Recently we had a requirement in our organization to implement encryption for some data transmission from Fiori to SAP with oData.  The requirement was to AES256 encrypt the information shared between the systems.

SAP Class/Function Modules & JS Libs used for the process:

  • From crypto-js library AES.js file is used to implement the logic for generation of AES key and encryption of information.
  • CL_SEC_SXML_WRITER is used to decryption of information.
  • SCMS_STRING_TO_XSTRING is used to convert string to xstring
  • /ui2/cl_abap2json is used to convert xstring to string

Import JS Library to your Project

  • First download CryptoJS zip from https://code.google.com/archive/p/crypto-js/downloads. I used the version 3.1.2. 
  • Unzip it in your computer. In rollups file you will find aes.js, copy it to your Project/webapp folder.

Bild1

Bild1

  • Now we have to import aes.js Javascript Lib in our Main controller or the controller you want to use.
  • Add the following command to top of your controller “jQuery.sap.require(“yourUploadedAESFileDirection”)”

Bild2

Generate Encryption Key & Encryption (in FIori JS)

I used following logic to generate Key for encryption in JavaScript and sending to SAP via oData Service.

*IV: In cryptography, an initialization vector (IV) is an input to a cryptographic primitive being used to provide the initial state. The IV is typically required to be random. Randomization is crucial for some encryption schemes to achieve semantic security, a property whereby repeated usage of the scheme under the same key does not allow an attacker to infer relationships between (potentially similar) segments of the encrypted message.

Note: Use your own ramdom created IV. And the randomly generated Key length should be 32 characters.

Encryption:

// This is our Secret Message ChiperText
let data = "THIS IS MY SECRET KEY";
//initialization vector for additional secure
let iv = 'ThisIs33221321OurIV1ar234567';
//Your key length should be 32 characters, you should generate your own random key every time
let key = 'THISISOURKEY1234567WORKSTATION01';

// prepare key & iv for CryptoJS encryption
let fkey = CryptoJS.enc.Utf8.parse(key);
let fiv = CryptoJS.enc.Utf8.parse(iv);

//Encyrption
//We access the library with calling "CryptoJS" 
//and it returns the encrypted value in "enc.ciphertext"
let enc = CryptoJS.AES.encrypt(data, fkey, {
                    iv: fiv,
                    mode: CryptoJS.mode.CBC,
                    padding: CryptoJS.pad.Pkcs7,
});


Sending to SAP:

let aFilters = [];
//Call your oData Service to send the encrypted text
//We used here just one Filter with name of "KEY"
//To send the text we change the format of "enc.ciphertext" as string
aFilters.push(new Filter("KEY", FilterOperator.EQ, enc.ciphertext.toString()));
this.getView().getModel().read("/CryptoSet", {
				filters: aFilters,
				success: function (oData, response) {
                                       //do something
				}.bind(this),
				error: function (oError) {
                                     //do something
				}.bind(this)
			});

You can use a function call instead of entity set. its up to you. If you want to follow my way you can get more information about oData services entitySet on following link.

https://blogs.sap.com/2021/05/19/a-step-by-step-process-to-post-odata-services-in-sap-sap-hana-system/

 

Decryption on Serverside (ABAP)

Here you can copy bellow code in your oData Service class “*_DPC_EXT” in your entitySet method.

Variable declaration

    "Encryption Parameters
    DATA: lt_binary TYPE STANDARD TABLE OF x255.


    DATA: i_xstring     TYPE xstring,
          lx_plaintext  TYPE xstring,
          i_iv          TYPE string,
          i_ivx         TYPE xstring,
          i_key_xstring TYPE xstring,
          i_key         TYPE string,
          lv_text_dec   TYPE string,
*this is our encrypted text from Fiori
          lv_ciphertext TYPE string. 

I used “lv_ciphertext” as my input variable. You can loop in your entityset method the import table it_filter_select_options and write your key value to lv_ciphertext. It should be in upper case.

Prepare the variables in right format 

We need convert strings to xstring format to be use in Class cl_sec_sxml_writer

*>> Set KEY & IV parameters
      i_iv = 'ThisIs33221321OurIV1ar234567'.
      i_key = 'THISISOURKEY1234567WORKSTATION01'.

*Convert all to xstring format
      i_xstring = lv_ciphertext.

      CALL FUNCTION 'SCMS_STRING_TO_XSTRING'
        EXPORTING
          text   = i_key
        IMPORTING
          buffer = i_key_xstring
        EXCEPTIONS
          failed = 1
          OTHERS = 2.
      IF sy-subrc <> 0.
* Implement suitable error handling here
      ENDIF.

      CALL FUNCTION 'SCMS_STRING_TO_XSTRING'
        EXPORTING
          text   = i_iv
        IMPORTING
          buffer = i_ivx
        EXCEPTIONS
          failed = 1
          OTHERS = 2.
      IF sy-subrc <> 0.
* Implement suitable error handling here
      ENDIF.

      "Add IV to ciphertext 
      CONCATENATE   i_ivx(16) i_xstring INTO i_xstring  IN BYTE MODE.

Decrypt the “i_xstring” variable by using class “cl_sec_sxml_writer”

    IF i_xstring IS NOT INITIAL AND
       i_key_xstring IS NOT INITIAL AND
       i_ivx IS NOT INITIAL.

      TRY.
          " DECRYPT WITH AES256 ALGORITHM
          cl_sec_sxml_writer=>decrypt(
            EXPORTING ciphertext = i_xstring key = i_key_xstring algorithm = cl_sec_sxml_writer=>co_aes256_algorithm
            IMPORTING plaintext = lx_plaintext ).

        CATCH cx_sec_sxml_encrypt_error INTO DATA(oref).
      ENDTRY.

    ENDIF.

Here we got our decrypted text in xstring format in lx_plaintext. Now convert it to string.

*      " convert xstring to string for output
          lv_text_dec = /ui2/cl_abap2json=>conv_xstring_to_string( lx_plaintext ).

Why is it important to consider encrypted data transfer?

Encrypting personal data whilst it is being transferred from one device to another provides effective protection against interception of the communication by a third party whilst the data is in transfer. It is also strongly recommended to use encrypted communication when transmitting any data over a wireless communication network (eg Wi-Fi) or when the data will pass through an untrusted network.
Data can be transferred over a non-secure communication channel yet still remain protected. The biggest advantage of this approach is, if you want to delivery some important data via oData, your data stay safe even if someone listening the network.

Assigned Tags

      4 Comments
      You must be Logged on to comment or reply to a post.
      Author's profile photo Benjamin Krencker
      Benjamin Krencker

      Hi Törehan Gören

      This is an interesting blog post but I don‘t understand why you had to implement encryption by yourself as you can setup Fiori to use SSL (TLS) for securing the communication.

      Maybe you can clarify why it was necessary to use AES or the benefits of your approach?

      Ben

      Author's profile photo Törehan Gören
      Törehan Gören
      Blog Post Author

      Hi Benjamin Krencker,

      it was already setup as regular SSL, but the transferred Data contained passwords and customer didn't find SSL encryption secure enough and we just added as second security. Maybe it's not something i will use again but i wanted to share.

       

      KR

      Törehan

      Author's profile photo Benjamin Krencker
      Benjamin Krencker

      Ok thanks, now I understand 🙂

      Thanks for sharing!

      Author's profile photo Gregor Wolf
      Gregor Wolf

      Hi Törehan,

      looking at the shared implementation I would question what additional security the encryption should add here. The key and iv are part of the code that is transfered via the SSL encryption. So this implementation relies still on the security of the SSL/TLS connection. The only option that would add more security would be to ask the user for an encryption Key that is not transfered over the SSL connection. But then you have the challenge how you would provide this Key to the SAP System.

      The only real solution would be using Private / Public Keys. So in the Client you would use the Public Key of the SAP System to encrypt the data which then can be decrypted with the Private Key of the SAP System.

      Best Regards
      Gregor