Tree view in RAP

Estimated read time 14 min read

In this blog we will cover: 

Introduction, Architecture overview, Scenario, Procedure, Conclusion. 

Introduction: 

The CDS hierarchy in SAP ABAP is used to define recursive, tree-like relationships in data directly within Core Data Services (CDS) views. It allows structured, hierarchical data (like manager-employee, material categories, sales orgs, BOMs, etc.) to be represented and consumed easily in UI applications and analytics tools. 

In the RAP (RESTful ABAP Programming Model), a Tree View is used to visualize hierarchical (recursive) data structures in the UI—typically in Fiori Elements apps such as List Reports with tree tables. 

Tree View allows end users to navigate data in a parent-child format (e.g., managers → employees, sales org → region → country).

├── Region North America 

│   ├── Country USA 

│   └── Country Canada 

└── Region Europe 

    ├── Country Germany 

    └── Country France 

To enable a Tree View in a RAP app: 

Model recursive data in a CDS view (e.g., employee-manager, sales org tree) Create a CDS hierarchy (define hierarchy) Use a C_ projection view to expose the hierarchy using:  @odata.hierarchy.recursiveHierarchy: [ { entity.name: ‘ZVS_I_SALES_ORG_HN’ } ] Add your entity to Service Definition and Service Binding Run the Fiori app (it will automatically detect and display a tree) 

Treeviews: Architecture Overview 

The implementation of a treeview in the ABAP RESTful Application Programming Model (RAP) requires different entities depending on whether the treeview should be read-only or editable. 

Architecture Overview: Read-Only Treeview 

 

 

Architecture Overview: Read-Only Tree View in CDS 

To enable a read-only hierarchical display of data in the UI, the following CDS artifacts are used in combination: Database Table 
A custom database table holds the hierarchical data structure. Interface View 
This CDS view entity is built on top of the database table and defines the data model. It includes a self-association to represent the parent-child hierarchy within the same dataset. CDS Hierarchy 
A persistent CDS hierarchy is created using the DEFINE HIERARCHY statement. It provides a hierarchical interpretation of the interface view, enabling the framework to understand how records are nested. Projection View 
This view projects the interface view and incorporates the CDS hierarchy to expose the structured, hierarchical data as required by the UI. Service Definition and Service Binding 
These are created to expose the CDS projection view as an OData service. This step enables the consumption of hierarchical data in SAP Fiori or other UI frameworks. 

Architecture Overview: Editable Treeview with Draft

 

 

Editable Tree View with Draft Enablement – Architecture Overview 

To enable an editable tree view with draft functionality, the following key artifacts work together to define and expose the hierarchical data structure to the UI: 

Database table:

Active and draft tables store the hierarchical data and hierarchy directory separately, supporting draft-enabled transactional scenarios. 

CDS view Entities (Interface Views):

Interface views reference the underlying database tables and act as the first projection layer. The CDS view for the hierarchical data must include: A self-association to represent the parent-child relationship within the same entity (enabling hierarchy logic). A one-to-many association to link with the hierarchy directory entity. 

CDS Hierarchy:

A persistent CDS hierarchy is defined using DEFINE HIERARCHY.It enables hierarchical interpretation for the data exposed by the first-layer CDS view. 

Base CDS views:

These views enrich the model with compositional information. The hierarchy directory view acts as the composition root (parent). The hierarchical data view acts as the composition child. 

Behaviour Definition for base views:

Defines transactional behavior, including: Draft capability Editing operations required by the UI. 

Projection views:

Serve the consumption layer: For the hierarchy directory: A projection view supports transactional queries. For hierarchical data: A projection view combines interface view data with hierarchical logic using the @OData.hierarchy.recursiveHierarchy annotation (referring to the CDS hierarchy). 

Projection behaviour definition:

Describes the behavior of projection views, allowing: Custom logic like determinations, validations, authorizations, numbering, etc. 

Service Definition and Service Binding:

Finally, a service definition and binding are created to expose the hierarchy and its data structure to the UI layer via OData. 

===========================================================================

Scenario for Tree view in RAP: 

In large global companies, the Sales & Distribution (SD) module often reflects the company’s organizational structure. Typically, Sales Organizations are arranged in a multi-level hierarchy like this: 

This kind of structure helps companies manage sales performance, reporting, and operations more effectively. 

However, many systems don’t provide a read-only, easy-to-use view of this hierarchy — especially in a tree or drill-down format that users can easily navigate. 

In this blog, we’ll walk through how to model and expose this Sales Org hierarchy using CDS Hierarchies, and finally expose it through an OData service to be consumed in a Fiori UI. 

Procedure: 

Step 1: Define the Base Table – ZVS_DT_SALES 

This transparent table stores the core sales organization data including parent-child relationships. 

@EndUserText.label : ‘Hierarchy: Read Only: Sales Organization’
@AbapCatalog.enhancement.category : #NOT_EXTENSIBLE
@AbapCatalog.tableCategory : #TRANSPARENT
@AbapCatalog.deliveryClass : #A
@AbapCatalog.dataMaintenance : #RESTRICTED
define table zvs_dt_sales {

key client : abap.clnt not null;
key sales_org_id : abap.char(6) not null;
name : abap.char(50);
region : abap.char(20);
country : abap.char(3);
@Semantics.amount.currencyCode : ‘zvs_dt_sales.currency’
revenue : abap.curr(21,2);
currency : /dmo/currency_code;
parent_sales_org : abap.char(6);

}

Note: parent_sales_org is a self-referencing field to represent the hierarchy. 

This table contain some records: 

 

Step 2: Interface View – ZVS_I_SALES 

This CDS view represents the Sales Org data and defines a self-association to establish the parent-child link. 

@AbapCatalog.viewEnhancementCategory: [#NONE]
@AccessControl.authorizationCheck: #NOT_REQUIRED
@EndUserText.label: ‘Interface View: Sales Organization’
@Metadata.ignorePropagatedAnnotations: true
@ObjectModel.usageType:{
serviceQuality: #X,
sizeCategory: #S,
dataClass: #MIXED
}
define view entity zvs_i_sales as select from zvs_dt_sales
association to zvs_i_sales as _Parent on
$projection.ParentSalesOrg = _Parent.SalesOrgId
{
key sales_org_id as SalesOrgId,
name as Name,
region as Region,
country as Country,
@Semantics.amount.currencyCode: ‘Currency’
revenue as Revenue,
currency as Currency,
parent_sales_org as ParentSalesOrg,

_Parent
}

Step 3: Define Hierarchy – ZVS_I_SALES_HN 

Using CDS hierarchy syntax, we now define a parent-child recursive hierarchy. 

@EndUserText.label:’Sales Organization Hierarchy’

define hierarchy zvs_i_sales_hn
as parent child hierarchy (
source zvs_i_sales
child to parent association _Parent
start where ParentSalesOrg is initial
siblings order by SalesOrgId ascending
)
{
key SalesOrgId,
ParentSalesOrg

}

This is where the magic happens. This hierarchy enables a recursive structure that can be rendered in Fiori Tree controls. 

 

Step 4: Projection View – ZVS_C_SALES 

This is the final consumption layer that will be exposed as OData. The hierarchy is referenced using the @OData.hierarchy.recursiveHierarchy annotation. 

@AccessControl.authorizationCheck: #NOT_REQUIRED
@EndUserText.label: ‘Projection View: Sales Organization’
@Metadata.ignorePropagatedAnnotations: true
@ObjectModel.usageType:{
serviceQuality:#X,
sizeCategory:#S,
dataClass:#MIXED
}
@Metadata.allowExtensions:true
@Search.searchable:true

@OData.hierarchy.recursiveHierarchy: [{ entity.name: ‘zvs_i_sales_hn’ }]
define view entity zvs_c_sales as select from zvs_i_sales
association of many to one zvs_c_sales as _Parent
on $projection.ParentSalesOrg = _Parent.SalesOrgId
{
key SalesOrgId,
@Search.defaultSearchElement: true
Name,
Region,
Country,
@Semantics.amount.currencyCode: ‘Currency’
Revenue,
Currency,
ParentSalesOrg,
/* Associations */
_Parent
}

Screenshot: 

Metadata extension: 

@Metadata.layer: #CORE
annotate entity zvs_c_sales with
{
@UI: {lineItem: [{ label: ‘Sales org ID’, position: 10 }],
identification: [{ label: ‘Sales org ID’, position: 10 }]
}
SalesOrgId;

@UI: {lineItem: [{ label: ‘Sales org Name’, position: 20 }],
identification: [{ label: ‘Sales org Name’, position: 20 }]
}
Name;

@UI: {lineItem: [{ label: ‘Region’, position: 30 }],
identification: [{ label: ‘Region’, position: 30 }]
}
Region;

@UI: {lineItem: [{ label: ‘Country’, position: 40 }],
identification: [{ label: ‘Country’, position: 40 }]
}
Country;

@UI: {lineItem: [{ label: ‘Revenue’, position: 50 }],
identification: [{ label: ‘Revenue’, position: 50 }]
}
Revenue;

@UI: {lineItem: [{ label: ‘Currency’, position: 60 }],
identification: [{ label: ‘Currency’, position: 60 }]
}
Currency;

@UI: {lineItem: [{ label: ‘Parent Sales org ID’, position: 70 }],
identification: [{ label: ‘Parent Sales org ID’, position: 70 }]
}
ParentSalesOrg;

}

Step 6: Service Binding – ZVS_C_SALES_ORG_V4 

If you will choose service binding type as V2, So you will get one error:

So select your Binding type as V4,

Now preview your application: 

Conclusion: 

Using CDS views and hierarchies in SAP S/4HANA is a simple and effective way to show the Sales Organization structure in a clear, tree-like format. It helps sales managers easily understand how different sales units are connected and how each one is performing. This setup is read-only, so the data stays safe, and it works well with Fiori apps for a smooth user experience. 

Overall, this approach makes reporting and analysis easier without needing a lot of custom coding. 

 

​ In this blog we will cover: Introduction, Architecture overview, Scenario, Procedure, Conclusion. Introduction: The CDS hierarchy in SAP ABAP is used to define recursive, tree-like relationships in data directly within Core Data Services (CDS) views. It allows structured, hierarchical data (like manager-employee, material categories, sales orgs, BOMs, etc.) to be represented and consumed easily in UI applications and analytics tools. In the RAP (RESTful ABAP Programming Model), a Tree View is used to visualize hierarchical (recursive) data structures in the UI—typically in Fiori Elements apps such as List Reports with tree tables. Tree View allows end users to navigate data in a parent-child format (e.g., managers → employees, sales org → region → country).├── Region North America │   ├── Country USA │   └── Country Canada └── Region Europe     ├── Country Germany     └── Country France To enable a Tree View in a RAP app: Model recursive data in a CDS view (e.g., employee-manager, sales org tree) Create a CDS hierarchy (define hierarchy) Use a C_ projection view to expose the hierarchy using:  @odata.hierarchy.recursiveHierarchy: [ { entity.name: ‘ZVS_I_SALES_ORG_HN’ } ] Add your entity to Service Definition and Service Binding Run the Fiori app (it will automatically detect and display a tree) Treeviews: Architecture Overview The implementation of a treeview in the ABAP RESTful Application Programming Model (RAP) requires different entities depending on whether the treeview should be read-only or editable. Architecture Overview: Read-Only Treeview   Architecture Overview: Read-Only Tree View in CDS To enable a read-only hierarchical display of data in the UI, the following CDS artifacts are used in combination: Database Table A custom database table holds the hierarchical data structure. Interface View This CDS view entity is built on top of the database table and defines the data model. It includes a self-association to represent the parent-child hierarchy within the same dataset. CDS Hierarchy A persistent CDS hierarchy is created using the DEFINE HIERARCHY statement. It provides a hierarchical interpretation of the interface view, enabling the framework to understand how records are nested. Projection View This view projects the interface view and incorporates the CDS hierarchy to expose the structured, hierarchical data as required by the UI. Service Definition and Service Binding These are created to expose the CDS projection view as an OData service. This step enables the consumption of hierarchical data in SAP Fiori or other UI frameworks. Architecture Overview: Editable Treeview with Draft  Editable Tree View with Draft Enablement – Architecture Overview To enable an editable tree view with draft functionality, the following key artifacts work together to define and expose the hierarchical data structure to the UI: Database table:Active and draft tables store the hierarchical data and hierarchy directory separately, supporting draft-enabled transactional scenarios. CDS view Entities (Interface Views):Interface views reference the underlying database tables and act as the first projection layer. The CDS view for the hierarchical data must include: A self-association to represent the parent-child relationship within the same entity (enabling hierarchy logic). A one-to-many association to link with the hierarchy directory entity. CDS Hierarchy:A persistent CDS hierarchy is defined using DEFINE HIERARCHY.It enables hierarchical interpretation for the data exposed by the first-layer CDS view. Base CDS views:These views enrich the model with compositional information. The hierarchy directory view acts as the composition root (parent). The hierarchical data view acts as the composition child. Behaviour Definition for base views:Defines transactional behavior, including: Draft capability Editing operations required by the UI. Projection views:Serve the consumption layer: For the hierarchy directory: A projection view supports transactional queries. For hierarchical data: A projection view combines interface view data with hierarchical logic using the @OData.hierarchy.recursiveHierarchy annotation (referring to the CDS hierarchy). Projection behaviour definition:Describes the behavior of projection views, allowing: Custom logic like determinations, validations, authorizations, numbering, etc. Service Definition and Service Binding:Finally, a service definition and binding are created to expose the hierarchy and its data structure to the UI layer via OData. ===========================================================================Scenario for Tree view in RAP: In large global companies, the Sales & Distribution (SD) module often reflects the company’s organizational structure. Typically, Sales Organizations are arranged in a multi-level hierarchy like this: This kind of structure helps companies manage sales performance, reporting, and operations more effectively. However, many systems don’t provide a read-only, easy-to-use view of this hierarchy — especially in a tree or drill-down format that users can easily navigate. In this blog, we’ll walk through how to model and expose this Sales Org hierarchy using CDS Hierarchies, and finally expose it through an OData service to be consumed in a Fiori UI. Procedure: Step 1: Define the Base Table – ZVS_DT_SALES This transparent table stores the core sales organization data including parent-child relationships. @EndUserText.label : ‘Hierarchy: Read Only: Sales Organization’
@AbapCatalog.enhancement.category : #NOT_EXTENSIBLE
@AbapCatalog.tableCategory : #TRANSPARENT
@AbapCatalog.deliveryClass : #A
@AbapCatalog.dataMaintenance : #RESTRICTED
define table zvs_dt_sales {

key client : abap.clnt not null;
key sales_org_id : abap.char(6) not null;
name : abap.char(50);
region : abap.char(20);
country : abap.char(3);
@Semantics.amount.currencyCode : ‘zvs_dt_sales.currency’
revenue : abap.curr(21,2);
currency : /dmo/currency_code;
parent_sales_org : abap.char(6);

}Note: parent_sales_org is a self-referencing field to represent the hierarchy. This table contain some records:  Step 2: Interface View – ZVS_I_SALES This CDS view represents the Sales Org data and defines a self-association to establish the parent-child link. @AbapCatalog.viewEnhancementCategory: [#NONE]
@AccessControl.authorizationCheck: #NOT_REQUIRED
@EndUserText.label: ‘Interface View: Sales Organization’
@Metadata.ignorePropagatedAnnotations: true
@ObjectModel.usageType:{
serviceQuality: #X,
sizeCategory: #S,
dataClass: #MIXED
}
define view entity zvs_i_sales as select from zvs_dt_sales
association to zvs_i_sales as _Parent on
$projection.ParentSalesOrg = _Parent.SalesOrgId
{
key sales_org_id as SalesOrgId,
name as Name,
region as Region,
country as Country,
@Semantics.amount.currencyCode: ‘Currency’
revenue as Revenue,
currency as Currency,
parent_sales_org as ParentSalesOrg,

_Parent
}Step 3: Define Hierarchy – ZVS_I_SALES_HN Using CDS hierarchy syntax, we now define a parent-child recursive hierarchy. @EndUserText.label:’Sales Organization Hierarchy’

define hierarchy zvs_i_sales_hn
as parent child hierarchy (
source zvs_i_sales
child to parent association _Parent
start where ParentSalesOrg is initial
siblings order by SalesOrgId ascending
)
{
key SalesOrgId,
ParentSalesOrg

}This is where the magic happens. This hierarchy enables a recursive structure that can be rendered in Fiori Tree controls.  Step 4: Projection View – ZVS_C_SALES This is the final consumption layer that will be exposed as OData. The hierarchy is referenced using the @OData.hierarchy.recursiveHierarchy annotation. @AccessControl.authorizationCheck: #NOT_REQUIRED
@EndUserText.label: ‘Projection View: Sales Organization’
@Metadata.ignorePropagatedAnnotations: true
@ObjectModel.usageType:{
serviceQuality:#X,
sizeCategory:#S,
dataClass:#MIXED
}
@Metadata.allowExtensions:true
@Search.searchable:true

@OData.hierarchy.recursiveHierarchy: [{ entity.name: ‘zvs_i_sales_hn’ }]
define view entity zvs_c_sales as select from zvs_i_sales
association of many to one zvs_c_sales as _Parent
on $projection.ParentSalesOrg = _Parent.SalesOrgId
{
key SalesOrgId,
@Search.defaultSearchElement: true
Name,
Region,
Country,
@Semantics.amount.currencyCode: ‘Currency’
Revenue,
Currency,
ParentSalesOrg,
/* Associations */
_Parent
}Screenshot: Metadata extension: @Metadata.layer: #CORE
annotate entity zvs_c_sales with
{
@UI: {lineItem: [{ label: ‘Sales org ID’, position: 10 }],
identification: [{ label: ‘Sales org ID’, position: 10 }]
}
SalesOrgId;

@UI: {lineItem: [{ label: ‘Sales org Name’, position: 20 }],
identification: [{ label: ‘Sales org Name’, position: 20 }]
}
Name;

@UI: {lineItem: [{ label: ‘Region’, position: 30 }],
identification: [{ label: ‘Region’, position: 30 }]
}
Region;

@UI: {lineItem: [{ label: ‘Country’, position: 40 }],
identification: [{ label: ‘Country’, position: 40 }]
}
Country;

@UI: {lineItem: [{ label: ‘Revenue’, position: 50 }],
identification: [{ label: ‘Revenue’, position: 50 }]
}
Revenue;

@UI: {lineItem: [{ label: ‘Currency’, position: 60 }],
identification: [{ label: ‘Currency’, position: 60 }]
}
Currency;

@UI: {lineItem: [{ label: ‘Parent Sales org ID’, position: 70 }],
identification: [{ label: ‘Parent Sales org ID’, position: 70 }]
}
ParentSalesOrg;

}Step 6: Service Binding – ZVS_C_SALES_ORG_V4 If you will choose service binding type as V2, So you will get one error:So select your Binding type as V4,Now preview your application: Conclusion: Using CDS views and hierarchies in SAP S/4HANA is a simple and effective way to show the Sales Organization structure in a clear, tree-like format. It helps sales managers easily understand how different sales units are connected and how each one is performing. This setup is read-only, so the data stays safe, and it works well with Fiori apps for a smooth user experience. Overall, this approach makes reporting and analysis easier without needing a lot of custom coding.    Read More Application Development and Automation Blog Posts articles 

#SAP

You May Also Like

More From Author