Skip to Content
Technical Articles
Author's profile photo Mike B.

How to add new row / element to context node collection in SAP CRM using ABAP

Sometimes performing even basics tasks in ABAP may confuse, especially if you are a newbie in ABAP. Today I’m going to show how to add new row (line, element) to context node collection in SAP CRM using ABAP. At the end of the post you can find the final code example, implementing the discussed task. Feel free to copy, paste and run this code snippet.

Theory. In order to add new element to context node you have to:

  1. Define a structure line of the context node element
  2. Create data reference, based on the structure line, defined at the previous step
  3. Define the new context node object that will contain the new values, we’re going to add to the context node
  4. Fill the new context node object with the new values
  5. Add new context node object, filled with the data to the context node

Practice. The final code:

  1. ” define structure line of the context node
  2. TYPES:
  3.         BEGIN OF line_struct_type,
  4.                 personID                TYPE numc5,
  5.                 firstName               TYPE char30,
  6.                 lastName                TYPE char30,
  7.         END OF line_struct_type.
  8. DATA:
  9.         cn_line_struct          TYPE REF TO DATA,
  10.         cn_single_element       TYPE REF TO cl_bsp_wd_value_node.
  11. ” create data object, based on defined structure line
  12. CREATE DATA cn_line_struct TYPE line_struct_type.
  13. ” create new data container object according to the context node structure line
  14. CREATE OBJECT cn_single_element
  15.         EXPORTING
  16.                 iv_data_ref = cn_line_struct.
  17. ” fill the values into new data container object
  18. cn_single_element->set_property_as_string(
  19.         EXPORTING
  20.                 iv_attr_name = ‘personID’
  21.                 iv_value     = ‘222’
  22. ).
  23. ” push the new data container object to the existed context node collection
  24. comp_controller_ref->typed_context->%context_node%->collection_wrapper->ADD (
  25.         EXPORTING
  26.                 iv_entity = cn_single_element
  27. ).

As you can see, even such basic stuff in ABAP SAP CRM may contain some pitfalls.

Assigned Tags

      21 Comments
      You must be Logged on to comment or reply to a post.
      Author's profile photo juergen baur
      juergen baur

      great smal solution.

      Do you have more of such examples?

      Author's profile photo Mike B.
      Mike B.
      Blog Post Author

      Could you specify what kind examples do you actually looking for?

      Author's profile photo juergen baur
      juergen baur

      I'm thinking about basic things e.g.

      Remove entity from collection with interator:

          DATA: lv_collection TYPE REF TO if_bol_bo_col,

                entity        TYPE REF TO cl_crm_bol_entity.

          data: lv_index      type i.

      *     In display mode only show attributes that contain a value

            IF entity->is_locked( ) EQ abap_false.

              lv_index = lv_collection->size( ).

              WHILE lv_index GT 0.

                entity ?= lv_collection->find( iv_index = lv_index ).

                IF  entity IS BOUND

                AND entity->get_property_as_string( 'ATTR_VALUE' ) IS INITIAL.

                  lv_collection->remove( entity ).

                ENDIF.

                SUBTRACT 1 FROM lv_index.

              ENDWHILE.

            ENDIF.

      Or working with value nodes.

      br

      Jürgen

      Author's profile photo Mike B.
      Mike B.
      Blog Post Author

      Ok, I'll tink about it.

      BTW, if I remember right, entity->is_locked( ) indicates if the current entity is locked only by user, who calls is_locked( ). Am I right?

      If I'm right, the delete process can cause the problem, it may not delete the element, may cause the dump or other side-effects.

      So, be careful with this scenario.

      Author's profile photo juergen baur
      juergen baur

      HI Mike,

      it is just an example from my z_component nothing from production.

      Just an example.

      Remove entity from collection with interator:

          DATA: lv_collection TYPE REF TO if_bol_bo_col,

                     entity          TYPE REF TO cl_crm_bol_entity,

                     lv_index      TYPE i.

              lv_index = lv_collection->size( ).

              WHILE lv_index GT 0.

                entity ?= lv_collection->find( iv_index = lv_index ).

                IF  entity IS BOUND

                AND entity->get_property_as_string( 'ATTR_VALUE' ) IS INITIAL.

                  lv_collection->remove( entity ).

                ENDIF.

                SUBTRACT 1 FROM lv_index.

              ENDWHILE.

      So, now it is more general.

      br

      Jürgen

      Author's profile photo Hai Wang
      Hai Wang

      That is great! How do you find out? 😕

      Author's profile photo Mike B.
      Mike B.
      Blog Post Author

      By trial and error method 😉

      Author's profile photo Leon Limson
      Leon Limson

      Good one!!

      Cheers,

      Leon

      Author's profile photo Harish Kumar
      Harish Kumar

      nice doc..

      but i have one doubt regarding the display of new added attribute,  will it be display in configuration of view or not if we want to display it in UI. or any other way to display..?

      Best regards,

      Harish kumar.

      Author's profile photo Mike B.
      Mike B.
      Blog Post Author

      In my post I related to the question of adding new row to existed context node with already defined structure, not to the question of adding a new attribute to the context node. Thus, if you have defined displaying of this attribute in UI via configuration or via BSP, and you retrieve this new added line from context node correctly, so I don't see any reason to have an issue.

      If you mentioned some other doubt, please, let me know.

      Author's profile photo Former Member
      Former Member

      Very informative. Thanks 🙂

      Author's profile photo Former Member
      Former Member

      Hi Mike,

      Good One.

      I need some clarification.

      In this case you considered the context node holds only a value node ( value attributes ) right?

      If the context node holds  a model node then this thing will not work.

      In this case we need to get it's parent and use the create_related_entity method and then we need to add it to the collection of the context node.

      Is it correct???

      Regards,

          DP.

      Author's profile photo Mike B.
      Mike B.
      Blog Post Author

      Unfortunately, I can't check it right now, but it looks like a right direction.

      Try to implement and let us know if it works.

      Author's profile photo Former Member
      Former Member

      I tried this before..

      If it is a context node with model attributes we cannot add the cl_bsp_wd_value_node to the collection of context node as it refers to cl_crm_bol_entity.

      I think what ever the example code that you wrote is for a context node with value attributes.

      Regards,

          DP.

      Author's profile photo Mike B.
      Mike B.
      Blog Post Author

      Yeap, code, I posted, is specified for value node case.

      Basically, I don't see a reason why we can't add new element to model context node, so tomorrow I'll try to play with the case of model node and hope, will can suggest the way to solve the issue.

      Author's profile photo Former Member
      Former Member

      There is no issue in doing that for a model node.. We just need to use the method create_related_entity and add it to the collection.  I did it once earlier

      I my code btpartnerset is the parent object and its child Btpartner is a table view, so i used the following code :

      data : lr_curr_partset type ref to cl_crm_bol_entity.

      lr_curr_partset ?= me->typed_context->btpartnerset->collection_wrapper->get_current( ).

      CALL METHOD LR_CURR_PARTSET->CREATE_RELATED_ENTITY

        EXPORTING

          IV_RELATION_NAME = 'BTPartnerOpportunity'

        RECEIVING

          RV_RESULT = lr_partneroppt.

      check lr_partneroppt is bound.

      me->typed_context->btpartner->collection_wrapper->add( lr_partneroppt ).

      Author's profile photo Mike B.
      Mike B.
      Blog Post Author

      Let me understand, earlier you wrote: «If it is a context node with model attributes we cannot add», now you are writing: «There is no issue in doing that for a model node».

      So, what's the problem? Do you succeed to implement the task or not?

      Do you succeed to add a new element to context node of model node type or not?

      Please, clarify the situation, I want to know if «to play with the case» or you are already OK with the case.

      Author's profile photo Former Member
      Former Member

      I am already ok with this case. I just tried your code for adding a row to model node but it did not worked for me. So I am asking you for a clarification that your code is only for Value node and for adding a row to a model node we need to follow the code which i posted in the previous comment.

      Author's profile photo Mike B.
      Mike B.
      Blog Post Author

      Actually, at the end we're using the same code except one thing.

      In my code I'm showing how to build new element, fill it with data and only after that to add it to collection wrapper.

      In contrast, in your case, there is no such step, since you are working with model node, so, you don't have to execute all this dances with defining structure, creating element and filling it with data. You just need to create related entity, to get the reference to created relation and if it's bounded, add it to collection wrapper.

      That's all.

      Author's profile photo Luís Pérez Grau
      Luís Pérez Grau

      Hi,

      Technically looks like you can, but I don't really see the benefit of it. Diferent kinds of entities inside a context node can lead to confusion or errors,

      Example 1: The context node is pointed to a table view element, each row should have the same structure so all entities inside the context node should be equall.

      Example 2: Someone fresh just started in the project, he/she will need some time to understand what the hell is happening, "why in this context node which I use the method get_curren give me an entity BuilHeader(for example) and in other scenarios is a "Blahblahblah" ?

      I hope you don't take it to the wrong way, I'm just trying to contribute.

      Cheers!

      Luis

      Author's profile photo Mike B.
      Mike B.
      Blog Post Author

      100% agree.