SAP-Watson IoT Integration Strategy
This recipe describes how to create an express.js web application that 1) listens for temperature readings from a sensor connected to the Watson IoT platform and 2) triggers some action on an SAP ERP system if a specified temperature value is breached.
The coldchain web application is used as the example to demonstrate how the integration between the express.js application and the SAP ERP system can be performed. The coldchain application monitors the temperature of a purchased package as it is moving through a supply chain from the manufacturer’s facility to the buyer. The package is assumed to be temperature-sensitive (e.g. a medicine packaged in ice) and must be kept at a temperature below 45 degrees Fahrenheit. As the package moves through the supply chain, if its temperature rises above the 45-degree Fahrenheit threshold, the sales order associated with the package should be immediately cancelled in the manufacturer’s SAP ERP system and the package should be returned to the manufacturer for a replacement.
The picture below details the architectural components associated with the coldchain solution. The image depicts the communication between the coldchain web application and the SAP systems is accomplished through the SAP PI. Additionally, it shows that the IoT sensor sends information to the Watson IoT platform to which it is registered, and that those messages are listened for by the coldchain web application.
The SAP ERP system initiates delivery of a coldchain package and, when this occurs, the sales order document (VBELN) associated with the package is sent from the ERP system to the coldchain web application via the SAP PI. As the package is moving through the supply chain, a sensor attached to the package is continually sending the current temperature of the package to the coldchain web application via the Watson IoT platform. Upon receiving the temperature reading, the coldchain application writes that information to a blockchain ledger so that the package’s temperature history can be tracked. As long as the temperature of the package remains below the stipulated 45-degree Fahrenheit level, the package continues its journey from the manufacturer to the buyer. However, at some point, if the 45-degree temperature threshold is breached while the package is in transit, the coldchain web application is immediately alerted by the blockchain (which has the temperature contract implemented within it), and the process to halt the package shipment and to cancel it is initiated. To trigger this sales order cancellation, the coldchain application sends a SOAP message containing the VBELN to the SAP PI invoking the exposed PI method outbound_zlss_return. This method triggers another message to be sent from the SAP PI to the SAP ERP system which directs the ERP system to cancel the sales order shipment associated with the VBELN and to create a replacement shipment. This is accomplished via the zlss_return method implemented in the ERP system.
The sequence just described is illustrated by Steps 1 and 2 in the diagram below.
At this point, the reader might logically wonder why the SAP PI is needed. Couldn’t the SAP ERP system simply expose the zlss_return method as an OData service and have the coldchain application directly call it? The short answer is that it could, but this is not considered a best practice. Using a middle layer such as the SAP PI is preferred in production quality environments. Using the OData strategy is fine to validate a PoC (proof-of-concept), but not for a production environment setting.
To see a video demo of this process, use this link: https://www-01.ibm.com/common/ssi/cgi-bin/ssialias?htmlfid=86016086USEN&
Create a method which interfaces with the SAP PI
The first step in implementing the integration described in the preceding SAP-Watson IoT Integration Strategy section is to create an interface function between the coldchain application and the SAP PI component.
The sap-integration.js code above implements a method called returnOrder.
returnOrder, in turn, creates a SOAP client which invokes an exposed method on the SAP PI called outbound_zlss_return. The VBELN (sales order number) is passed to that method by the coldchain app. When called, the SAP PI method outbound_zlss_return triggers cancellation of the sales order associated with the VBELN by invoking the ERP function zlss_return residing on the ERP system.
The SAP PI method outbound_zlss_return is described to the coldchain application in a file called return.wsdl.
Update the application code to import the necessary libraries that allow integration with SAP and the Watson IoT platform
Line 5 above imports the MQTT.js client library. Message Queue Telemetry Transport, aka MQTT, is one of the most widely used lightweight protocols to carry minimal data overhead. This protocol is especially associated with Internet of Things (IoT) development. The messages which will be sent from the Watson IoT platform to the coldchain app will be MQTT messages. Importing this library will allow the application code to subscribe to MQTT messages and connect to an MQTT message broker.
Line 9 imports the sap-integration.js library file we created in Step 2 and gives our app.js access to the returnOrder method in that file. We will be invoking that method later in this recipe.
Update the application code to correctly interface with the Watson IoT platform
If the IoT temperature sensor is registered successfully with the Watson IoT platform, the Watson IoT platform should continually be sending out messages from the sensor similar to the following:
The screenshot above was taken from the Watson IoT Platform under the Recent Events tab for the connected device, in this case, SensorTag1 (device id: 546c0e809981):
The MQTT payload for one of the messages above should look similar to this:
where objectTemp is the sensor’s temperature in Celsius. This objectTemp is what will be monitored by the coldchain application to ensure it remains below the contracted 45-degree Fahrenheit threshold.
Now that we have verified that the IoT sensor is successfully connected to the Watson IoT platform, we need to update the application code to listen for these messages.
To do this, we first need to set the IoT message broker associated with the Watson IoT platform and connect to it. The following lines accomplish this.
Line 2 defines the device id that the application will be listening for MQTT messages from. For this example, it is ‘546c0e809981’. Note that this device id matches the device id for which we verified successful registration with the Watson IoT platform earlier.
Line 4 sets the IoT message broker to the Watson IoT platform’s message broker. This is the message broker to which the IoT sensor will be sending its MQTT messages and from which the application will be listening for MQTT messages.
Lines 5 – 11 create an MQTT client that connects to the Watson IoT MQTT message broker. Lines 13 – 16 connects the application’s MQTT client to the Watson IoT message broker and specifies to the broker which specific messages (in MQTT terminology, “topics”) the application wishes to subscribe to. In this case, it is the messages from the device id associated with appDeviceID.
Update the application code to act upon MQTT messages from the Watson IoT platform
Now that the application is successfully subscribed to read MQTT messages from a specific device registered to the Watson IoT platform, it must now act upon them in some way as per the requirements of the application. For the coldchain scenario, the application code parses the temperature from the received MQTT message, converts it from Celsius to Fahrenheit, and sends the converted temperature to the UI front-end for display. This is done via a configured web socket connection. Ultimately, the temperature is written to a blockchain ledger so that the temperature history of the package can be recorded and tracked.
The coldchain application code is shown above as an example to illustrate how to read and act upon MQTT messages from a device connected to the Watson IoT platform.
Line 5 retrieves the message from the MQTT broker matching the “topic” defined in Step 4 and stores that message in a variable called message. This is the MQTT message containing the sensor temperature information.
Lines 8 – 12 parses the message and extracts the temperature into a local variable called tempFromDevice.
Line 20 converts the temperature from Celsius to Fahrenheit and stores it in another local variable called nobj.
Finally, the sensor temperature, now reflected in Fahrenheit, is sent to the coldchain front-end UI by the ws.send() call on line 21.
Invoke the SAP PI interface when a specific criteria has been met
The final step in this recipe is to call the appropriate SAP PI method when a specific criteria has been met. In the coldchain example, the criteria is met when the temperature sensor emits a temperature above the 45-degree Fahrenheit threshold. However, it could easily be any number of other criteria such as too much light exposure for a package (e.g. a medicine) that should have no-to-minimal light exposure. Other criteria could be used as well like humidity, vibration, radioactivity or any data that can be captured by a sensor.
Recall that in Step 2 of this recipe, we created a returnOrder method in sap-integration.js and subsequently in Step 3, we imported that sap-integration.js custom library into our application giving the app access to that returnOrder method. We will now have the application expose an /asset/return endpoint as shown below. Note that when called this endpoint invokes the SAP PI returnOrder method:
Line 1 above creates and exposes the /asset/return endpoint on the application, and when that endpoint is invoked, sapPI.returnOrder is called with the VBELN as one of the parameters as shown in line 3. As mentioned earlier, the VBELN is the sales order document indicating the specific sales order that needs to be cancelled in the SAP ERP system. When returnOrder is called on the PI, it, in turn, invokes zlss_return on the SAP ERP system which cancels the salers order associated with the passed-in VBELN.
The code below provides an example of how this /asset/return endpoint can be called: