Skip to content

Creating a rate of change signals

Use Case

The Falkonry TSI platform allows users to generate derived signals using the Calculations Transform feature. This feature provides a flexible way to create rate-of-change signals and other computed metrics from existing raw signals streaming into the system.

Resources

  • Below are step by step instructions for how to create rate of change signals using the Calculations Transform feature.
  • For more detailed documentation for using Calculations Transform please check out the Calculation Transformation Overview

Setting up the Calculations Transform payload

  • Login to your Falkonry account, navigate to Signals, and collect the IDs of the signals you want to use for making rate of change signals
  • Add relevant information to the CALCSETUP payload (see Calculation Transformation APIs for detailed instructions on API setup)
    • Copy the signal ids and names and add them to the payload
    • Create an inputSignalSet name for your collection of input signals
    • Create an outputSignalSet name for which will be the outputs of your python function (ie, six_machines/machine1/temperature1_ROC)
    • Establish the valueTypes for the outputSignals (this will be enforced upon generating data for your output signals)
    • Add a string of your Python script to the "script" section of the payload
    • Define the statistic type for sampling data
    • Select your Evaluation Window time range
  • Submit POST request to flows to run Calc Setup

Script example

This is an example of a simple script that will take in two signals 'six_machines/machine1/temperature1' and 'six_machines/machine1/temperature2', and create two rate of change signals, 'outputSignalSet/six_machines/machine1/temperature1_ROC' and 'outputSignalSet/six_machines/machine1/temperature2_ROC'.

def calculate(signal_dict):
    """    
    Parameters:
        signal_dict (dict): A dictionary with keys 'six_machines/machine1/temperature1' and 'six_machines/machine1/temperature2', each mapping to a list or NumPy array of numeric values.

    Returns:
        dict: A dictionary with keys 'six_machines/machine1/temperature1_ROC' and 'six_machines/machine1/temperature2_ROC', each containing the rate of change array for the corresponding signal.
    """
    rate_of_change = {}

    for key in signal_dict.keys():
        signal = np.array(signal_dict[key])
        roc = np.diff(signal, prepend=signal[0])  # or use prepend=0 if you prefer
        rate_of_change[f"{key}_ROC"] = roc

    return rate_of_change

Posting Calc Setup Flow

After constructing your payload, it should resemble the following:

 {
    "flowType": "CALCSETUP",
    "name": "Calc Setup flow with 2 inputs and 2 outputs",
    "spec": {
        "name": "MainInputs",
        "inputSignalset": {
            "name": "Demo_Input_ROC",
            "valueType": "Numeric",
            "signals": [
                {
                    "signal": "123456789123456789",
                    "name": "six_machines/machine1/temperature1"
                },
                {
                    "signal": "123456789123456789",
                    "name": "six_machines/machine1/temperature2"
               }
            ]
        },
        "outputSignalset": {
            "name": "Demo_Calc_ROC",
            "signals": [
                {
                    "valueType": "Numeric",
                    "name": "six_machines/machine1/temperature1_ROC"
                },
                {
                    "valueType": "Numeric",
                    "name": "six_machines/machine1/temperature2_ROC"
                }
            ]
        },
        "modelDetails": {
            "statistic": "mean",
            "script": "def calculate(signal_dict):\n    rate_of_change = {}\n\n    for key in signal_dict.keys():\n        signal = numpy.array(signal_dict[key])\n        roc = numpy.diff(signal)  # or use prepend=0 if you prefer\n        rate_of_change[f\"{key}_ROC\"] = roc\n\n    return rate_of_change\n", 
            # A string of a python function that takes in the temperature signals and outputs the rate of change of those signals with the suffix "_ROC"
            "valueType": "Numeric",
            "evaluationWindow": "PT3S"
        }
    }
}

We can then post this payload to the /flows endpoint. This will create a Calc Setup flow in the Activities Monitor and generate your Calculations Transform model.

curl --location --request POST 'https://app3.falkonry.ai/api/1.2/accounts/xxxxxxxxxxxxxxx/flows' \
--header 'Authorization: Bearer <token>' \
--header 'Content-Type: application/json' \
--data '{Insert Calc Setup Json payload}'

Note

Once a CALCSETUP flow is successfully posted, the model becomes live. As new data is ingested for the input signals, the model will automatically generate output values for the associated output signals in real time.

Historical Evaluation of your Calculation Transforms Model

The CALCEVAL flow is used to evaluate a Calculation transform model over a historical range of time. This process generates values for the output signal set based on past data from the input signals. See Calculation Transformation APIs for detailed instructions on the API setup. Below is an example CALCEVAL payload for running a historical evaluation.

 {
    "flowType": "CALCEVAL",
    "name": "eval ",
    "assessment": "123456789123456789",
    "spec": {
        "timeRange": {
            "startTime": "2024-08-09T00:00:00.000000000Z",
            "endTime":   "2024-08-10T00:00:00.000000000Z"
        },
        "model": "123456789123456789"
    }
}

We can then post this payload to the /flows endpoint. This will create a CALCEVAL flow in the Activities Monitor and generate historical output data from your corresponding Calculations Transform model.

curl --location --request POST 'https://app3.falkonry.ai/api/1.2/accounts/xxxxxxxxxxxxxxx/flows' \
--header 'Authorization: Bearer <token>' \
--header 'Content-Type: application/json' \
--data '{Insert Calc Eval Json payload}'