Technical Articles
Build and deploy a CAP Project Node.js API with a SAP Fiori Elements UI and a managed approuter configuration
In this post, I’m going to show how a SAP Cloud Application Programming Model (CAP) application can be generated and deployed to the Cloud Foundry environment of SAP BTP, leveraging the Application Wizards currently on SAP Business Application Studio.
Prerequisites:
- You’ll need an SAP Business Technology Platform (SAP BTP) trial account
- You are subscribed to SAP Business Application Studio, follow this tutorial for more information
- You are subscribed to the SAP Launchpad Service, follow this tutorial for more information
- You are subscribed to SAP HANA Cloud service, SAP HANA Cloud database is setup and running in your cloud space, refer to this tutorial for more information
- If the referenced services are not available in Service Marketplace, please select Entitlements from the root of your subacacount, select Configure Entitlements, locate the required service, create it, save it and then return to the Service Marketplace to add the required service to your subaccount.
Turn up the tunes, get yourself some water and lets rock n’roll…
Step 1. Create Dev Space
From your SAP BTP cockpit, select Instances and Subscriptions, select SAP Business Application Studio which will open a new tab into your dev space manager. Generate a Full Stack Cloud Application dev space with SAP HANA Tools enabled.
Full Stack Dev Space
Dont like the theme? Change the theme colour if you like! For more advanced customisation techniques, check out this video.
Step 2. Generate an Application Programming Model Node.js Project
There are two ways to generate the project;
- Using the Core Data Services (CDS) cli
- Application Wizard
For the remaining steps, it’s assumed the application programming model project is called managedAppCAPProject (Catalog API) and the SAP Fiori application is called feproject-ui (Catalog UI).
To generate using CDS cli, open a new terminal window and execute the following steps;
cds init managedAppCAPProject
cd managedAppCAPProject/
cds add samples
cds add hana
cds add mta
npm install
cds build --for hana
cp gen/db/package.json db
Or if you want to run it all together;
cds init managedAppCAPProject && cd managedAppCAPProject && cds add samples && cds add hana && cds add mta && npm install && cds build --for hana && cp gen/db/package.json db
If you used the template generator, open a terminal window from the root of your project and execute;
cds build --for hana && cp gen/db/package.json db
In both cases, you should end up with a generated application programming model project and a skeleton multi target configuration with SAP HANA Project view enabled.
Application Programming Model Project with SAP HANA Projects View
Step 3. Configure managed approuter configuration
Right click mta.yaml and select Create MTA Module from Template
– Select Approuter Configuration
– Select your HTML5 application runtime – select Managed Approuter
– Unique name – managedRouterCapProject
– Do you plan to add a UI? – Yes
– Select Next
You now have an application programming model project created!
Stpe 4. Modify and validate your local setup
In your project root, open the file srv/cat-service.cds, add new UI annotations, as shown;
using my.bookshop as my from '../db/data-model';
service CatalogService {
@readonly entity Books as projection on my.Books;
}
// New UI annotations
annotate CatalogService.Books with @(
UI : {
SelectionFields : [
title
],
LineItem : [
{ Value : ID },
{ Value : title },
{ Value : stock }
],
}
){
ID @( title: 'ID' );
title @( title: 'Title' );
stock @( title: 'Stock' );
};
At this stage, lets ensure everything is working;
- There are no local build issues
- We can preview the application programming model project and is responding and using an in-memory database
Open a new terminal window and ensure you are the root of your project /home/user/projects/managedAppCAPProject, run cds watch to validate everything is working correctly, a new browser tab will open for you to validate the metadata and service calls exposed by your new application programming model project.
– If the default port 4004 is already open and you want to see what is bound to it, select View -> Find Command -> Ports Preview
– If you cannot kill the port, open the project package.json and append the port flag to the start script, for example: “start”: “cds run –port 4003”, now run npm run start again
Congratulations…
Application Programming Model Project
Challenge one! Follow this tutorial on how to use SAP Hana Cloud HDI instances during local development, switching from SQLite to SAP HANA Cloud. Remember, your application should already be configured with SAP HANA Cloud so all you need to change is the package.json with the new CDS settings.
Also, if you want to extend the capability of your CDS model, here is a sample repo for reference Book Example.
Step 5. Add SAP Fiori Elements UI
Right click mta.yaml again and select Create MTA Module from Template
– Select SAP Fiori Application
– Select your application type and floor plan, in this case select SAP Fiori Elements -> List Report Object page and select Next
– Select Use a Local CAP Project and point to your new application programming model project -> managedAppCAPProject
– Select default OData Service -> CatalogService (Node.js)
– Select Next
– Select Books as the Main entity
– Enter a unique module name -> feproject-ui
– Enter an application namespace -> cap.tutorial
– Select Add deployment configuration to MTA project – Yes (will default to yes as the mta.yaml was detected in the project path)
– Additional Options can remain as No
– Select Next
– Select Please choose the target – Cloud Foundry
– Select Local CAP Project API (Instance Based Destination) for your Destination Name
Application Programming Model OData Service
SAP Fiori Elements Project Attributes
Destination Selection
You will now have a new SAP Fiori application generated inside your application programming model project. The HTML5 SAP Fiori applcation has been appended to your mta.yaml, please refer to the module called captutorialfeprojectui, as shown;
- name: captutorialfeprojectui
type: html5
path: app/feproject-ui
build-parameters:
build-result: dist
builder: custom
commands:
- npm install
- npm run build:cf
supported-platforms: []
Remember! You can re-run the SAP FIori template generator as shown above, multiple times, adding different UI’s to suit your needs.
If you previously had executed cds watch, then refresh your browser tab and you will now see the SAP Fiori web application listed; if not, just re-run cds watch from a terminal window;
SAP Fiori Elements Web Application Listed
Select the SAP Fiori web application, select the default tile and your application should render. If no data is being shown, tweak the Adapt Filters and the settings (cog icon) to select which values you want displayed.
SAP Fiori Web Application
Your CAP project with a Fiori UI application is now ready to be built and deployed to CF.
Step 6. Are we done? Not if you selected None as the destination name…
If you selected None as the destination name for the CF target system, then you have some manual work todo! As result, we have to make a manual change to mta.yaml and the Fiori application.
Open app/feproject-cap/xs-app.json, add the following route, ensuring its the first in the list;
{
"authenticationType": "none",
"csrfProtection": false,
"source": "^/catalog/",
"destination": "cap-catalog-api"
},
What is going on here? When deployed to CF, xs-app.json handles the URL routing of the Fiori application. All calls starting with a catalog request, for example catalog/$metadata?sap-language=EN will be intercepted by the this route handler and forwarded to the destination cap-catalog-api to retrieve the OData service. Also, notice the authenticationType is set to none, which means the catalog API is public!!! This is important, it means you now have a public facing endpoint! Be careful!
Challenge two! Follow this tutorial to lock down the catalog API using xsuaa
But where does the cap-catalog-api destination come from? During the SAP Fiori application setup, we were prompted to select a CF destination, we selected None! In this case, we need to create a destination so that the SAP Fiori application, when deployed to CF can retrieve the OData service from the application programming model project.
Going off topic slightly here but an instance based destination differs to a subacacount destination. For example, if you return to your SAP BTP cockpit, select your subaccount and then select Destinations under the Connectivity tab, you will see subaccount destinations. These destinations are availabe to all applications deployed to the same CF space and are external endpoints, that contain connection details for the remote communication of an application. For a deeper dive into destinations, please follow this link.
The next task is to create a destination to expose the application programming model project as an endpoint to allow the SAP Fiori application consume the exposed OData service BUT this endpoint is only available to applications that are bound to our multi target application.
Open mta.yaml and make the following changes;
Find managedAppCAPProject-destination-service and locate the existing destinations list, append a new destination called cap-catalog-api. Ensure the indentation is aligned with the existing destination, this will allow communication between the application programming model project and SAP Fiori application when deployed to CF;
- Authentication: NoAuthentication
Name: cap-catalog-api
ProxyType: Internet
Type: HTTP
URL: ~{srv-api/srv-url}
HTML5.DynamicDestination: true
HTML5.ForwardAuthToken: true
Again, in managedAppCAPProject-destination-service append the following root node called requires, this should be aligned with type and parameter.
At the end you should have the following configuration;
- name: managedAppCAPProject-destination-service
type: org.cloudfoundry.managed-service
requires:
- name: srv-api
parameters:
config:
HTML5Runtime_enabled: true
init_data:
instance:
destinations:
- Authentication: NoAuthentication
Name: ui5
ProxyType: Internet
Type: HTTP
URL: https://ui5.sap.com
- Authentication: NoAuthentication
Name: cap-catalog-api
ProxyType: Internet
Type: HTTP
URL: ~{srv-api/srv-url}
HTML5.DynamicDestination: true
HTML5.ForwardAuthToken: true
existing_destinations_policy: update
version: 1.0.0
service: destination
service-name: managedAppCAPProject-destination-service
service-plan: lite
Step 7. Job done! Ready for deployment!
Your project structure should look like this;
Project Structure
Right click your mta.yaml and select Build MTA Project. Open the mta_archives folder, right click the generated mtar file and select Deploy MTA Archive, if you are not logged into CF, it will prompt you todo so.
CF Deployment Success
Remember, any modifications made locally, will require you to build and redeploy the mta project to CF for the changes to be reflected on CF.
ERROR ERROR ERROR If the appropriate hdi-shared service plan is not configured on your account, the deployment will fail but will give you the exact reason. Review your mta.yaml, specifically the managedAppCAPProject-db and update the service from hana to hanatrial. However, in most cases, it’s the database is not running on your CF space that is the cause! For more info, follow this link to either restart the service instance locally or via SAP BTP cockpit.
Step 8. Validate your deployment
You have two options to retrieve the URL of the deployed HTML5 application, open a terminal window and execute the following command;
cf html5-list -u -di managedAppCAPProject-destination-service -u --runtime launchpad
Select the clickable endpoint, when opened, your SAP Fiori UI application will be displayed.
Alternatively, login to your SAP BTP subaccount, select HTML5 Applications from the left navigation tab and select your new SAP Fiori application;
SAP BTP Fiori Application
Last challenge! Do you want to support SAP Launchpad Service? Open a terminal window, change into your SAP Fiori application /home/user/projects/managedAppCAPProject/app/feproject-ui and run the following command;
npx -p @sap/ux-ui5-tooling fiori add flp-config
Semantic Object is a unique business entity within your SAP Launchpad site, in this case MyCAPProject
Action is display
All other fields are optional.
FLP Settings
The only change made is to your manfiest.json where a new node crossNavigation is added, containing all the entered values. Rebuild and redeploy and follow this tutorial on how to consume the SAP Fiori application in your Launchpad site.
Tips
Tip 1. There are always some improvements we can make! If you have other applications deployed in your CF space and are tight for space and memory, then you can append the following attributes to any running application;
memory: 256M
disk-quota: 1024M
For example, you can update the managedAppCAPProject-srv module as follows;
- name: managedAppCAPProject-srv
type: nodejs
path: gen/srv
requires:
- name: managedAppCAPProject-db
provides:
- name: srv-api
properties:
srv-url: ${default-url}
parameters:
buildpack: nodejs_buildpack
memory: 256M
disk-quota: 1024M
build-parameters:
builder: npm-ci
Tip 2. If you want to handle different CDS environments, for example, to be able to run SQLite in development or SAP HANA Cloud in production, then you can use CDS profiles. Take a look at the CDS ENV profiles page.
Tip 3. If you are using SAP Business Application Studio as your development environment and want to support XSUAA for local testing, append the jwt-auth configuation to your package.json, take a look at the XSUAA Hybrid Setup for more information.
"requires": {
"db": {
"kind": "hana"
},
"uaa": {
"kind": "xsuaa"
},
"auth": {
"kind": "jwt-auth"
}
}
Related Blogs
- https://blogs.sap.com/2022/01/14/designing-ui5-apps-for-sap-launchpad-service-part-1/
- https://blogs.sap.com/2020/12/15/deploying-a-cap-based-fiori-app-to-a-central-launchpad/
- https://blogs.sap.com/2021/01/11/create-an-sap-fiori-elements-ui-for-cap-node.js-applications-in-sap-business-application-studio/
Conclusion
Your first application programming model project with a SAP Fiori Elements UI using a managed approuter is now live!
I would suggest following the challenge links as they will provide more details how to configure HDI instances and especially, to lock down your application using xsuaa!
Complete github repo of the project is available along with the associated challenges, recently updated with Node v16 support https://github.com/SAP-samples/fiori-tools-samples/tree/main/cap/cap-fiori-mta.
I would suggest following up with any questions on the SAP Community topic page for SAP Fiori.
Hope you enjoyed this tutorial.
Thank you John. This is one complete tutorial/blog post.
Thank you John.
One question. While I try to perform all the steps, on right click to mta.yaml file > Create MTA Module from Template, I do not see Approuter Generator in BAS. I am using trail version.
Could you please help me what should I do then?
Thanks
Sheetal
Just to confirm, you dont see the Approuter Configuration as shown in the screenshot?
Of if this is not available via yeoman CLI i.e. open a new terminal window, type yo, there should be a Routing Config option.
If you dont have these options then you have created a basic dev space. Please re-create the dev space with Sap Fiori or Full stack options.