Technology Blogs by Members
Explore a vibrant mix of technical expertise, industry insights, and tech buzz in member blogs covering SAP products, technology, and events. Get in the mix!
cancel
Showing results for 
Search instead for 
Did you mean: 
diwaneamit
Participant
Hello All,

This is the second blog in this series. You can refer to the first blog in the below link:

SAP ABAP Programming Model for FIORI- List Report Application (Part 1)

In this blog we will be looking into BOPF part to enable the Determination, Validation and Action in our Fiori List report Application:

Let's proceed with this tutorial. In last blog we have created a Transaction CDS on SPFLI Table.

Go to the CDS View and click on the highlighted dot, and then the link for the Generated BOPF Object as shown in below image:


BOPF Path


 

The Generated Business Object will look as below. Click on 'Go to Root Node':


 

In the root Node we can see option to Navigate for Determination, Action and Validation


BOPF Root Node


 

Determination: It can be use to determine some value at runtime. In our case we are using it to generate the Primary key value at runtime.

To create a new Determination, click on the Determination link in above image and then click on 'New' Button.


 

 

Give the name, description and Category as given below. (Ignore the error, I am receiving it as I have already created it)


 


Once created click on 'Triggers Configured' and enable it for create and update. You can also see the generated class for this determination where we will be writing our code:



 

Now go into the generated class and write the below code:
class ZCL_IDEMO_D_CALCULATEKEYVALUES definition
public
inheriting from /BOBF/CL_LIB_D_SUPERCL_SIMPLE
final
create public .
public section.
methods /BOBF/IF_FRW_DETERMINATION~EXECUTE
redefinition .
protected section.
private section.
ENDCLASS.

CLASS ZCL_IDEMO_D_CALCULATEKEYVALUES IMPLEMENTATION.
METHOD /bobf/if_frw_determination~execute.

"Read data with the given keys (typed with combined type table)
DATA lt_data TYPE ztidemo_ddl_spfli.
"Call retrieve method of BOPF Framework
io_read->retrieve(
EXPORTING
iv_node = is_ctx-node_key " uuid of node name
it_key = it_key " keys given to the determination
IMPORTING
eo_message = eo_message " pass message object
et_data = lt_data " itab with node data
et_failed_key = et_failed_key " pass failures
).
IF eo_message IS NOT BOUND.
eo_message = /bobf/cl_frw_factory=>get_message( ).
ENDIF.

"Select Data from DB Table
SELECT FROM spfli
FIELDS carrid, MAX( connid ) AS max
GROUP BY carrid
INTO TABLE @DATA(lt_max_item).


" Assign numbers to each newly created item and trigger the modification in BOPF
LOOP AT lt_data REFERENCE INTO DATA(lr_data).
IF lr_data->connid IS INITIAL.
"As the field is read only it will be always Initial in our case
READ TABLE lt_max_item WITH KEY carrid = lr_data->parent_key REFERENCE INTO DATA(lr_max_item).
IF sy-subrc = 0.
lr_max_item->max = lr_max_item->max + 10.
ELSE.
"Assign an Incremented value. In real case scenario we can get the new number from number range "function
APPEND INITIAL LINE TO lt_max_item REFERENCE INTO lr_max_item.
lr_max_item->max = lr_data->parent_key.
lr_max_item->max = lt_max_item[ carrid = 'AA' ]-max + 1 .
lr_max_item->carrid = 'AA'.
ENDIF.

" Fill leading zeros for ALPHANUM field on database
lr_data->carrid = lr_max_item->carrid.
lr_data->connid = |{ lr_max_item->max ALPHA = IN }|.
lr_data->arrtime = sy-uzeit.
lr_data->deptime = sy-uzeit.

io_modify->update(
EXPORTING
iv_node = is_ctx-node_key " uuid of node
iv_key = lr_data->key " key of line
is_data = lr_data " ref to modified data
it_changed_fields =
VALUE #( ( zif_idemo_ddl_spfli_c=>sc_node_attribute-zidemo_ddl_spfli-carrid )
( zif_idemo_ddl_spfli_c=>sc_node_attribute-zidemo_ddl_spfli-connid )
( zif_idemo_ddl_spfli_c=>sc_node_attribute-zidemo_ddl_spfli-arrtime )
( zif_idemo_ddl_spfli_c=>sc_node_attribute-zidemo_ddl_spfli-deptime )
( zif_idemo_ddl_spfli_c=>sc_node_attribute-zidemo_ddl_spfli-fltype )
)
). "Here you have to pass all the field name which you change or passing value
ENDIF.
ENDLOOP.
ENDMETHOD.
ENDCLASS.

 

Similarly create a new Validation by clicking on the Validation link under the root node. You can refer below image for the generated Validation:


BOPF Validation


 

Validation: Validation are use to validate the Input Screen data.

In our case we are validating the Country From Field.

I have created a Message class with below messages-


Message Class


Go to the generated validation class and write down the below code:
CLASS zcl_idemo_v_validatecountry DEFINITION
PUBLIC
INHERITING FROM /bobf/cl_lib_v_supercl_simple
FINAL
CREATE PUBLIC .

PUBLIC SECTION.

METHODS /bobf/if_frw_validation~execute
REDEFINITION .
PROTECTED SECTION.
PRIVATE SECTION.
ENDCLASS.

CLASS ZCL_IDEMO_V_VALIDATECOUNTRY IMPLEMENTATION.
METHOD /bobf/if_frw_validation~execute.
" Internal tab for Header Data
" Created using reference to Generated Table Type
DATA(lt_head) = VALUE ztidemo_ddl_spfli( ).
" Get Header Data row under process
io_read->retrieve(
EXPORTING
iv_node = is_ctx-node_key " Node Name
it_key = it_key " Key Table
IMPORTING
et_data = lt_head " Data Return Structure
).
" Instantiate Message Object if not bound
IF eo_message IS NOT BOUND.
eo_message = /bobf/cl_frw_factory=>get_message( ).
ENDIF.
"Loop the fetched records
LOOP AT lt_head REFERENCE INTO DATA(lr_head).
" Validate
DATA ls_msg TYPE symsg.
"If Country From is blank raise an error
IF lr_head->countryfr IS INITIAL.
ls_msg-msgty = 'E'.
ls_msg-msgid = 'ZBOPF'.
ls_msg-msgno = '000'.
ELSE.
"If entered Country is not valid raise an error
SELECT COUNT(*) FROM t005 INTO @DATA(lv_count) WHERE land1 = @lr_head->countryfr.
IF lv_count = 0.
ls_msg-msgty = 'E'.
ls_msg-msgid = 'ZBOPF'.
ls_msg-msgno = '001'.
ENDIF.
ENDIF.

" Add Message
IF NOT ls_msg IS INITIAL.
eo_message->add_message(
EXPORTING
is_msg = ls_msg " Message
iv_node = is_ctx-node_key " Node
iv_key = lr_head->key " Instance key
).

"Below step is important to stop the flow when error occurs
DATA ls_key TYPE /bobf/s_frw_key.
ls_key-key = lr_head->key.

APPEND ls_key TO et_failed_key.

ENDIF.
ENDLOOP.
ENDMETHOD.
ENDCLASS.

 

In Case if Validation fails, the create or update process will not get complete and error will appear on the FIORI App screen as shown below:


Validation Errors


Finally we will be adding the Action to our BOPF:

Action: Usually we use it to perform some activity based on some event which cannot be handled in create, update or delete methods.

In our case we are creating a new record by referring to the selected one. The Action button is added to the UI view with the help of annotation mentioned in the Metadata Extension view for SPFLI.


 

To create a Action we need to navigate to the root node for the generated Business Object of SPFLI (Shown in the image earlier) and click on the Action link.

Click on the 'New' Button in next page and create new Action referring to the below Image.(Note that the Action Name should match to the dataAction Value mentioned in the Metadata Extension view file).


 

After the Action is created go to the generated class and write down the below code:



CLASS zcl_idemo_a_copy DEFINITION
PUBLIC
INHERITING FROM /bobf/cl_lib_a_supercl_simple
FINAL
CREATE PUBLIC .

PUBLIC SECTION.

METHODS /bobf/if_frw_action~execute
REDEFINITION .
PROTECTED SECTION.
PRIVATE SECTION.
ENDCLASS.

CLASS zcl_idemo_a_copy IMPLEMENTATION.

METHOD /bobf/if_frw_action~execute.
DATA: lr_head_ref TYPE REF TO data.

DATA(lt_head) = VALUE ztidemo_ddl_spfli( ).
DATA ls_head_ref TYPE zsidemo_ddl_spfli.

" Retrieve the data from the Node
io_read->retrieve(
EXPORTING
iv_node = is_ctx-node_key
it_key = it_key
IMPORTING
et_data = lt_head
).

"Copy the data from retrieved node
LOOP AT lt_head REFERENCE INTO DATA(lr_head).
ASSIGN lr_head->* TO FIELD-SYMBOL(<fs_head>).

ls_head_ref-carrid = <fs_head>-carrid.
"Increase the connection id by 10 to avoid the primary key violation error
ls_head_ref-connid = <fs_head>-connid + 10.
"Date and time cannot be kept blank else the OData Metadata will fail to load
ls_head_ref-arrtime = sy-uzeit.
ls_head_ref-deptime = sy-uzeit.
ls_head_ref-countryfr = <fs_head>-countryfr.
"Copy field data
CREATE DATA lr_head_ref TYPE zsidemo_ddl_spfli.
ASSIGN lr_head_ref->* TO FIELD-SYMBOL(<fs_head_ref>).
IF <fs_head_ref> IS ASSIGNED.
<fs_head_ref> = ls_head_ref.
ENDIF.

"Create Record
io_modify->create(
EXPORTING
iv_node = is_ctx-node_key
is_data = lr_head_ref
IMPORTING
ev_key = DATA(lv_copy_key)
).

ENDLOOP.
ENDMETHOD.
ENDCLASS.

 

So here we are completed with this blog. We have successfully added the Determination, Validation and Action Node behavior to our BOPF. In the next blog we will see how to finally consume this view as a Fiori Application using SAP WebIDE.

SAP ABAP Programming Model for FIORI- List Report Application (Part 3)

Thanks,

Amit Diwane
12 Comments
Labels in this area