Skip to content

Create a Kelvin SmartApp™

You can build for both x86_64 and arm64 devices.

create default application
1
$ kelvin app create <SMARTAPP_NAME>

This will give a response similar to this;

command output
1
2
[kelvin.sdk][2025-03-19 18:39:54][I] Refreshing metadata..
Please provide a name for the application: event-detection

After providing Kelvin SmartApps™ name (i.e.: event-detection):

command output
1
2
3
[kelvin.sdk][2025-03-19 18:43:36][I] Creating new application "event-detection"
[kelvin.sdk][2025-03-19 18:43:36][I] Retrieving the latest schema version
[kelvin.sdk][2025-03-19 18:43:39][R] Successfully created new application: "event-detection".

This will automatically create a Kelvin SmartApp™ bootstrap within a directory named as event-detection populated with some default files and configurations.

Folder Structure

You can now open the folder in your favorite IDE or editor and start to modify the files to create your Kelvin SmartApp™.

default folder structure
1
2
3
4
5
6
7
8
9
$ cd event-detection
$ tree ./
├── Dockerfile
├── app.yaml
├── main.py
├── requirements.txt
└── schemas
    ├── configuration.json
    └── parameters.json

Below is a brief description of each file.

app.yaml

The app.yaml is the main configuration file that holds both Application definitions as well as the deployment/runtime configuration.

This file is used for Kelvin SmartApps™, Docker Apps, Imports (Connectors) and Exports.

On this page we are only focused on the Kelvin SmartApps™ options.

It is composed of the following sections:

spec_version key

The spec_version key is automatically injected and specifies Kelvin SmartApps™ JSON Schema (latest) version which both defines and validates the app.yaml structure.

spec_version
1
spec_version: 5.0.0

type

This defines the type for the application.

  • app: A Smart App that allows mapping inputs and outputs to data streams, sending control changes, recommendations, and data tags.
  • docker: An docker application that does not connect to the platform's data streams.
  • importer: Connects to an external system to import data into the platform as well as receive control changes to act on the external system.
  • exporter: Connects to the platform to export data to an external system.
application type
1
type: app

info

The root section holds Kelvin SmartApp™ basic information required to make itself uploadable to Kelvin's App Registry.

application info
1
2
3
4
5
name: event-detection
title: Event Detection
description: Monitors if a motor is overheating. If so, it will send a Control Change to reduce the Motor Speed.
version: 1.0.0
category: smartapp

The name is Kelvin SmartApp™ unique identifier.

The title and description will appear on the Kelvin UI once Kelvin SmartApps™ is uploaded.

The version defines the version of this Kelvin SmartApp™ and is used in the Kelvin UI.

Info

The version should be bumped every time Kelvin SmartApps™ gets an update, and before it gets uploaded to the App Registry.

The category will decide which group in the Applications dashboard of the Kelvin UI the Kelvin SmartApp™ will be placed by default.

Info

Operations will still be able to change the group the Kelvin SmartApp™ is associated with through the Kelvin UI.

flags

This is where you are able to set some of the Application's capabilities.

application flags
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
flags:
  enable_runtime_update:

    # enables configuration updates at runtime
    configuration: false 

    # enables deployment of more assets at runtime mode
    resources: false # default false

    # enables app parameters updates at runtime mode
    parameters: true # default true

    # enables asset properties updates at runtime mode
    resource_properties: true # default true

data_streams

This defines the inputs and outputs for the Kelvin SmartApp™

Warning

If you are generating Control Changes to an Asset through a Connector, then you will need to declare these outputs in the control_changes section which is documented in the next tab.

application data streams
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
data_streams:
  inputs:
    - name: temp_f
      data_type: number
    - name: speed_sp_out
      data_type: number

  outputs:
    - name: temp_c
      data_type: number

control_changes

This defines the data streams that are allowed to handle control changes.

You do not need to declare the Data Stream in the data_streams and control_changes sections. Either depending on its role in the Kelvin SmartApp™ is sufficient.

application data streams with control change flag
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
control_changes:
  inputs:
    - name: inter_app_value
      data_type: number

  outputs:
    - name: speed_sp_out
      data_type: number
    - name: control_mode
      data_type: number
    - name: scada_mode
      data_type: number

parameters

Kelvin SmartApp™ App Parameters are defined in three sections in the app.yaml file;

  • parameters defines the name and type of the App Parameter.
  • ui_schemas (this section) is a link to a JSON file containing all the information about how to display App Parameters in the Kelvin UI.
  • defaults / parameters define the default values assigned to each Asset when it is first created or when a Kelvin SmartApp™ update introduces a new App Parameter to existing Assets.

Each parameter can be defined by four different data_types. Full documentation on the different data_types is in the concept overview page.

In the app.yaml file it will look like this;

Note

Defaults section is explained in detail in the defaults tab.

app parameters
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
parameters:
  - name: closed_loop
    data_type: boolean
  - name: speed_decrease_set_point
    data_type: number
  - name: temperature_max_threshold
    data_type: number

ui_schemas:
  parameters: "schemas/parameters.json"

defaults:
  parameters:
    closed_loop: false
    speed_decrease_set_point: 1000
    temperature_max_threshold: 59

For the parameters.json file you can define all the information for the Kelvin UI. This can be the title, type of input required and limitations of the values allowed.

It will look something like this.

sample ui_schema/parameters.json
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
{
    "type": "object",
    "properties": {
        "closed_loop": {
            "type": "boolean",
            "title": "Closed Loop"
        },
        "speed_decrease_set_point": {
            "type": "number",
            "title": "Speed Decrease SetPoint",
            "minimum": 1000,
            "maximum": 3000
        },
        "temperature_max_threshold": {
            "type": "number",
            "title": "Temperature Max Threshold",
            "minimum": 50,
            "maximum": 100
        }
    },
    "required": [
        "closed_loop",
        "speed_decrease_set_point",
        "temperature_max_threshold"
    ]
}

Which will be displayed on the Kelvin UI as:

App Parameters

ui_schemas

This is where the Kelvin SmartApp™ configuration and Kelvin SmartApp™ Parameters are defined for the Kelvin UI.

The actual information is kept in a json file in the schemas folder of the project. The file location is defined in the app.yaml file like this;

application ui schemas
1
2
3
ui_schemas:
  configurations: "schemas/configurations.json"
  parameters: "schemas/parameters.json"

The json files will come with default blank schemas when first created.

Note

configurations.json information is optional, and if not provided, the Kelvin UI will display the configuration settings in a raw JSON or YAML file format without verifying the structure or content before applying them to the Kelvin SmartApp™.

default schemas/configurations.json
1
2
3
4
5
{
    "type": "object",
    "properties": {},
    "required": []
}

Note

schemas/parameters.json information is optional, and if not provided, the Kelvin UI will display a simple UI interface with the keys as the titles and no restrictions beyond the type of input.

default schemas/parameters.json
1
2
3
4
5
{
    "type": "object",
    "properties": {},
    "required": []
}

An example of a App Parameters JSON file filled in would look something like this;

sample schemas/parameters.json
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
{
    "type": "object",
    "properties": {
        "closed_loop": {
            "type": "boolean",
            "title": "Closed Loop"
        },
        "speed_decrease_set_point": {
            "type": "number",
            "title": "Speed Decrease SetPoint",
            "minimum": 1000,
            "maximum": 3000
        },
        "temperature_max_threshold": {
            "type": "number",
            "title": "Temperature Max Threshold",
            "minimum": 50,
            "maximum": 100
        }
    },
    "required": [
        "closed_loop",
        "speed_decrease_set_point",
        "temperature_max_threshold"
    ]
}

Which will be displayed on the Kelvin UI like this:

App Parameters

defaults

This section hold four main sections;

Note

All items in the defaults section are optional.

  • system : Is used to set different system requirements/constraints within Kelvin SmartApps™ running environment. i.e. Resources, Environment Variables, Volumes, Ports, etc.
  • datastream_mapping : Here you can map specific app inputs/outputs declared earlier in the app.yaml file to existing Data Streams on the Kelvin Platform.
  • configuration : These are global variables that apply to the SmartApp as a whole, regardless of which asset is being managed.
  • parameters : Default app parameter values used in a Kelvin SmartApp. These are applied: When an asset is first added to the Kelvin SmartApp or During upgrades, when new app parameters become available for existing assets.
application defaults
1
2
3
4
5
defaults:
  system: {}
  datastream_mapping: []
  configuration: {}
  parameters: {}

defaults/system section

The system section is [optional].

This is where developers can set the system settings that the Kelvin SmartApp™ needs to be able to function as intended.

This includes opening ports, setting environment variables, limited resource usage, attaching volumes and setting the privileged tag which gives extended privileges on the host system.

application system defaults
1
2
3
4
5
6
7
defaults:
  system:
    resources: {}
    environment_vars: []
    volumes: []
    ports: []
    privileged: Boolean
System Section Options

resources section

The resources defines the reserved (requests) and limits the resources allocated to Kelvin SmartApps™:

  • Limits: This is a maximum resource limit enforced by the cluster. Kelvin SmartApps™ will not be allowed to use more than the limit set.

  • Requests: This is the minimum resources that is allocated to Kelvin SmartApps™. This is reserved for Kelvin SmartApps™ and can not be used by other Kelvin SmartApps™. If there are extra resources available, Kelvin SmartApps™ can use more than the requested resources as long as it does not exceed the Limits.

You can read the full documentation about CPU and Memory resources in the Advanced section.

application resource defaults
1
2
3
4
5
6
7
8
9
defaults:
  system:
    resources:
      requests:   # Reserved
        cpu: 100m
        memory: 256Mi
    limits:     # Limits
        cpu: 200m
        memory: 512Mi

environment_vars section

The environment_vars is used to define Environment Variables available within Kelvin SmartApps™ container. i.e.:

application environmental variable defaults
1
2
3
4
5
6
7
8
9
defaults:
  system:
    environment_vars:
      - name: AZURE_ACCOUNT_NAME
        value: <% secrets.azure-account-name %>
      - name: AZURE_ACCOUNT_KEY
        value: <% secrets.azure-account-key %>
      - name: AZURE_STORAGE_CONTAINER
        value: <% secrets.azure-storage-container %>

volumes section

Mounted volumes are [optional] and their main purpose is to share and persist data generated by Kelvin SmartApps™ or used by it in a specific place. They act like a shared folder between Kelvin SmartApps™ and the host. Kelvin supports directory volumes, such as folders or serial ports, persistent, and file/test volumes:

application attached volume defaults
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
defaults:
  system:
    volumes:
      # Folder Volume
      - name: serial-rs232
        target: /dev/rs232 # Container path
        type: host
        host:
        source: /dev/ttyS0 # Host path

      # Persistent Volume
      - name: extremedb
        target: /extremedb/data
        type: persistent

      # File/Text Volume
      - name: model-parameters
        target: /opt/kelvin/data/parameters.bin
        type: text # Renders data into a file
        text:
        base64: true
        encoding: utf-8
        data: |-
              SGVsbG8gUHJvZHVjdCBHdWlsZCwgZnJvbSB0aGUgRW5naW5lZXJpbmcgR3VpbGQhCg==

ports section

The ports is [optional] and used to define network port mappings. i.e.:

application open ports defaults
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
defaults:
  system:
    ports:
      - name: http
        type: host # Exposed on the host
        host:
        port: 80

      - name: opcua
        type: service # Exposed as a service for other containers
        service:
        port: 48010
        exposed_port: 30120
        exposed: true

privileged key

The privileged key is [optional] and used to grant extended privileges to Kelvin SmartApps™, allowing it to access any devices on the host, such as a Serial device:

application privileged defaults
1
2
3
defaults:
  system:
      privileged: true

defaults/datastream_mapping

Here you can map specific Kelvin SmartApp™ inputs/outputs declared earlier in the app.yaml file to existing Data Streams on the Kelvin Platform.

application data stream mapping defaults
1
2
3
4
5
6
defaults:
  datastream_mapping:
    - app: temp_f
      datastream: temperature_fahrenheit
    - app: temp_c
      datastream: temperature_celsius

defaults/configuration

These are the default global Kelvin SmartApp™ configuration values.

Configurations can also be optionally defined in the ui_schemas that provides a link to a JSON file containing all the information about how to display Configurations in the Kelvin UI.

Note

Operations will have the option to change these at runtime from the Kelvin UI.

application app configuration defaults
1
2
3
4
defaults:
  configuration:
    broker-ip: edge-mqtt-broker
    broker-port: 1883

defaults/parameters

Kelvin SmartApp™ App Parameters are defined in three sections in the app.yaml file;

  • parameters defines the name and type of the App Parameter.
  • ui_schemas (this section) is a link to a JSON file containing all the information about how to display App Parameters in the Kelvin UI.
  • defaults / parameters define the default values assigned to each Asset when it is first created or when a Kelvin SmartApp™ update introduces a new App Parameter to existing Assets.

Note

Operations will have the option to change these at runtime from the Kelvin UI.

application app parameter defaults
1
2
3
4
5
defaults:
  parameters:
    closed_loop: false
    speed_decrease_set_point: 1000
    temperature_max_threshold: 59

Python

The main.py is used as the entry point of Kelvin SmartApps™. When it runs, main.py is typically the first script that gets executed, and it usually contains the main logic or orchestrates the flow of Kelvin SmartApps™. However, naming a file "main.py" is just a convention, and it's not mandatory. The name helps developers quickly identify where the primary logic of Kelvin SmartApps™ begins.

The following code example will be generated upon kelvin app create:

default main.py
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
import asyncio

from kelvin.application import KelvinApp # KelvinApp import


async def main() -> None:
    # Creating instance of Kelvin SmartApp™ Client
    app = KelvinApp()

    # Connect the App Client
    await app.connect()

    while True:
        # Custom Loop
        await asyncio.sleep(1)


if __name__ == "__main__":
    asyncio.run(main())

Supporting Files

The requirements.txt file is used to list all the dependencies a Python Kelvin SmartApps™ needs. It can be used to easily install all the required packages, ensuring Kelvin SmartApps™ runs correctly.

The Dockerfile is a script used to define the instructions and configuration for building a Docker image. It specifies the base image, installation of software, file copying, and other setup tasks needed to create a reproducible and isolated environment for running Kelvin SmartApps™ in Docker containers.

default Dockerfile
1
2
3
4
5
6
7
8
FROM python:3.10-slim

ENV PYTHONUNBUFFERED=1
WORKDIR /opt/kelvin/app 
COPY . /opt/kelvin/app
RUN pip install -r requirements.txt

ENTRYPOINT python main.py

Info

If main.py is not the intended entry point, it also needs to be replaced on the Dockerfile.

Specifies which files and directories should be excluded when building Kelvin SmartApps™ Docker image. It helps reducing the build context, resulting in smaller, more efficient Docker image.