Supply Chain Management Blogs by Members
Learn about SAP SCM software from firsthand experiences of community members. Share your own post and join the conversation about supply chain management.
cancel
Showing results for 
Search instead for 
Did you mean: 
murali_manohar
Participant

Hello SAPians,

In this Blog post, I would like to take you through the concept of MDOs in SAP MII where, I would like to provide the step-by-step process to create a MDO object (as a data table) and use the MDO object to perform different types of CRUD operations and also create a SAP Ui5 Application which consumes the MDO queries to manipulate the data using different functions and deploy the application in SAP MII.

So, let's start with What is a MDO and why should we use an MDO in our applications?

An MDO is a semantic layer and level of abstraction on top of SAP MII data acquisition mechanisms, such as query templates & transactions.

There are two types of MDOs that can be configured such as:

1. Persistent MDO - when the data provider for the object is executed, the system persists the data that is returned.

2. On-Demand MDO - when the data provider for the object is executed, the data is not persisted. Instead, the data is returned from the data source in the real-time.

MDO is tightly coupled with your MII content and it is even defined inside of the MII Workbench along with the rest of your MII content. It also has a lifecycle tied to it which means that the definition for the management of its data is also part of the object definition which simplifies the complexity of the data management.
The MDO object still related one to one with a table in the NetWeaver database and will scale to whatever size the underlying NetWeaver database allows you to but it will not allow you to setup primary & foreign key dependencies, triggers, sequences, or anything else that Open SQL does not support.

you can get to more about the SAP MDO from the SAP MII help portal

Now, let's see how to create a MDO object, define the attributes and develop necessary CRUD operation queries using the MDO object.

Below are the URLs to use the MDO queries as web services and consume them in different places (be it in a SAP Ui5 web applications)

1. Insert Data:
           http://<server>:<port>/XMII/Illuminator?QueryTemplate=<YourInsertQueryPath>&Param.1=<value>&Param.2=...

2. Update Data: 
          http://<server>:<port>/XMII/Illuminator?QueryTemplate=<YourUpdateQueryPath>&Param.1=<value>&Param.2=...

3. Delete Data: 
          http://<server>:<port>/XMII/Illuminator?QueryTemplate=<YourDeleteQueryPath>&Param.1=<value>

4. Retrieve Data:
          http://<server>:<port>/XMII/Illuminator?QueryTemplate=<YourSelectQueryPath>

As we are ready with our requires MDOs queries, let's start creating a SAP Ui5 web application in VS code/BAS Tool(easier in VScode/BAS Tool when compared to Developing a web application in SAP MII workbench)

As we know, SAP Ui5 application follows MVC architecture, we develop application using Model, View & controller in the application. The project structure would be as follows:

murali_manohar_2-1715702349619.png

In this application, we are embedding the model within the controller itself i.e where we are consuming the MDO queries as web services. Hence, there is no Model folder/File here. For full fledged SAP ui5 application, please follow the SAP Ui5 guidelines for developing the web application.

Now, let's start developing a Web application which consumes the following MDO queries and display the data in the tabular format.

The below is the ui5 web application demo using MDOs & corresponding MDO queries created in SAP MII as data source for the web application

Below is the code snippet that is responsible for achieving the above web application.

index.html

 

 

<html>
    <head>
        <script src="https://ui5.sap.com/1.122.0/resources/sap-ui-core.js"
                 data-sap-ui-libs="sap.m"
                 data-sap-ui-theme="sap_belize_plus"
                 data-sap-ui-resourceroots='{
                    "am":"./"
                 }'
                 data-sap-ui-bindingSyntax="complex">
        </script>
        <script>
            var oView=new sap.ui.view({
                id:"xmlV",
                viewName:"am.view.view1",
                type:"XML"
            });
           oView.placeAt("uiHere");
            
        </script>
    </head>
    <body class="sapUiBody">
        <div id="uiHere"></div>
    </body>
</html>

 

 

Here, in the index.html we are performing the bootstrap with SAP Ui5 libraries and creating a view objects which pulls the all the ui elements defined in the view code and places the Ui elements in the division tag of the body.

Main.view.xml

 

 

<mvc:View xmlns:mvc="sap.ui.core.mvc" 
          xmlns="sap.m"
          xmlns:f="sap.ui.layout.form"
          xmlns:t="sap.ui.table"
          xmlns:c="sap.ui.core"
          xmlns:f1="sap.f"
        controllerName="am.controller.Main">
        <Page title="Employee Data">
            <f:SimpleForm backgroundDesign="Solid"  editable="true" id="simpleForm">

                <Label text="Employee Name" labelFor="EmpName" />
                <Input id="EmpName" required="true" width="30%" />

                <Label text="Employee ID" labelFor="EmpId" />
                <Input id="EmpId" required="true" width="30%" />

                <Label text="Gender" labelFor="Gen" />
                <Input id="Gen" required="true" width="30%" />

                <Label text="Age" labelFor="Age" />
                <Input id="Age" required="true" width="30%" />

                <Label text="Salary" labelFor="sal" />
                <Input id="Sal" required="true" width="30%" />

                <Label text="Designation" labelFor="Des" />
                <Input id="Des" required="true" width="30%" />

                <Label text="Location" labelFor="Loc" />
                <Input id="Loc" required="true" width="30%" />

            </f:SimpleForm>

            <Toolbar>
                <Button text="Insert New Employee" press="insertEmp"></Button>
          
                <Button text="Update Employee Record" press="updateEmp"></Button>
          
               <Button text="Delete Employee" press="deleteEmp"></Button>

                <Button  icon="sap-icon://synchronize"  press="refresh" ></Button>
                <Button icon="sap-icon://clear-all"  press="clearAllFields" ></Button>
            </Toolbar>

            <f1:DynamicPage>
                <f1:content>
                    <t:Table id="emptab" selectionMode="Single" rows="{SEModel>/Rowsets/Rowset/0/Row}">
                        <t:extension>
                            <OverflowToolbar style="Clear">
                                <Title text="Employee Records" textAlign="Center"/>
                            </OverflowToolbar>
                        </t:extension>
                        <t:columns>
                            <t:Column width="11rem">
                                <Label text="Employee Name" />
                                <t:template>
                                    <Text text="{SEModel>EmpName}" wrapping="false" />
                                </t:template>
                            </t:Column>
                            <t:Column width="11rem">
                                <Label text="Employee ID" />
                                <t:template>
                                    <Text text="{SEModel>EmpID}" wrapping="false" />
                                </t:template>
                            </t:Column>
    
                            <t:Column width="9rem">
                                <Label text="Gender" />
                                <t:template>
                                    <Text text="{SEModel>Gender}" wrapping="false" />
                                </t:template>
                            </t:Column>
                            <t:Column width="9rem">
                                <Label text="Age" />
                                <t:template>
                                    <Text text="{SEModel>Age}" wrapping="false" />
                                </t:template>
                            </t:Column>
                            <t:Column width="7rem">
                                <Label text="Salary" />
                                <t:template>
                                    <Text text="{SEModel>Salary}" wrapping="false" />
                                </t:template>
                            </t:Column>
    
                            <t:Column width="11rem">
                                <Label text="Designation" />
                                <t:template>
                                    <Text text="{SEModel>Designation}" wrapping="false" />
                                </t:template>
                            </t:Column>
    
                            <t:Column width="11rem">
                                <Label text="Location" />
                                <t:template>
                                    <Text text="{SEModel>Location}" wrapping="false" />
                                </t:template>
                            </t:Column>
    
                        </t:columns>
                    </t:Table>
                </f1:content>
            </f1:DynamicPage>
        </Page>
</mvc:View>

 

 

In View code, we have we have placed all the necessary input fields and a table to display the data, we can bind the data using different binding modes such as 

  1. Property Binding
  2. Expression Binding
  3. Aggregation Binding
  4. Element Binding

Here, i have used property binding to display the employee details in the table.

Main.controller.js

 

 

sap.ui.define([
    'sap/ui/core/mvc/Controller'
,
    'sap/ui/model/json/JSONModel'
    ],function(oCon,JSONModel) {

    'use strict';
    return oCon.extend("am.controller.Main",{
            
        onInit:function(){
	var SEModel=new JSONModel("/XMII/Illuminator?QueryTemplate=<Path>/SelectEmpData&Content-Type=text/json");
            this.getView().setModel(SEModel,"SEModel");
        },
	refresh:function(){
            var SEModel=new JSONModel("/XMII/Illuminator?QueryTemplate=<Path>/SelectEmpData&Content-Type=text/json");
            var E=this.getView().setModel(SEModel,"SEModel");
            return E;
            sap.m.MessageToast.show("Data Refreshed!",{
                duration:2000,
                width:"55em",
            });
        },
        insertEmp:function(){
            var empName=this.getView().byId("EmpName").getValue();
            var empId=this.getView().byId("EmpId").getValue();
            var gen=this.getView().byId("Gen").getValue();
            var age=this.getView().byId("Age").getValue();
            var sal=this.getView().byId("Sal").getValue();
            var des=this.getView().byId("Des").getValue();
            var loc=this.getView().byId("Loc").getValue();
            
            if(empName==""||empId==""||gen==""||age==""||sal==""||des==""||loc==""){
                sap.m.MessageToast.show("please enter all the fields to create an Employee record!!",{
                    duration:2000,
                    width:"55em",
                });
            }
	else{
            	var IEModel= new JSONModel("/XMII/Illuminator?QueryTemplate=<Path>/InsertEmpData&Param.1="+empName+"&Param.2="+empId+
"&Param.3="+gen+"&Param.4="+age+"&Param.5="+sal+"&Param.6="+des+"&Param.7="+loc);
            	this.getView().setModel(IEModel,"IEModel");
		sap.m.MessageToast.show("New Employee record created successfully!!!",{
                   		 duration:2000,
                   		 width:"55em",
               	 });
	}
        },
        updateEmp:function(){

            var empId=this.getView().byId("EmpId").getValue();
            var sal=this.getView().byId("Sal").getValue();
            var des=this.getView().byId("Des").getValue();
            var loc=this.getView().byId("Loc").getValue();
            
            if(empId==""||sal==""||des==""||loc==""){
                sap.m.MessageToast.show("please enter Employee ID, Salary, Designation & Location to update a Employee record!!",{
                    duration:2000,
                    width:"55em",
                });
            }
            var UEModel= new JSONModel("/XMII/Illuminator?QueryTemplate=<Path>/UpdateEmpData&Param.1="+empId+"&Param.2="+sal+"&Param.3="+des+"&Param.4="+loc);
            this.getView().setModel(UEModel,"UEModel");
            sap.m.MessageToast.show("Employee Record Updated Successfully!!",{
                duration:2000,
                width:"55em",
            });
        },
        clearAllFields:function() {
            this.getView().byId("EmpName").setValue("");
            this.getView().byId("EmpId").setValue("");
            this.getView().byId("Gen").setValue("");
            this.getView().byId("Age").setValue("");
            this.getView().byId("Sal").setValue("");
            this.getView().byId("Des").setValue("");
            this.getView().byId("Loc").setValue("");
        },
        deleteEmp:function(){
	var empId=this.getView().byId("EmpId").getValue();
            if(empId==""){
                sap.m.MessageToast.show("please enter Employee ID to delete an Employee record!!",{
                    duration:2000,
                    width:"55em",
                });
            }
            var UEModel= new JSONModel("/XMII/Illuminator?QueryTemplate=<Path>/DeleteEmpData&Param.1="+empId);
            this.getView().setModel(UEModel,"UEModel");
            sap.m.MessageToast.show("Employee Record deleted Successfully!!",{
                duration:2000,
                width:"55em",
            });
        }
    });
});

 

 

In controller code, we have defined the functions to trigger an event whenever a button is clicked and create a named JSON model and loaded the model using the illuminator services of the MDO queries created earlier.

once the application is developed, we need to create a manifest.json file within the webapp folder, which is an application description file holds the application properties such as application type, id, etc..

Manifest.json

 

 

{
    "sap.app":{
        "id":"MDOapp",
        "type":"application"
    }
}

 

 

you can find more information on Application descriptor file here 

once all the above files are developed, you can create the ui5 web project by following the below guidelines: 

Note: The following commands has to be executed within the project but outside webapp folder

  • Initiate a node project using npm init  in the terminal of VScode/BAS tool - this should create a package.json file in the project folder.
  • now, we initiate a ui5 project using ui5 init - this should create a ui5.yaml file 
  • you can now test the project by using the command ui5 serve -o index.html which open the ui5 web application in the browser without any errors and your application will be displayed on the browser.

Deployment of SAP Ui5 App in SAP MII:

  • once the ui5 application is built using the above guidelines, export the code from VS Code/BAS Tool to a project specific location.
  • now open SAP MII workbench and navigate to the Web Tab of SAP MII project where you want to deploy the application.
  • Right click on the project --> import --> select the Ui5 project folder --> open. Now the application is deployed in the SAP MII.
  • For Testing, open the project --> web app folder --> right click on index.html(basically landing page of the application) copy url and open it in browser, your sap ui5 application should load without any issue.
  • or, you can test by opening the index.html file and click on test icon on the top-right of MII Menu bar.

I hope, this blog provides you the basic knowledge of creation of MDO objects, queries and its consumption in a SAP Ui5 application. Please do let me know if you have any queries or suggestions.

Note:  Please note that this is a basic SAP Ui5 application to demonstrate the usage of MDO objects and queries in SAP MII.

Thank You!

*VSCode - Visual Studio Code
*BAS - Business Application Studio
*MDO - Manufacturing Data Objects

 

Labels in this area