一个评论示例:HVAC 温度控制 - Amazon IoT Events
Amazon Web Services 文档中描述的 Amazon Web Services 服务或功能可能因区域而异。要查看适用于中国区域的差异,请参阅中国的 Amazon Web Services 服务入门

本文属于机器翻译版本。若本译文内容与英语原文存在差异,则一律以英文原文为准。

一个评论示例:HVAC 温度控制

以下某些示例 JSON 文件具有内联注释,这使得它们无效的 JSON。这些示例的完整版本,无需评论,请访问HVAC 温度控制

Background

本示例实现了一个温控器控制模型,使您能够执行以下操作。

  • 定义一个探测器模型,可用于监控和控制多个区域。为每个区域创建一个检测器实例。

  • 从每个控制区域的多个传感器中获取温度数据。

  • 更改区域的温度设置点。

  • 为每个区域设置操作参数,并在实例正在使用时重置这些参数。

  • 从区域动态添加或删除传感器。

  • 指定最短运行时间以保护加热和冷却装置。

  • 拒绝异常传感器读数。

  • 定义紧急设定点,如果任何一个传感器报告温度高于或低于给定阈值,则立即进行加热或冷却。

  • 报告异常读数和温度峰值。

输入定义

我们希望创建一个探测器模型,我们可以用来监控和控制多个不同区域的温度。每个区域可以有多个传感器来报告温度。我们假设每个区域都有一个加热装置和一个冷却装置,可以打开或关闭以控制该区域的温度。每个区域由一个检测器实例控制。

由于我们监控和控制的不同区域可能具有不同的特征,需要不同的控制参数,因此我们定义了'seedTemperatureInput'为每个区域提供这些参数。当我们将其中一条输入消息发送到Amazon IoT Events时,将创建一个新的检测器模型实例,该实例具有我们希望在该区域使用的参数。这是该输入的定义。

CLI 命令:

aws iotevents create-input --cli-input-json file://seedInput.json

file:seedInput.json

{ "inputName": "seedTemperatureInput", "inputDescription": "Temperature seed values.", "inputDefinition": { "attributes": [ { "jsonPath": "areaId" }, { "jsonPath": "desiredTemperature" }, { "jsonPath": "allowedError" }, { "jsonPath": "rangeHigh" }, { "jsonPath": "rangeLow" }, { "jsonPath": "anomalousHigh" }, { "jsonPath": "anomalousLow" }, { "jsonPath": "sensorCount" }, { "jsonPath": "noDelay" } ] } }

响应:

{ "inputConfiguration": { "status": "ACTIVE", "inputArn": "arn:aws:iotevents:us-west-2:123456789012:input/seedTemperatureInput", "lastUpdateTime": 1557519620.736, "creationTime": 1557519620.736, "inputName": "seedTemperatureInput", "inputDescription": "Temperature seed values." } }

Notes

  • 将为每个唯一的'areaId'在任何消息中收到。请参阅'key'字段中的'areaDetectorModel'定义。

  • 平均温度可以从'desiredTemperature'通过'allowedError'之前,加热或冷却装置被激活的区域。

  • 如果任何传感器报告温度高于'rangeHigh',检测器报告尖峰并立即启动冷却装置。

  • 如果任何传感器报告温度低于'rangeLow',检测器报告尖峰并立即启动加热装置。

  • 如果任何传感器报告温度高于'anomalousHigh'或下面的'anomalousLow',检测器会报告异常传感器读数,但忽略报告的温度读数。

  • 这些区域有:'sensorCount'告诉探测器报告该区域的传感器数量。探测器通过给出每个接收温度读数相应的权重系数来计算该区域的平均温度。因此,检测器无需跟踪每个传感器的报告内容,并且可以根据需要动态更改传感器的数量。但是,如果单个传感器脱机,探测器将不会知道这一点,也不会给它留出余地。我们建议您创建另一个专门用于监视每个传感器的连接状态的检测器型号。使用两种互补探测器模型可简化两种模型的设计。

  • 这些区域有:'noDelay'该值可以是true或者false。加热或冷却装置打开后,它应保持一段最短的时间,以保护装置的完整性并延长其使用寿命。如果'noDelay'设置为false,检测器实例会在关闭冷却和加热装置之前强制执行延迟,以确保它们的运行时间最短。由于我们无法使用变量值来设置计时器,因此检测器模型定义中的延迟秒数已经被硬编码。

这些区域有:'temperatureInput'用于将传感器数据传输到检测器实例。

CLI 命令:

aws iotevents create-input --cli-input-json file://temperatureInput.json

file:temperatureInput.json

{ "inputName": "temperatureInput", "inputDescription": "Temperature sensor unit data.", "inputDefinition": { "attributes": [ { "jsonPath": "sensorId" }, { "jsonPath": "areaId" }, { "jsonPath": "sensorData.temperature" } ] } }

响应:

{ "inputConfiguration": { "status": "ACTIVE", "inputArn": "arn:aws:iotevents:us-west-2:123456789012:input/temperatureInput", "lastUpdateTime": 1557519707.399, "creationTime": 1557519707.399, "inputName": "temperatureInput", "inputDescription": "Temperature sensor unit data." } }

Notes

  • 这些区域有:'sensorId'不被示例检测器实例用于直接控制或监视传感器。它会自动传递到检测器实例发送的通知中。从那里,它可以用于识别出现故障的传感器(例如,定期发送异常读数的传感器可能即将发生故障)或已脱机的传感器(当它被用作监控设备心跳的其他检测器型号的输入时)。这些区域有:'sensorId'也可以帮助识别区域中的温暖区域或寒区,如果其读数经常与平均值不同。

  • 这些区域有:'areaId'用于将传感器的数据路由到相应的检测器实例。为每个唯一的'areaId'在任何消息中收到。请参阅'key'字段中的'areaDetectorModel'定义。

探测器模型定义

这些区域有:'areaDetectorModel'示例具有内联的注释。

CLI 命令:

aws iotevents create-detector-model --cli-input-json file://areaDetectorModel.json

file:areaDetectorModel.json

{ "detectorModelName": "areaDetectorModel", "detectorModelDefinition": { "states": [ { "stateName": "start", // In the 'start' state we set up the operation parameters of the new detector instance. // We get here when the first input message arrives. If that is a 'seedTemperatureInput' // message, we save the operation parameters, then transition to the 'idle' state. If // the first message is a 'temperatureInput', we wait here until we get a // 'seedTemperatureInput' input to ensure our operation parameters are set. We can // also reenter this state using the 'BatchUpdateDetector' API. This enables us to // reset the operation parameters without needing to delete the detector instance. "onEnter": { "events": [ { "eventName": "prepare", "condition": "true", "actions": [ { "setVariable": { // initialize 'sensorId' to an invalid value (0) until an actual sensor reading // arrives "variableName": "sensorId", "value": "0" } }, { "setVariable": { // initialize 'reportedTemperature' to an invalid value (0.1) until an actual // sensor reading arrives "variableName": "reportedTemperature", "value": "0.1" } }, { "setVariable": { // When using 'BatchUpdateDetector' to re-enter this state, this variable should // be set to true. "variableName": "resetMe", "value": "false" } } ] } ] }, "onInput": { "transitionEvents": [ { "eventName": "initialize", "condition": "$input.seedTemperatureInput.sensorCount > 0", // When a 'seedTemperatureInput' message with a valid 'sensorCount' is received, // we use it to set the operational parameters for the area to be monitored. "actions": [ { "setVariable": { "variableName": "rangeHigh", "value": "$input.seedTemperatureInput.rangeHigh" } }, { "setVariable": { "variableName": "rangeLow", "value": "$input.seedTemperatureInput.rangeLow" } }, { "setVariable": { "variableName": "desiredTemperature", "value": "$input.seedTemperatureInput.desiredTemperature" } }, { "setVariable": { // Assume we're at the desired temperature when we start. "variableName": "averageTemperature", "value": "$input.seedTemperatureInput.desiredTemperature" } }, { "setVariable": { "variableName": "allowedError", "value": "$input.seedTemperatureInput.allowedError" } }, { "setVariable": { "variableName": "anomalousHigh", "value": "$input.seedTemperatureInput.anomalousHigh" } }, { "setVariable": { "variableName": "anomalousLow", "value": "$input.seedTemperatureInput.anomalousLow" } }, { "setVariable": { "variableName": "sensorCount", "value": "$input.seedTemperatureInput.sensorCount" } }, { "setVariable": { "variableName": "noDelay", "value": "$input.seedTemperatureInput.noDelay == true" } } ], "nextState": "idle" }, { "eventName": "reset", "condition": "($variable.resetMe == true) && ($input.temperatureInput.sensorData.temperature < $variable.anomalousHigh && $input.temperatureInput.sensorData.temperature > $variable.anomalousLow)", // This event is triggered if we have reentered the 'start' state using the // 'BatchUpdateDetector' API with 'resetMe' set to true. When we reenter using // 'BatchUpdateDetector' we do not automatically continue to the 'idle' state, but // wait in 'start' until the next input message arrives. This event enables us to // transition to 'idle' on the next valid 'temperatureInput' message that arrives. "actions": [ { "setVariable": { "variableName": "averageTemperature", "value": "((($variable.averageTemperature * ($variable.sensorCount - 1)) + $input.temperatureInput.sensorData.temperature) / $variable.sensorCount)" } } ], "nextState": "idle" } ] }, "onExit": { "events": [ { "eventName": "resetHeatCool", "condition": "true", // Make sure the heating and cooling units are off before entering 'idle'. "actions": [ { "sns": { "targetArn": "arn:aws:sns:us-west-2:123456789012:heatOff" } }, { "sns": { "targetArn": "arn:aws:sns:us-west-2:123456789012:coolOff" } }, { "iotTopicPublish": { "mqttTopic": "hvac/Heating/Off" } }, { "iotTopicPublish": { "mqttTopic": "hvac/Cooling/Off" } } ] } ] } }, { "stateName": "idle", "onInput": { "events": [ { "eventName": "whatWasInput", "condition": "true", // By storing the 'sensorId' and the 'temperature' in variables, we make them // available in any messages we send out to report anomalies, spikes, or just // if needed for debugging. "actions": [ { "setVariable": { "variableName": "sensorId", "value": "$input.temperatureInput.sensorId" } }, { "setVariable": { "variableName": "reportedTemperature", "value": "$input.temperatureInput.sensorData.temperature" } } ] }, { "eventName": "changeDesired", "condition": "$input.seedTemperatureInput.desiredTemperature != $variable.desiredTemperature", // This event enables us to change the desired temperature at any time by sending a // 'seedTemperatureInput' message. But note that other operational parameters are not // read or changed. "actions": [ { "setVariable": { "variableName": "desiredTemperature", "value": "$input.seedTemperatureInput.desiredTemperature" } } ] }, { "eventName": "calculateAverage", "condition": "$input.temperatureInput.sensorData.temperature < $variable.anomalousHigh && $input.temperatureInput.sensorData.temperature > $variable.anomalousLow", // If a valid temperature reading arrives, we use it to update the average temperature. // For simplicity, we assume our sensors will be sending updates at about the same rate, // so we can calculate an approximate average by giving equal weight to each reading we receive. "actions": [ { "setVariable": { "variableName": "averageTemperature", "value": "((($variable.averageTemperature * ($variable.sensorCount - 1)) + $input.temperatureInput.sensorData.temperature) / $variable.sensorCount)" } } ] } ], "transitionEvents": [ { "eventName": "anomalousInputArrived", "condition": "$input.temperatureInput.sensorData.temperature >= $variable.anomalousHigh || $input.temperatureInput.sensorData.temperature <= $variable.anomalousLow", // When an anomalous reading arrives, send an MQTT message, but stay in the current state. "actions": [ { "iotTopicPublish": { "mqttTopic": "temperatureSensor/anomaly" } } ], "nextState": "idle" }, { "eventName": "highTemperatureSpike", "condition": "$input.temperatureInput.sensorData.temperature > $variable.rangeHigh", // When even a single temperature reading arrives that is above the 'rangeHigh', take // emergency action to begin cooling, and report a high temperature spike. "actions": [ { "iotTopicPublish": { "mqttTopic": "temperatureSensor/spike" } }, { "sns": { "targetArn": "arn:aws:sns:us-west-2:123456789012:coolOn" } }, { "iotTopicPublish": { "mqttTopic": "hvac/Cooling/On" } }, { "setVariable": { // This is necessary because we want to set a timer to delay the shutoff // of a cooling/heating unit, but we only want to set the timer when we // enter that new state initially. "variableName": "enteringNewState", "value": "true" } } ], "nextState": "cooling" }, { "eventName": "lowTemperatureSpike", "condition": "$input.temperatureInput.sensorData.temperature < $variable.rangeLow", // When even a single temperature reading arrives that is below the 'rangeLow', take // emergency action to begin heating, and report a low-temperature spike. "actions": [ { "iotTopicPublish": { "mqttTopic": "temperatureSensor/spike" } }, { "sns": { "targetArn": "arn:aws:sns:us-west-2:123456789012:heatOn" } }, { "iotTopicPublish": { "mqttTopic": "hvac/Heating/On" } }, { "setVariable": { "variableName": "enteringNewState", "value": "true" } } ], "nextState": "heating" }, { "eventName": "highTemperatureThreshold", "condition": "(((($variable.averageTemperature * ($variable.sensorCount - 1)) + $input.temperatureInput.sensorData.temperature) / $variable.sensorCount) > ($variable.desiredTemperature + $variable.allowedError))", // When the average temperature is above the desired temperature plus the allowed error factor, // it is time to start cooling. Note that we calculate the average temperature here again // because the value stored in the 'averageTemperature' variable is not yet available for use // in our condition. "actions": [ { "sns": { "targetArn": "arn:aws:sns:us-west-2:123456789012:coolOn" } }, { "iotTopicPublish": { "mqttTopic": "hvac/Cooling/On" } }, { "setVariable": { "variableName": "enteringNewState", "value": "true" } } ], "nextState": "cooling" }, { "eventName": "lowTemperatureThreshold", "condition": "(((($variable.averageTemperature * ($variable.sensorCount - 1)) + $input.temperatureInput.sensorData.temperature) / $variable.sensorCount) < ($variable.desiredTemperature - $variable.allowedError))", // When the average temperature is below the desired temperature minus the allowed error factor, // it is time to start heating. Note that we calculate the average temperature here again // because the value stored in the 'averageTemperature' variable is not yet available for use // in our condition. "actions": [ { "sns": { "targetArn": "arn:aws:sns:us-west-2:123456789012:heatOn" } }, { "iotTopicPublish": { "mqttTopic": "hvac/Heating/On" } }, { "setVariable": { "variableName": "enteringNewState", "value": "true" } } ], "nextState": "heating" } ] } }, { "stateName": "cooling", "onEnter": { "events": [ { "eventName": "delay", "condition": "!$variable.noDelay && $variable.enteringNewState", // If the operational parameters specify that there should be a minimum time that the // heating and cooling units should be run before being shut off again, we set // a timer to ensure the proper operation here. "actions": [ { "setTimer": { "timerName": "coolingTimer", "seconds": 180 } }, { "setVariable": { // We use this 'goodToGo' variable to store the status of the timer expiration // for use in conditions that also use input variable values. If // 'timeout()' is used in such mixed conditionals, its value is lost. "variableName": "goodToGo", "value": "false" } } ] }, { "eventName": "dontDelay", "condition": "$variable.noDelay == true", // If the heating/cooling unit shutoff delay is not used, no need to wait. "actions": [ { "setVariable": { "variableName": "goodToGo", "value": "true" } } ] }, { "eventName": "beenHere", "condition": "true", "actions": [ { "setVariable": { "variableName": "enteringNewState", "value": "false" } } ] } ] }, "onInput": { "events": [ // These are events that occur when an input is received (if the condition is // satisfied), but don't cause a transition to another state. { "eventName": "whatWasInput", "condition": "true", "actions": [ { "setVariable": { "variableName": "sensorId", "value": "$input.temperatureInput.sensorId" } }, { "setVariable": { "variableName": "reportedTemperature", "value": "$input.temperatureInput.sensorData.temperature" } } ] }, { "eventName": "changeDesired", "condition": "$input.seedTemperatureInput.desiredTemperature != $variable.desiredTemperature", "actions": [ { "setVariable": { "variableName": "desiredTemperature", "value": "$input.seedTemperatureInput.desiredTemperature" } } ] }, { "eventName": "calculateAverage", "condition": "$input.temperatureInput.sensorData.temperature < $variable.anomalousHigh && $input.temperatureInput.sensorData.temperature > $variable.anomalousLow", "actions": [ { "setVariable": { "variableName": "averageTemperature", "value": "((($variable.averageTemperature * ($variable.sensorCount - 1)) + $input.temperatureInput.sensorData.temperature) / $variable.sensorCount)" } } ] }, { "eventName": "areWeThereYet", "condition": "(timeout(\"coolingTimer\"))", "actions": [ { "setVariable": { "variableName": "goodToGo", "value": "true" } } ] } ], "transitionEvents": [ // Note that some tests of temperature values (for example, the test for an anomalous value) // must be placed here in the 'transitionEvents' because they work together with the tests // in the other conditions to ensure that we implement the proper "if..elseif..else" logic. // But each transition event must have a destination state ('nextState'), and even if that // is actually the current state, the "onEnter" events for this state will be executed again. // This is the reason for the 'enteringNewState' variable and related. { "eventName": "anomalousInputArrived", "condition": "$input.temperatureInput.sensorData.temperature >= $variable.anomalousHigh || $input.temperatureInput.sensorData.temperature <= $variable.anomalousLow", "actions": [ { "iotTopicPublish": { "mqttTopic": "temperatureSensor/anomaly" } } ], "nextState": "cooling" }, { "eventName": "highTemperatureSpike", "condition": "$input.temperatureInput.sensorData.temperature > $variable.rangeHigh", "actions": [ { "iotTopicPublish": { "mqttTopic": "temperatureSensor/spike" } } ], "nextState": "cooling" }, { "eventName": "lowTemperatureSpike", "condition": "$input.temperatureInput.sensorData.temperature < $variable.rangeLow", "actions": [ { "iotTopicPublish": { "mqttTopic": "temperatureSensor/spike" } }, { "sns": { "targetArn": "arn:aws:sns:us-west-2:123456789012:coolOff" } }, { "sns": { "targetArn": "arn:aws:sns:us-west-2:123456789012:heatOn" } }, { "iotTopicPublish": { "mqttTopic": "hvac/Cooling/Off" } }, { "iotTopicPublish": { "mqttTopic": "hvac/Heating/On" } }, { "setVariable": { "variableName": "enteringNewState", "value": "true" } } ], "nextState": "heating" }, { "eventName": "desiredTemperature", "condition": "(((($variable.averageTemperature * ($variable.sensorCount - 1)) + $input.temperatureInput.sensorData.temperature) / $variable.sensorCount) <= ($variable.desiredTemperature - $variable.allowedError)) && $variable.goodToGo == true", "actions": [ { "sns": { "targetArn": "arn:aws:sns:us-west-2:123456789012:coolOff" } }, { "iotTopicPublish": { "mqttTopic": "hvac/Cooling/Off" } } ], "nextState": "idle" } ] } }, { "stateName": "heating", "onEnter": { "events": [ { "eventName": "delay", "condition": "!$variable.noDelay && $variable.enteringNewState", "actions": [ { "setTimer": { "timerName": "heatingTimer", "seconds": 120 } }, { "setVariable": { "variableName": "goodToGo", "value": "false" } } ] }, { "eventName": "dontDelay", "condition": "$variable.noDelay == true", "actions": [ { "setVariable": { "variableName": "goodToGo", "value": "true" } } ] }, { "eventName": "beenHere", "condition": "true", "actions": [ { "setVariable": { "variableName": "enteringNewState", "value": "false" } } ] } ] }, "onInput": { "events": [ { "eventName": "whatWasInput", "condition": "true", "actions": [ { "setVariable": { "variableName": "sensorId", "value": "$input.temperatureInput.sensorId" } }, { "setVariable": { "variableName": "reportedTemperature", "value": "$input.temperatureInput.sensorData.temperature" } } ] }, { "eventName": "changeDesired", "condition": "$input.seedTemperatureInput.desiredTemperature != $variable.desiredTemperature", "actions": [ { "setVariable": { "variableName": "desiredTemperature", "value": "$input.seedTemperatureInput.desiredTemperature" } } ] }, { "eventName": "calculateAverage", "condition": "$input.temperatureInput.sensorData.temperature < $variable.anomalousHigh && $input.temperatureInput.sensorData.temperature > $variable.anomalousLow", "actions": [ { "setVariable": { "variableName": "averageTemperature", "value": "((($variable.averageTemperature * ($variable.sensorCount - 1)) + $input.temperatureInput.sensorData.temperature) / $variable.sensorCount)" } } ] }, { "eventName": "areWeThereYet", "condition": "(timeout(\"heatingTimer\"))", "actions": [ { "setVariable": { "variableName": "goodToGo", "value": "true" } } ] } ], "transitionEvents": [ { "eventName": "anomalousInputArrived", "condition": "$input.temperatureInput.sensorData.temperature >= $variable.anomalousHigh || $input.temperatureInput.sensorData.temperature <= $variable.anomalousLow", "actions": [ { "iotTopicPublish": { "mqttTopic": "temperatureSensor/anomaly" } } ], "nextState": "heating" }, { "eventName": "highTemperatureSpike", "condition": "$input.temperatureInput.sensorData.temperature > $variable.rangeHigh", "actions": [ { "iotTopicPublish": { "mqttTopic": "temperatureSensor/spike" } }, { "sns": { "targetArn": "arn:aws:sns:us-west-2:123456789012:heatOff" } }, { "sns": { "targetArn": "arn:aws:sns:us-west-2:123456789012:coolOn" } }, { "iotTopicPublish": { "mqttTopic": "hvac/Heating/Off" } }, { "iotTopicPublish": { "mqttTopic": "hvac/Cooling/On" } }, { "setVariable": { "variableName": "enteringNewState", "value": "true" } } ], "nextState": "cooling" }, { "eventName": "lowTemperatureSpike", "condition": "$input.temperatureInput.sensorData.temperature < $variable.rangeLow", "actions": [ { "iotTopicPublish": { "mqttTopic": "temperatureSensor/spike" } } ], "nextState": "heating" }, { "eventName": "desiredTemperature", "condition": "(((($variable.averageTemperature * ($variable.sensorCount - 1)) + $input.temperatureInput.sensorData.temperature) / $variable.sensorCount) >= ($variable.desiredTemperature + $variable.allowedError)) && $variable.goodToGo == true", "actions": [ { "sns": { "targetArn": "arn:aws:sns:us-west-2:123456789012:heatOff" } }, { "iotTopicPublish": { "mqttTopic": "hvac/Heating/Off" } } ], "nextState": "idle" } ] } } ], "initialStateName": "start" }, "key": "areaId", "roleArn": "arn:aws:iam::123456789012:role/IoTEventsRole" }

响应:

{ "detectorModelConfiguration": { "status": "ACTIVATING", "lastUpdateTime": 1557523491.168, "roleArn": "arn:aws:iam::123456789012:role/IoTEventsRole", "creationTime": 1557523491.168, "detectorModelArn": "arn:aws:iotevents:us-west-2:123456789012:detectorModel/areaDetectorModel", "key": "areaId", "detectorModelName": "areaDetectorModel", "detectorModelVersion": "1" } }

批处理更新检测器示例

可以将BatchUpdateDetector操作将检测器实例置于已知状态,包括计时器和变量值。在下面的示例中,BatchUpdateDetector操作会重置受温度监测和控制区域的运行参数。通过此操作,您可以执行此操作,而无需删除、重新创建或更新检测器模型。

CLI 命令:

aws iotevents-data batch-update-detector --cli-input-json file://areaDM.BUD.json

file:areaDM.BUD.json

{ "detectors": [ { "messageId": "0001", "detectorModelName": "areaDetectorModel", "keyValue": "Area51", "state": { "stateName": "start", "variables": [ { "name": "desiredTemperature", "value": "22" }, { "name": "averageTemperature", "value": "22" }, { "name": "allowedError", "value": "1.0" }, { "name": "rangeHigh", "value": "30.0" }, { "name": "rangeLow", "value": "15.0" }, { "name": "anomalousHigh", "value": "60.0" }, { "name": "anomalousLow", "value": "0.0" }, { "name": "sensorCount", "value": "12" }, { "name": "noDelay", "value": "true" }, { "name": "goodToGo", "value": "true" }, { "name": "sensorId", "value": "0" }, { "name": "reportedTemperature", "value": "0.1" }, { "name": "resetMe", // When 'resetMe' is true, our detector model knows that we have reentered the 'start' state // to reset operational parameters, and will allow the next valid temperature sensor // reading to cause the transition to the 'idle' state. "value": "true" } ], "timers": [ ] } } ] }

响应:

{ "batchUpdateDetectorErrorEntries": [] }

BatchPutMessage 示例

例 1

使用BatchPutMessage操作来发送"seedTemperatureInput"消息,该消息为温度控制和监控下的给定区域设置操作参数。收到的任何消息Amazon IoT Events具有新的"areaId"会导致创建一个新的检测器实例。但是新的检测器实例不会将状态更改为"idle"并开始监测温度和控制加热或冷却装置,直到"seedTemperatureInput"接收新区域的消息。

CLI 命令:

aws iotevents-data batch-put-message --cli-input-json file://seedExample.json

file:seedExample.json

{ "messages": [ { "messageId": "00001", "inputName": "seedTemperatureInput", "payload": "{\"areaId\": \"Area51\", \"desiredTemperature\": 20.0, \"allowedError\": 0.7, \"rangeHigh\": 30.0, \"rangeLow\": 15.0, \"anomalousHigh\": 60.0, \"anomalousLow\": 0.0, \"sensorCount\": 10, \"noDelay\": false}" } ] }

响应:

{ "BatchPutMessageErrorEntries": [] }

2

使用BatchPutMessage操作来发送"temperatureInput"消息报告给定控制和监控区域中传感器的温度传感器数据。

CLI 命令:

aws iotevents-data batch-put-message --cli-input-json file://temperatureExample.json

file:temperatureExample.json

{ "messages": [ { "messageId": "00005", "inputName": "temperatureInput", "payload": "{\"sensorId\": \"05\", \"areaId\": \"Area51\", \"sensorData\": {\"temperature\": 23.12} }" } ] }

响应:

{ "BatchPutMessageErrorEntries": [] }

例 3

使用BatchPutMessage操作来发送"seedTemperatureInput"消息来更改给定区域所需温度的值。

CLI 命令:

aws iotevents-data batch-put-message --cli-input-json file://seedSetDesiredTemp.json

file:seedSetDesiredTemp.json

{ "messages": [ { "messageId": "00001", "inputName": "seedTemperatureInput", "payload": "{\"areaId\": \"Area51\", \"desiredTemperature\": 23.0}" } ] }

响应:

{ "BatchPutMessageErrorEntries": [] }

例如:接收 MQTT 消息

如果您的传感器计算资源无法使用"BatchPutMessage"API,但可以将他们的数据发送到 Amazon IoT Core 消息代理使用轻量级 MQTT 客户端,您可以创建 Amazon IoT Core 主题规则将邮件数据重定向到Amazon IoT Events输入。以下是Amazon IoT Events主题规则,该规则采用"areaId""sensorId"输入字段,以及"sensorData.temperature"字段从消息有效负载"temp"字段,并将这些数据引入到我们的Amazon IoT Events "temperatureInput"

如果您的传感器计算资源无法使用"BatchPutMessage"API,但可以将他们的数据发送到 Amazon IoT Core 消息代理使用轻量级 MQTT 客户端,您可以创建 Amazon IoT Core 主题规则将邮件数据重定向到Amazon IoT Events输入。以下是Amazon IoT Events主题规则,该规则采用"areaId""sensorId"输入字段,以及"sensorData.temperature"字段从消息有效负载"temp"字段,并将这些数据引入到我们的Amazon IoT Events "temperatureInput"

CLI 命令:

aws iot create-topic-rule --cli-input-json file://temperatureTopicRule.json

file:seedSetDesiredTemp.json

{ "ruleName": "temperatureTopicRule", "topicRulePayload": { "sql": "SELECT topic(3) as areaId, topic(4) as sensorId, temp as sensorData.temperature FROM 'update/temperature/#'", "description": "Ingest temperature sensor messages into IoT Events", "actions": [ { "iotEvents": { "inputName": "temperatureInput", "roleArn": "arn:aws:iam::123456789012:role/service-role/anotheRole" } } ], "ruleDisabled": false, "awsIotSqlVersion": "2016-03-23" } }

答复:[无]

如果传感器发送有关主题的消息"update/temperature/Area51/03"具有以下有效载荷。

{ "temp": 24.5 }

这会导致数据被引入到Amazon IoT Events仿佛以下"BatchPutMessage"已进行 API 调用。

aws iotevents-data batch-put-message --cli-input-json file://spoofExample.json

file:spoofExample.json

{ "messages": [ { "messageId": "54321", "inputName": "temperatureInput", "payload": "{\"sensorId\": \"03\", \"areaId\": \"Area51\", \"sensorData\": {\"temperature\": 24.5} }" } ] }

示例:生成的 Amazon SNS 消息

以下是 SNS 消息的示例,由"Area51"检测器实例。

Heating system off command> { "eventTime":1557520274729, "payload":{ "actionExecutionId":"f3159081-bac3-38a4-96f7-74af0940d0a4", "detector":{ "detectorModelName":"areaDetectorModel","keyValue":"Area51","detectorModelVersion":"1"},"eventTriggerDetails":{"inputName":"seedTemperatureInput","messageId":"00001","triggerType":"Message"},"state":{"stateName":"start","variables":{"sensorCount":10,"rangeHigh":30.0,"resetMe":false,"enteringNewState":true,"averageTemperature":20.0,"rangeLow":15.0,"noDelay":false,"allowedError":0.7,"desiredTemperature":20.0,"anomalousHigh":60.0,"reportedTemperature":0.1,"anomalousLow":0.0,"sensorId":0},"timers":{}}},"eventName":"resetHeatCool"}
Cooling system off command> {"eventTime":1557520274729,"payload":{"actionExecutionId":"98f6a1b5-8f40-3cdb-9256-93afd4d66192","detector":{"detectorModelName":"areaDetectorModel","keyValue":"Area51","detectorModelVersion":"1"},"eventTriggerDetails":{"inputName":"seedTemperatureInput","messageId":"00001","triggerType":"Message"},"state":{"stateName":"start","variables":{"sensorCount":10,"rangeHigh":30.0,"resetMe":false,"enteringNewState":true,"averageTemperature":20.0,"rangeLow":15.0,"noDelay":false,"allowedError":0.7,"desiredTemperature":20.0,"anomalousHigh":60.0,"reportedTemperature":0.1,"anomalousLow":0.0,"sensorId":0},"timers":{}}},"eventName":"resetHeatCool"}

例如:描述检测器 API

可以将DescribeDetector操作来查看检测器实例的当前状态、变量值和计时器。

CLI 命令:

aws iotevents-data describe-detector --detector-model-name areaDetectorModel --key-value Area51

响应:

{ "detector": { "lastUpdateTime": 1557521572.216, "creationTime": 1557520274.405, "state": { "variables": [ { "name": "resetMe", "value": "false" }, { "name": "rangeLow", "value": "15.0" }, { "name": "noDelay", "value": "false" }, { "name": "desiredTemperature", "value": "20.0" }, { "name": "anomalousLow", "value": "0.0" }, { "name": "sensorId", "value": "\"01\"" }, { "name": "sensorCount", "value": "10" }, { "name": "rangeHigh", "value": "30.0" }, { "name": "enteringNewState", "value": "false" }, { "name": "averageTemperature", "value": "19.572" }, { "name": "allowedError", "value": "0.7" }, { "name": "anomalousHigh", "value": "60.0" }, { "name": "reportedTemperature", "value": "15.72" }, { "name": "goodToGo", "value": "false" } ], "stateName": "idle", "timers": [ { "timestamp": 1557520454.0, "name": "idleTimer" } ] }, "keyValue": "Area51", "detectorModelName": "areaDetectorModel", "detectorModelVersion": "1" } }

Amazon IoT Core 规则引擎示例

以下规则重新发布 Amazon IoT Core MQTT 消息作为卷影更新请求消息。我们假定 Amazon IoT Core 为由探测器模型控制的每个区域的加热装置和冷却装置定义了东西. 在这个例子中,我们定义了名为"Area51HeatingUnit""Area51CoolingUnit"

CLI 命令:

aws iot create-topic-rule --cli-input-json file://ADMShadowCoolOffRule.json

file:ADMShadowCoolOffRule.json

{ "ruleName": "ADMShadowCoolOff", "topicRulePayload": { "sql": "SELECT topic(3) as state.desired.command FROM 'hvac/Cooling/Off'", "description": "areaDetectorModel mqtt topic publish to cooling unit shadow request", "ruleDisabled": false, "awsIotSqlVersion": "2016-03-23", "actions": [ { "republish": { "topic": "$$aws/things/${payload.detector.keyValue}CoolingUnit/shadow/update", "roleArn": "arn:aws:iam::123456789012:role/service-role/ADMShadowRole" } } ] } }

响应:[空]

CLI 命令:

aws iot create-topic-rule --cli-input-json file://ADMShadowCoolOnRule.json

file:ADMShadowCoolOnRule.json

{ "ruleName": "ADMShadowCoolOn", "topicRulePayload": { "sql": "SELECT topic(3) as state.desired.command FROM 'hvac/Cooling/On'", "description": "areaDetectorModel mqtt topic publish to cooling unit shadow request", "ruleDisabled": false, "awsIotSqlVersion": "2016-03-23", "actions": [ { "republish": { "topic": "$$aws/things/${payload.detector.keyValue}CoolingUnit/shadow/update", "roleArn": "arn:aws:iam::123456789012:role/service-role/ADMShadowRole" } } ] } }

响应:[空]

CLI 命令:

aws iot create-topic-rule --cli-input-json file://ADMShadowHeatOffRule.json

file:ADMShadowHeatOffRule.json

{ "ruleName": "ADMShadowHeatOff", "topicRulePayload": { "sql": "SELECT topic(3) as state.desired.command FROM 'hvac/Heating/Off'", "description": "areaDetectorModel mqtt topic publish to heating unit shadow request", "ruleDisabled": false, "awsIotSqlVersion": "2016-03-23", "actions": [ { "republish": { "topic": "$$aws/things/${payload.detector.keyValue}HeatingUnit/shadow/update", "roleArn": "arn:aws:iam::123456789012:role/service-role/ADMShadowRole" } } ] } }

响应:[空]

CLI 命令:

aws iot create-topic-rule --cli-input-json file://ADMShadowHeatOnRule.json

file:ADMShadowHeatOnRule.json

{ "ruleName": "ADMShadowHeatOn", "topicRulePayload": { "sql": "SELECT topic(3) as state.desired.command FROM 'hvac/Heating/On'", "description": "areaDetectorModel mqtt topic publish to heating unit shadow request", "ruleDisabled": false, "awsIotSqlVersion": "2016-03-23", "actions": [ { "republish": { "topic": "$$aws/things/${payload.detector.keyValue}HeatingUnit/shadow/update", "roleArn": "arn:aws:iam::123456789012:role/service-role/ADMShadowRole" } } ] } }

响应:[空]