Skip to Content
Author's profile photo Fabian Lehmann

How to build an IoT app on top of SAP Cloud Platform IoT Application Enablement

Introducing

In this blog i want to continue the little walktrough which we´ve started last month about SAP Cloud Platform IoT service in combination with SAP Cloud Platform IoT Application Enablement:

Scenario Architecture

In the picture below you can see we´ve still connect our device to SAP Cloud Platform IoT services (1) and we´ve successfully build up the virtual(digital) twin of our device (2).

We want now start to develop a little app in the “neo” environment wit the SAP Web IDE (3) by the usage of the SAP IoT AE API´s:

Update/Change

As you can see in this blog by Lukas Brinkmann we´re now able to send commands from SAP CP IoT AE to IoT service an finally to our device.

Please check the “Release Notes” here for a little change of the “attribute type”:

A final example of an adjusted configuration can be found in my GitHub repository here

Futhermore you can find a python based prgramm (runs on your local pc or an Raspberry PI) which use publish/subscribe with MQTT here:

https://github.com/fableh/iot_python_scripts

If u execute the script and fire a command back to the device:

 …. we can now also se these commands in the console if we succesfully subsribed to the mqtt topic:

For more examples please visit also the SAP IoT Starte Kit, especially for the “Cloud Foundry” ennvironment for a lot of more examples:

https://github.com/SAP/iot-starterkit/tree/master/cf

 

IoT App development with SAP Web IDE Full Stack

Prerequisite: Before we can satrt the the development we need to check/create some destinations in the “neo” environment, These destinations are required to access the “iot data” from the “cloud foundry” environment. The setup of these destination is part of the onboarding process of your SAP CP IoT AE tenant.

A detailed documentation about the config can be found here.

After we have checked the destinations we can now execute the “SAP Web IDE Full Stack” in our SAP Cloud Platform Neo Environment.

For the usage of the SAP CP IoT Application Enablement features/templates you need to enable this as described here.

Now we can create a new template based “IoT Application” by using the wizard:

Afterwards we define teh basic information for our app:

Project Name CPU_usage
Namespace syc.iot.notebooks
Titel MyApp

 

 

Reference to the OData destination, which allows us to fetch the “Thing Data”:

Afterwards we can now search our property set(s):

In upcomming next screens we can now first decide which views we want to have in our app (we choose here all):

And finally we have now the chance to define for each view which properties we want to display:

After we run the application for a first test we got the following result:

But if we now want to click on our “Thing” to locate it in the map, something is missing.

Based on this it´s required to enhance our thing with some additional data.

Enhance the “Thing Data”

To specify the “location” of our thing we have two options one via the “Thing Modele Application” or via the “SAP CP IoT AE API´s”:

UI:

The API way (my choice);

 

Fetch the CSRF token

First of all we need to Fetch the CSRF Token and setting this globally in our Postman Environment:

URL: https://{{tenant_id}}.iot-sap.cfapps.eu10.hana.ondemand.com/appiot-mds/Things

Maintain your “Postman Environment” for SAP CP IoT AE:

Create the Location
URL: https://{{tenant_id}}.iot-sap.cfapps.eu10.hana.ondemand.com/location/Locations
{
	"basicData": {
		"tenant" : "<TENANT ID>"
	},
	"locationData": {
				"streetName": "Heinrich-von-Stephan-Straße",
                "houseNumber": "1-5",
                "cityName": "Göttingen",
                "postalCode": "37073",
                "country": "DE",
                "countryDescription": "Germany",
                "longitude": 9.92829,
                "latitude": 51.53708
	}
}

Response (Location ID):

https://location.cfapps.eu10.hana.ondemand.com/Locations('3C8C03C00CDE451092E293EDDF22489F')
Create the “Business Partner” for the Thing
URL: https://{{tenant_id}}.iot-sap.cfapps.eu10.hana.ondemand.com/tenant/Persons
{
	"person": 
	{
		"basicData": {
        	"tenant": "<TENANT ID>",
        	"etag": "1"
    	},

		"personName": {
                "formOfAddress": "0002",
                "formOfAddressDescription": "Mr.",
                "familyName": "Lehmann",
                "givenName": "Fabian"
            },
            "communicationData": {
                "emailAddress": "fabina.lehmann@sycor.de",
                "mobilePhoneNumber": "+49111111111",
                "landlinePhoneNumber": "+49222222222",
                "streetName": "Heinrich-von-Stephan-Straße 1-5  ",
                "cityName": "Göttingen",
                "postalCode": "37073 ",
                "country": "DE",
                "countryDescription": "Germany",
                "region": "03",
                "regionDescription": "Lower Saxony",
	},
		"objectGroup": "<object group>"
	},

"employingOrganization": 
	{
		"businessPartnerID": "<organization id>"
	},
	
	"userActive":"true"
}

Response (Person ID):

https://tenant-administration.cfapps.eu10.hana.ondemand.com/Persons('9E1B3941B70E47338276B3E4C9F1220D')

 

Update the Thing with the location and person id
URL: https://{{tenant_id}}.iot-sap.cfapps.eu10.hana.ondemand.com/appiot-mds/Things('442414166D8D4F79B809054EBE3B45C4')
  {
            "_id": "442414166D8D4F79B809054EBE3B45C4",
            "_externalId": "FabiansZBook",
            "_alternateId": "ZBook",
            "_name": "FabiansZBook",
            "_description": {
                "en": "FabiansZBook"
            },
            "_thingType": [
                "iotae.sycor.syc.sap.blogs.notebooks:ZBook"
            ],
            "_location": "3C8C03C00CDE451092E293EDDF22489F",
            "_customer": "9E1B3941B70E47338276B3E4C9F1220D",
            "_objectGroup": "D34AF712DFD34A77A92E9A26652D227E"
   }
        

 

Check the result in the SAP Web IDE “preview”

If we now enter the application again, we can see that our device is now located as defined and has assigned our “Person” as “Contact Info”:

We can now enter the different screens to see more details:

 

Summary

As u can see with SAP IoT Application Enablement, it´s really easy to develop an IoT App to visulaize your “Thing Data”. Futhermore we´ve seen how we can enhance our Thing with additional data e.g. from core applications like S/4 HANA.

In the next blog we want to cover the follwoing

  • Deploy the app to “SAP Cloud Platform Cloud Foundry Environment”.
  • Developing an second application were we visualize routes on the map.
  • Creating events via the SAP CP IoT Application Enablement API.

 

Some links

SAP Cloud Platform Application Enablement

What´s new in SAP Application Enablement

SAP CP IoT AE – Reuse Controls and Templates

IoT Application Projects in SAP Web IDE

SAP IoT Starter Kit on GitHub

Used python script to send and retrieve data

 

cheers,

Fabian

 

 

Assigned Tags

      13 Comments
      You must be Logged on to comment or reply to a post.
      Author's profile photo Venu Ravipati
      Venu Ravipati

      Hi Fabian,

      Thank you for writing these wonderful blogs. Waiting for other blogs in this series.

      I do not know if this question is answered already, but want to know what is the best way to combine SAP IoT Application Enablement Thing data with SAP S/4HANA data?

      can we do this in SAP IoT Application Enablement Thing Modeler? or in SAP Web IDE?

      Could you please share some insights?

      Thank you and Best Regards,

      Venu

      Author's profile photo Fabian Lehmann
      Fabian Lehmann
      Blog Post Author

      Hi Venu,

      from my perspective the perfect integration between S/4 HANA and SAP CP IoT AE works with SAP CP Integration (aka HCI).

      I´am using this e.g. also for the integration with SAP hybris C4S or other SCP related services lile workflow services or business rules service,

      U can chek these little blog series which covers this as well:

      https://blogs.sap.com/2017/08/01/connect-a-device-to-the-sap-cloud-platform-internet-of-things-cloud-foundry-environment-part-1/

      As u can see in the API Hub S/4 HANA Cloud provides a wide range of API´s as well: https://api.sap.com/shell/discover/contentpackage/SAPS4HANACloud?section=ARTIFACTS

      cheers,

      fabian

      Author's profile photo Venu Ravipati
      Venu Ravipati

      Thank you Fabian

      Author's profile photo Avinash Manoli
      Avinash Manoli

      Hi Fabian,

      Many thanks for the detailed blogs and documentation on the IoT 4.0 platform.

      We have been trying to connect to the IoT 4.0 platform to send data via MQTT. We are attempting the Internet of Things gateway cloud platform for the connection. We have changed the hostname in the “Gateway_3_IoT Gateway MQTT_configuration.xml” file to our tenant hostname and deployed it. The <hostname> section currently looks like this “Companyname.eu10.cp.iot.sap”  throughout the XML file. We have downloaded the .key and .cert file and are using it in the python code(Thanks for the code btw :o).

      We want to send some static data and view it in the device under data visualization. The Paho-MQTT library is providing callbacks on connection, subscribing as well for publishing but no callback for on_message is coming through. The data is not being published onto the subscribed topic as well on the 4.0 platform. A sample output is provided for your consideration. Please let us know if there’s something that we are missing or not doing right?

       

       

      config_broker='companyname.cp.iot.sap'
      
      config_credentials_key='d:/Users/avmanoli/Desktop/certs/credentials.key'
      config_credentials_crt='d:/Users/avmanoli/Desktop/certs/credentials.crt'
      
      config_alternate_id_device='device_alternate_id_insetered_here'
      config_alternate_id_capability='device_capability_id_insetered_here'
      config_alternate_id_sensor='device_sensor_id_insetered_here'
      
      broker=config_broker
      broker_port=8883
      
      my_device=config_alternate_id_device
      client=mqtt.Client(client_id=my_device)
      client.on_connect=on_connect_broker
      client.on_subscribe=on_subscribe
      client.on_message=on_message
      client.on_publish=on_publish
      
      
      client.tls_set(ca_certs=None ,certfile=config_credentials_crt,  keyfile=config_credentials_key)
      
      client.connect(broker, broker_port, 60)
      
      my_subscription_topic='commands/' + 'config_alternate_id_device'
      client.subscribe(my_subscription_topic, 0)
      my_publish_topic='measures/' +'config_alternate_id_device'
      
      client.loop_start()
      
      my_mqtt_payload = "{ \"capabilityAlternateId\": \""+config_alternate_id_capability+"\",\"sensorAlternateId\": \""+config_alternate_id_sensor+"\", \"measures\":"555"}"
      result=client.publish(my_publish_topic, str(my_mqtt_payload), qos=1)
      #print(result)
      
      time.sleep(2)
      ####print("published successfully")
      ##client.disconnect() #disconnect
      ##client.loop_stop() #stop loop

       

      Many Thanks,

      Avinash Manoli

      Author's profile photo Fabian Lehmann
      Fabian Lehmann
      Blog Post Author

      Hi Avinash Manoli,

      first of all can you tell me how you want to connect the SAP Cloud Platform IoT service.

      Did you use the GW "edge" component, or the direct connection to iot service.

      Why do u have changed sth. in this file “Gateway_3_IoT Gateway MQTT_configuration.xml”

      Normaly in my scenario i connect directly via MQTTS (cert based auth) to SAP CP iot service, no need to change any config file.

      br,

      fabian

       

      Author's profile photo Avinash Manoli
      Avinash Manoli

      Hi Fabian,

      Many Thanks for your reply.

      We are attempting the direct connection to the IoT service and NOT the Gateway Edge Method. I have reverted the changes made to the XML File and the hostname component now reads as <localhost>.

      The situation remains the same though. The on_connect call back returns an “rc” value of 0 indicating successful connection, The on_subscribe callback returns a “granted_qos” of 0 but the message does not get published.

      We have been able to successfully send a payload to one of the devices using the “Eclipse Paho windows client” and we can view the data in the IoT platform under data visualization. When we attempt to send the same payload to the same device over the python code, we are unable to do so. This in spite of having a successful connection established. I have tried the code in Python 2 as well as Python 3. What do you think is going on here ?

      The Output and the Entire code I’m using is given below. Appreciate any of your thoughts on the matter.

      import time, sys, platform
      import json
      import base64
      import time
      
      import paho.mqtt.client as mqtt
      
      # ========================================================================
      
      def on_connect_broker(client, userdata, flags, rc):
             print('Connected to MQTT broker with result code: ' + str(rc))
              
      def on_subscribe(client, obj, message_id, granted_qos):
      	print('on_subscribe - message_id: ' + str(message_id) + ' / qos: ' + str(granted_qos))
      
      def on_message(client, userdata, message):
             print("received message =",str(message.payload.decode("utf-8")))
      
      def on_publish(client, userdata, mid):
          print("Published to client", str(client))
          
      # ========================================================================
      
      config_broker='company-name.eu10.cp.iot.sap'
      
      config_credentials_key='d:/Users/avmanoli/Desktop/certs/credentials.key'
      config_credentials_crt='d:/Users/avmanoli/Desktop/certs/credentials.crt'
      
      broker=config_broker
      broker_port=8883
      
      client=mqtt.Client(client_id="163b8dd6c89384f5")
      
      client.on_connect=on_connect_broker
      client.on_subscribe=on_subscribe
      client.on_message=on_message
      client.on_publish=on_publish
      
      client.tls_set(ca_certs=None ,certfile=config_credentials_crt,  keyfile=config_credentials_key)
      
      client.connect(broker, broker_port, 60)
      
      client.loop_start()
      
      client.subscribe("commands/163b8dd6c89384f5",0)
      time.sleep(5)
      payload = { "capabilityAlternateId": "77cd654bc535257f", "sensorAlternateId": "c799ef4166e30028", "measures": [["125"]] } 
      client.publish("measures/163b8dd6c89384f5", str(payload), 0)
      time.sleep(5)

      [EDIT]: The on_log function gives the following output. Acknowledgements are being received for connection as well as for subscription

      Many Thanks,

      Avinash Manoli

      Author's profile photo Fabian Lehmann
      Fabian Lehmann
      Blog Post Author

      Hi  Avinash,

      so i´ve tried this with the script which i mentioned in the blog 5 minutes ago and it works perfect to send a message from SAP CP IoT service perfect to your device/notebook:

      SensorType Definition:

      Started script:

      E:\MQTT_ZBook>python mqtt_cpu_usage.py
      Connected to MQTT broker with result code: 0
      on_subscribe - message_id: 1 / qos: (0,)
      8463810560
      { "capabilityAlternateId": "047eb5587b117f8f","sensorAlternateId": "32a8aa589ad04c33", "measures":7.8}
      (0, 2)
      8449789952
      { "capabilityAlternateId": "047eb5587b117f8f","sensorAlternateId": "32a8aa589ad04c33", "measures":7.8}
      (0, 3)
      8462884864
      { "capabilityAlternateId": "047eb5587b117f8f","sensorAlternateId": "32a8aa589ad04c33", "measures":6.6}
      (0, 4)
      8475246592
      { "capabilityAlternateId": "047eb5587b117f8f","sensorAlternateId": "32a8aa589ad04c33", "measures":14.1}
      (0, 5)
      on_message - commands/9c6f7ab92eb4807c 0
      on_message - commands/9c6f7ab92eb4807c 0 b'{"sensorAlternateId":"32a8aa589ad04c33","capabilityAlternateId":"9e3180b0bba5068a","command":{"usage":"123.0"}}'
      dealing with a control command
      command: {'usage': '123.0'}
      
      =======================NEW MQTT EVENT RCV======================================
      123.0
      =================================================================================

       

      Requested API call to the device:

      HTTP POST: https://<tenant>/iot/core/api/v1/devices/<device id>/commands

      {
        "capabilityId": "12e4465e-788f-4269-8e83-3b2e641aaf46",
        "command": {
          "usage": "123.0"
        },
        "sensorId": "141"
      }

       

      hopefully this helps.

       

      br,

      fabian

       

      Author's profile photo Avinash Manoli
      Avinash Manoli

      Hi Fabian,

      Many Thanks for your reply.  I have now been able to fix the issue. Previously I was sending the payload in the same manner as i was sending it through the PAHO Java client. I believe that was the issue. Once I changed it and sent it in the format that you send the payload, the data is now populating under the device.

      Many Thanks,
      Avinash Manoli

      Author's profile photo Fabian Lehmann
      Fabian Lehmann
      Blog Post Author

      Hi Avinash,

       

      you´re welcome.

       

      br,

      fabian

      Author's profile photo Wouter Lemaire
      Wouter Lemaire

      Hi Fabian,

      Any idea if it's possible to fetch commands on the device with REST api? If possible, we would have to poll for commands I guess?

      Kr,

      Wouter

      Author's profile photo Anton Levin
      Anton Levin

      Hello Wouter, Gateway REST exposes an endpoint for getting the device commands. See more at https://help.sap.com/viewer/3d1c4ea7d7344d6fb5b0ca602d3ee9b7/Cloud/en-US/eebbcd06a9be4fa4ac1702db3a52380c.html

      Regards, Anton

       

      Author's profile photo Fabian Lehmann
      Fabian Lehmann
      Blog Post Author

      Hi Wouter,

       

      does the answer from Anton resolved your issue?

      thx,

      fabian

      Author's profile photo Wouter Lemaire
      Wouter Lemaire

      Yes! Perfect 🙂 Thanks!