Implementing Navigation

Objectives

After completing this lesson, you will be able to:
  • Define a data model declaratively
  • Implement a navigation

Declarative Data Model Definition

Development flow: Declarative data model definition

Now it is time for the declarative way defining a data model. Without any template to import or build on, it is the most time consuming way. On the other hand, it offers the most freedom. This concept continues with implementing the ABAP code manually: Time versus freedom.

Screenhots about defining a data model declaratively in SEGW

There are some elements of a data model that are often created manually. These elements are as follows:

  • Associations
  • Association sets
  • Navigation properties
  • Function imports

Some elements that can be created easily based on existing data structures can also be created manually or be maintained. These elements are as follows:

  • Entity types
  • Entity sets
  • Complex types
  • Properties
Screenshots of entity type and entity set in SEGW

When defining an entity type declaratively, properties are added by appending or inserting rows in the properties table. The property name is defined using the camel-case notation, which is not supported by ABAP. Therefore an ABAP field name represents the property in the ABAP code using capital letters and underscores.

At least one property must be defined as key. Every property needs a primitive or complex type. An extension to the OData standard by SAP are optional flags documenting the implemented features of the service in its metadata.

For an entity set, the flag Addressable is not just documentation like the others. It controls if the entity set can be addressed directly in an OData request or only indirectly via navigation.

Screenshots of primitive types and labels of an entity property in SEGW

Primitive types are defined by the OData standard and cover many common types used in programming. Some challenge can arise when mapping some of these types to ABAP types. For example, there is no boolean in ABAP.

Another extension to the OData standard by SAP are labels for properties. These are translatable text originating from ABAP and consumable in UI technologies. Beside a free or explicit text, the following ABAP repository elements are supported as text source:

  • Data element
  • Global ABAP class
  • ABAP program

Add an Additional Entity to a Data Model

Business Example

You are a developer in your company. You need to define an entity and entity set declaratively. In addition, you want to implement the method for querying a set of entities.

Template:
GW100_S_READ (SAP Gateway Project)
Solution:
GW100_S_DECLMODEL (SAP Gateway Project)

Note

This exercise requires an SAP Learning system. Login information are provided by your system setup guide.

Note

You may continue with your solution of the previous exercise or copy the template to ZGW100_##_DECLMODEL. Whenever the values or object names in this exercise include ##, replace ## with the number of your user.

Prerequisites

The data model was defined and the service was registered in exercise Define a Data Model Based on a Data Dictionary Structure.

Task 1: Define an Entity Declaratively using SAP Gateway Service Builder

Steps

  1. In the SAP Gateway Service Builder of your SAP S/4HANA (S4H) system, define the entity BusinessPartner declaratively consisting of the following fields:

    Caution

    Be sure not to have any typos in the property names, otherwise the ABAP field will be incorrect and the code provided in the solution will not work.
    NameKeyEDM Core TypeMax LengthLabel
    BusinessPartnerIDxEdm.String10Business Partner ID
    BusinessPartnerRole Edm.String3Business Partner Role
    EmailAddress Edm.String255E-mail Address
    CompanyName Edm.String80Company Name
    CurrencyCode Edm.String5Currency Code
    City Edm.String40City
    Street Edm.String60Street
    Country Edm.String3Country
    AddressType Edm.String2Address Type
    1. In the SAP Easy Access of your S4H, search for SAP Gateway Service Builder or start transaction SEGW.

    2. In the SAP Gateway Service Builder for your project, expand the node Data ModelEntity Types.

    3. In the context menu of Entity Types, choose Create.

    4. In the Entity Type Name field, enter BusinessPartner.

    5. Select the Create Related Entity Set checkbox.

    6. Choose Continue,

    7. Expand BusinessPartner in the left pane.

    8. Double-click Properties.

    9. Select Append Row and enter the values from the table above.

    10. Choose Save.

  2. Set the entity set BusinessPartnerSet to be Addressable from outside.

    1. Expand Data Model.

    2. Double-click Entity Sets.

    3. For of the BusinessPartnerSet, set the Addressable checkbox.

    4. Choose Generate Runtime Objects.

Task 2: Implement and Test the Query Operation of the new Entity

Steps

  1. In the SAP Gateway Service Builder of your SAP S/4HANA (S4H) system, navigate to the implementation of the BUSINESSPARTNERS_GET_ENTITYSET method of your project.

    1. In the SAP Gateway Service Builder of your S4H, expand the node Service ImplementationBusinessPartnerSet.

    2. In the context menu of GetEntitySet (Query), choose Go to ABAP Workbench.

    3. In the Information popup, choose Continue.

      Result

      The method is not yet implemented.
  2. In the Class Builder, redefine the method BUSINESSPARTNERS_GET_ENTITYSET to query all business partners calling the BAPI_EPM_BP_GET_LIST function module.

    1. In the Class Builder, choose Display <-> Change.

    2. Place the curser in the method BUSINESSPARTNERS_GET_ENTITYSET and choose Redefine.

    3. Write the following code or copy it from the solution:

      Code Snippet
      1234567891011121314151617181920212223242526272829303132
      METHOD businesspartners_get_entityset. DATA: lt_headerdata TYPE TABLE OF bapi_epm_bp_header, lt_return TYPE TABLE OF bapiret2. * Get data CALL FUNCTION 'BAPI_EPM_BP_GET_LIST' TABLES bpheaderdata = lt_headerdata return = lt_return. IF lt_return IS NOT INITIAL. "Message Container mo_context->get_message_container( ) ->add_messages_from_bapi( lt_return ). RAISE EXCEPTION TYPE /iwbep/cx_mgw_busi_exception EXPORTING textid = /iwbep/cx_mgw_busi_exception=>business_error message_container = mo_context->get_message_container( ). ENDIF. * Map properties from the back-end to output response structure et_entityset = VALUE #( FOR header IN lt_headerdata ( businesspartnerid = header-bp_id businesspartnerrole = header-bp_role emailaddress = header-email_address companyname = header-company_name currencycode = header-currency_code city = header-city street = header-street country = header-country addresstype = header-address_type ) ). ENDMETHOD.
    4. Choose Activate.

    5. In the Inactive Objects popup, select all objects and choose Continue.

    6. Choose Exit.

  3. In the SAP Gateway Client of your S4H, test the query operation in your service. Query all business partners.

    1. In the SAP Gateway Service Builder of your S4H, double-click Service Maintenance.

    2. Choose SAP Gateway Client.

    3. In the SAP Gateway Client, select HTTPS as Protocol.

    4. Choose Entity Set.

    5. In the Entity Sets popup, double-click BusinessPartnerSet.

      Example

      /sap/opu/odata/SAP/ZGW100_##_STUDENT_SRV/BusinessPartnerSet
    6. Choose Execute.

      Result

      The HTTP Response displays the business partners.

Implementation of a Navigation

Navigation example and definition in data model

In this app example, a business partner in the role of a supplier delivers a number of products. The button Products in the business partner details navigates to the list of products.

The achieve this behavior in OData, the entity types for business partner and product must be connected via an association in the data model. The cardinality of the association is set to "one (1)" to "at least on or more (n)" .

Each entity type can define navigation properties typed by an association. Navigation properties materialize as relative links in the payload and allow the user or client to navigate through the result set in a similar way to a website with hyperlinks.

Screenshot flow of Create Association wizard in SEGW

When choosing CreateAssociation on the Data Model node in the SAP Gateway Service Builder, a wizard starts allowing to define everything needed for a navigation:

  • An association defining principal and dependent entity with multiplicity
  • An referential constraint connecting the principal key to the dependent property
  • An association set defining the principal and dependent entity sets

Navigation properties should have meaningful names so that it is clear what the consumer can expect when calling them. Defining only one navigation property allows a uni-directional navigation. Defining two navigation properties allows bi-directional navigation.

Screenshots of navigation elements in SEGW

Everything created by the wizard can be adapted afterwards in the data model. Associations and association sets have their own nodes in the data model. Navigation properties are part of the corresponding entity types

Methods called in a navigation and expand request

For implementing a navigation only, you must solely implement the method to get the navigation target. Depending on the multiplicity of the association, this is the <Entity Set>_GET_ENTITY method for multiplicity = 1 and <Entity Set>_GET_ENTITYSET method for multiplicity n.

For implementing an expand, you must implement the method to get the source and expanded data. If the source is a single entry, the <Entity Set>_GET_ENTITY method must be implemented. If the whole entity set is the source, the <Entity Set>_GET_ENTITYSET method must be implemented. For the expanded data, it again depends on the multiplicity of the association.

Source code implementing a navigation

Defining the navigation elements in the data model is only the first part of creating a navigation. The second part is the implementation in the data provider class. For small data models, this can be done in the <Entity Set>_GET_ENTITY and <Entity Set>_GET_ENTITYSET methods depending on the multiplicity. For larger models it is recommended to outsource the evaluation of the navigation in own methods.

Again, the io_tech_request_context parameter provides the OData request header. First, the source of the navigation must be determined. The methods get_source_entity_type_name() or get_source_entity_set_name() can be used for that.

The next step is to get the source keys of the navigation by calling the get_converted_source_keys() method. The exporting parameter es_key_values is of type DATA, which means it adjusts itself to the type passed via the variable used in the method call. You can use the structure type from the model provider class generated based on the properties of the entity type.

The following block provides the example source code in a copy-friendly way:

Code Snippet
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263
METHOD productset_get_entityset. DATA: lt_headerdata TYPE TABLE OF bapi_epm_product_header, lt_return TYPE TABLE OF bapiret2. DATA: ls_bp_id TYPE bapi_epm_bp_id, ls_bp_headerdata TYPE bapi_epm_bp_header, lt_so_supplier TYPE TABLE OF bapi_epm_supplier_name_range, ls_businesspartner TYPE zcl_zgw100_01_student_mpc=>ts_businesspartner. * Get key for navigation source CASE io_tech_request_context->get_source_entity_type_name( ). WHEN zcl_zgw100_01_student_mpc=>gc_businesspartner. io_tech_request_context->get_converted_source_keys( IMPORTING es_key_values = ls_businesspartner ). ls_bp_id-bp_id = ls_businesspartner-businesspartnerid. CALL FUNCTION 'BAPI_EPM_BP_GET_DETAIL' EXPORTING bp_id = ls_bp_id IMPORTING headerdata = ls_bp_headerdata TABLES return = lt_return. IF lt_return IS NOT INITIAL. " Message Container mo_context->get_message_container( ) ->add_messages_from_bapi( lt_return ). RAISE EXCEPTION TYPE /iwbep/cx_mgw_busi_exception EXPORTING textid = /iwbep/cx_mgw_busi_exception=>business_error message_container = mo_context->get_message_container( ). ENDIF. lt_so_supplier = VALUE #( ( sign = 'I' option = 'EQ' low = ls_bp_headerdata-company_name ) ). ENDCASE. * Get data CALL FUNCTION 'BAPI_EPM_PRODUCT_GET_LIST' TABLES headerdata = lt_headerdata selparamsuppliernames = lt_so_supplier return = lt_return. IF lt_return IS NOT INITIAL. " Message Container mo_context->get_message_container( ) ->add_messages_from_bapi( lt_return ). RAISE EXCEPTION TYPE /iwbep/cx_mgw_busi_exception EXPORTING textid = /iwbep/cx_mgw_busi_exception=>business_error message_container = mo_context->get_message_container( ). ENDIF. * Fill response data er_entity = CORRESPONDING #( ls_headerdata ). ENDMETHOD.

Note

In the source code example, the BAPI for getting products does not offer a parameter to filter the products by business partner id, which is provided by the OData request. Therefore the parameter to filter the products by business partner name is used, which is read before using the BAPI for getting a business partner.

Implement a Navigation

Business Example

You are a developer or solution architect in your company. You need to model and implement navigation between entities.

Template:
GW100_S_DECLMODEL (SAP Gateway Project)
Solution:
GW100_S_NAVIGATION (SAP Gateway Project)

Note

This exercise requires an SAP Learning system. Login information are provided by your system setup guide.

Note

You may continue with your solution of the previous exercise or copy the template to ZGW100_##_NAVIGATION. Whenever the values or object names in this exercise include ##, replace ## with the number of your user.

Prerequisites

The data model for business partner was defined in exercise Add an Additional Entity to a Data Model and the query operation for products was implemented in exercise Implement a Query Operation.

Task 1: Model a Navigation using the SAP Gateway Service Builder

Steps

  1. In the SAP Gateway Service Builder of your SAP S/4HANA (S4H) system, model a navigation between the BusinessPartner and Product entities connecting one BusinessPartnerID to many SupplierID. Create the navigation property ProductSet in the BusinessPartner entity type.

    1. In the SAP Easy Access of your S4H, search for SAP Gateway Service Builder or start transaction SEGW.

    2. In the SAP Gateway Service Builder, for your project, expand the node Data Model.

    3. In the context menu of Associations, choose Create.

    4. In the Create Association popup, in the Association Name field, enter BusinessPartner_Products.

    5. For the Principal Entity, enter the following values:

      FieldValue
      Entity Type NameBusinessPartner
      Cardinality1
      Navigation PropertyProductSet
    6. For the Dependent Entity, enter the following values:

      FieldValue
      Entity Type NameProduct
      Cardinality1..n
    7. Choose Next.

    8. In the Dependent Property field, using the value help, enter SupplierID and choose Next.

    9. Choose Finish.

    10. Choose Generate Runtime Objects.

  2. In the SAP Gateway Client of your S4H, compare the result of the $metadata request with the Data Model of your SAP Gateway project.

    1. In the SAP Gateway Service Builder of your S4H, double-click Service Maintenance.

    2. Choose SAP Gateway Client.

    3. In the SAP Gateway Client, select HTTPS as Protocol.

    4. Choose Add URI Option.

    5. In the Add URI Option popup, double-click $metadata.

      Example

      /sap/opu/odata/SAP/ZGW100_##_STUDENT_SRV/$metadata
    6. Choose Execute.

      Result

      The HTTP Response displays the metadata of your service.
    7. Compare the service metadata with the Data Model of your SAP Gateway project.

Task 2: Implement and Test a Navigation

Steps

  1. In the SAP Gateway Client of your S4H, test the navigation in your service. Query the products of a business partner.

    1. In the SAP Gateway Client of your S4H, choose Entity Set.

    2. In the Entity Sets popup, double-click BusinessPartnerSet.

      Example

      /sap/opu/odata/SAP/ZGW100_##_STUDENT_SRV/BusinessPartnerSet
    3. Choose Execute.

      Result

      The HTTP Response displays all business partners.
    4. In the Request URI field, add one of the links to the products of a business partner.

      Example

      /sap/opu/odata/SAP/ZGW100_##_STUDENT_SRV/BusinessPartnerSet('0100000000')/ProductSet
    5. Choose Execute.

      Result

      The HTTP Response displays all products for all business partners instead of only for the requested one.
  2. In the SAP Gateway Service Builder of your S4H, adapt the method PRODUCTSET_GET_ENTITYSET to query products based on the navigation source using the selection criteria of BAPI_EPM_PRODUCT_GET_LIST function module.

    1. In the SAP Gateway Service Builder of your S4H, expand Service ImplementationProductSet.

    2. In the context menu of GetEntitySet (Query), choose Go to ABAP Workbench.

    3. Add the following code or copy it from the solution:

      Note

      If you copy the code from the solution, replace the references to the model provider class of the solution with one to your model provider class.
      Code Snippet
      12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152
      METHOD productset_get_entityset. DATA: lt_headerdata TYPE TABLE OF bapi_epm_product_header, lt_return TYPE TABLE OF bapiret2. DATA: ls_bp_id TYPE bapi_epm_bp_id, ls_bp_headerdata TYPE bapi_epm_bp_header, lt_so_supplier TYPE TABLE OF bapi_epm_supplier_name_range, ls_businesspartner TYPE zcl_zgw100_##_student_mpc=>ts_businesspartner. * Get key for navigation source CASE io_tech_request_context->get_source_entity_type_name( ). WHEN zcl_zgw100_##_student_mpc=>gc_businesspartner. io_tech_request_context->get_converted_source_keys( IMPORTING es_key_values = ls_businesspartner ). ls_bp_id-bp_id = ls_businesspartner-businesspartnerid. CALL FUNCTION 'BAPI_EPM_BP_GET_DETAIL' EXPORTING bp_id = ls_bp_id IMPORTING headerdata = ls_bp_headerdata TABLES return = lt_return. IF lt_return IS NOT INITIAL. " Message Container mo_context->get_message_container( ) ->add_messages_from_bapi( lt_return ). RAISE EXCEPTION TYPE /iwbep/cx_mgw_busi_exception EXPORTING textid = /iwbep/cx_mgw_busi_exception=>business_error message_container = mo_context->get_message_container( ). ENDIF. lt_so_supplier = VALUE #( ( sign = 'I' option = 'EQ' low = ls_bp_headerdata-company_name ) ). ENDCASE. * Get data CALL FUNCTION 'BAPI_EPM_PRODUCT_GET_LIST' TABLES headerdata = lt_headerdata selparamsuppliernames = lt_so_supplier return = lt_return. ... ENDMETHOD.
    4. Choose Activate.

    5. In the Inactive Objects popup, select all objects and choose Continue.

  3. In the SAP Gateway Client of your S4H, retest the navigation in your service. Query the products of a business partner.

    1. In the SAP Gateway Client, choose Execute.

      Example

      /sap/opu/odata/SAP/ZGW100_##_STUDENT_SRV/BusinessPartnerSet('0100000000')/ProductSet

      Result

      The HTTP Response displays the products for the business partner.

Task 3: Implement and Test an Expand

Steps

  1. In the SAP Gateway Client of your S4H, test the query option $expand in your service. Read a business partner including its products.

    1. In the SAP Gateway Client of your S4H, replace the / in front of ProductSet with ?$expand=.

      Example

      /sap/opu/odata/SAP/ZGW100_##_STUDENT_SRV/BusinessPartnerSet('0100000000')?$expand=ProductSet
    2. Choose Execute.

      Result

      The HTTP Response displays the error Method 'BUSINESSPARTNERS_GET_ENTITY' not implemented in data provider class.
  2. In the SAP Gateway Service Builder of S4H, navigate to the implementation of the BUSINESSPARTNERS_GET_ENTITY method of your project.

    1. In the SAP Gateway Service Builder of your S4H, for your project, expand the node Service ImplementationBusinessPartnerSet.

    2. In the context menu of GetEntity (Read), choose Go to ABAP Workbench.

    3. In the Information popup, choose Continue.

      Result

      The method is not yet implemented.
  3. In the Class Builder, redefine the method BUSINESSPARTNERS_GET_ENTITY to read a single business partner by calling the BAPI_EPM_BP_GET_DETAIL function module.

    1. In the Class Builder, choose Display <-> Change.

    2. Place the curser in the method BUSINESSPARTNERS_GET_ENTITY and choose Redefine.

    3. Write the following code or copy it from the solution:

      Code Snippet
      12345678910111213141516171819202122232425262728293031323334353637383940414243
      METHOD businesspartners_get_entity. DATA: ls_bp_id TYPE bapi_epm_bp_id, ls_headerdata TYPE bapi_epm_bp_header, lt_return TYPE TABLE OF bapiret2. * Get key fields from request io_tech_request_context->get_converted_keys( IMPORTING es_key_values = er_entity ). ls_bp_id-bp_id = er_entity-businesspartnerid. * Get data CALL FUNCTION 'BAPI_EPM_BP_GET_DETAIL' EXPORTING bp_id = ls_bp_id IMPORTING headerdata = ls_headerdata TABLES return = lt_return. IF lt_return IS NOT INITIAL. " Message Container mo_context->get_message_container( ) ->add_messages_from_bapi( lt_return ). RAISE EXCEPTION TYPE /iwbep/cx_mgw_busi_exception EXPORTING textid = /iwbep/cx_mgw_busi_exception=>business_error message_container = mo_context->get_message_container( ). ENDIF. * Map properties from the back-end to output response structure er_entity = VALUE #( businesspartnerid = ls_headerdata-bp_id businesspartnerrole = ls_headerdata-bp_role emailaddress = ls_headerdata-email_address companyname = ls_headerdata-company_name currencycode = ls_headerdata-currency_code city = ls_headerdata-city street = ls_headerdata-street country = ls_headerdata-country addresstype = ls_headerdata-address_type ). ENDMETHOD.
    4. Choose Activate.

    5. In the Inactive Objects popup, select all objects and choose Continue.

  4. In the SAP Gateway Client, retest the expand in your service. Read a business partner including its products.

    1. In the SAP Gateway Client of your S4H, choose Execute.

      Example

      /sap/opu/odata/SAP/ZGW100_##_STUDENT_SRV/BusinessPartnerSet('0100000000')?$expand=ProductSet

      Result

      The HTTP Response displays the business partner and its products.

Log in to track your progress & complete quizzes