|
17 | 17 |
|
18 | 18 | import org.junit.jupiter.api.Test; |
19 | 19 | import org.thingsboard.client.ApiException; |
| 20 | +import org.thingsboard.client.model.AlarmCalculatedFieldConfiguration; |
| 21 | +import org.thingsboard.client.model.AlarmConditionValueAlarmRuleSchedule; |
| 22 | +import org.thingsboard.client.model.AlarmRuleDefinition; |
| 23 | +import org.thingsboard.client.model.AlarmRuleSchedule; |
| 24 | +import org.thingsboard.client.model.AlarmRuleSimpleCondition; |
| 25 | +import org.thingsboard.client.model.AlarmRuleSpecificTimeSchedule; |
| 26 | +import org.thingsboard.client.model.AlarmSeverity; |
20 | 27 | import org.thingsboard.client.model.Argument; |
21 | 28 | import org.thingsboard.client.model.ArgumentType; |
22 | 29 | import org.thingsboard.client.model.CalculatedField; |
|
27 | 34 | import org.thingsboard.client.model.PageDataCalculatedField; |
28 | 35 | import org.thingsboard.client.model.ReferencedEntityKey; |
29 | 36 | import org.thingsboard.client.model.SimpleCalculatedFieldConfiguration; |
| 37 | +import org.thingsboard.client.model.TbelAlarmConditionExpression; |
30 | 38 | import org.thingsboard.client.model.TimeSeriesOutput; |
31 | 39 |
|
32 | 40 | import java.util.ArrayList; |
33 | 41 | import java.util.List; |
| 42 | +import java.util.Map; |
| 43 | +import java.util.Set; |
34 | 44 | import java.util.UUID; |
35 | 45 |
|
36 | 46 | import static org.junit.jupiter.api.Assertions.assertEquals; |
37 | 47 | import static org.junit.jupiter.api.Assertions.assertNotNull; |
| 48 | +import static org.junit.jupiter.api.Assertions.assertTrue; |
38 | 49 |
|
39 | 50 |
|
40 | 51 | public class CalculatedFieldApiTest extends AbstractApiTest { |
@@ -172,4 +183,116 @@ void testCalculatedFieldLifecycle() throws ApiException { |
172 | 183 | assertEquals(4, device1FieldsAfterDelete.getData().size()); |
173 | 184 | } |
174 | 185 |
|
| 186 | + @Test |
| 187 | + void testAlarmCalculatedFieldLifecycle() throws ApiException { |
| 188 | + long timestamp = System.currentTimeMillis(); |
| 189 | + |
| 190 | + // create a device to attach the alarm calculated field to |
| 191 | + Device device = new Device(); |
| 192 | + device.setName("AlarmCalcFieldDevice_" + timestamp); |
| 193 | + device.setType("default"); |
| 194 | + Device createdDevice = client.saveDevice(device, null, null, null, null, null); |
| 195 | + |
| 196 | + // build the alarm calculated field configuration |
| 197 | + AlarmCalculatedFieldConfiguration config = new AlarmCalculatedFieldConfiguration(); |
| 198 | + |
| 199 | + // argument: temperature time-series |
| 200 | + Argument tempArg = new Argument(); |
| 201 | + ReferencedEntityKey refKey = new ReferencedEntityKey(); |
| 202 | + refKey.setKey("temperature"); |
| 203 | + refKey.setType(ArgumentType.TS_LATEST); |
| 204 | + tempArg.setRefEntityKey(refKey); |
| 205 | + config.putArgumentsItem("temp", tempArg); |
| 206 | + |
| 207 | + // create rule: HIGH_TEMPERATURE when temp > 50 (TBEL expression) |
| 208 | + TbelAlarmConditionExpression createExpression = new TbelAlarmConditionExpression(); |
| 209 | + createExpression.setExpression("return temp > 50;"); |
| 210 | + AlarmRuleSimpleCondition createCondition = new AlarmRuleSimpleCondition(); |
| 211 | + createCondition.setExpression(createExpression); |
| 212 | + AlarmRuleSpecificTimeSchedule specificTimeSchedule = new AlarmRuleSpecificTimeSchedule().addDaysOfWeekItem(3); |
| 213 | + AlarmConditionValueAlarmRuleSchedule schedule = new AlarmConditionValueAlarmRuleSchedule().staticValue(specificTimeSchedule); |
| 214 | + createCondition.setSchedule(schedule); |
| 215 | + AlarmRuleDefinition createRule = new AlarmRuleDefinition(); |
| 216 | + createRule.setCondition(createCondition); |
| 217 | + createRule.setAlarmDetails("Temperature is too high: ${temp}"); |
| 218 | + config.setCreateRules(Map.of( |
| 219 | + AlarmSeverity.CRITICAL.name(), createRule |
| 220 | + )); |
| 221 | + |
| 222 | + // clear rule: when temp drops below 30 |
| 223 | + TbelAlarmConditionExpression clearExpression = new TbelAlarmConditionExpression(); |
| 224 | + clearExpression.setExpression("return temp < 30;"); |
| 225 | + AlarmRuleSimpleCondition clearCondition = new AlarmRuleSimpleCondition(); |
| 226 | + clearCondition.setExpression(clearExpression); |
| 227 | + AlarmRuleDefinition clearRule = new AlarmRuleDefinition(); |
| 228 | + clearRule.setCondition(clearCondition); |
| 229 | + config.setClearRule(clearRule); |
| 230 | + |
| 231 | + config.setPropagate(true); |
| 232 | + config.setPropagateToOwner(false); |
| 233 | + |
| 234 | + // create calculated field |
| 235 | + CalculatedField cf = new CalculatedField(); |
| 236 | + cf.setName(TEST_PREFIX + "AlarmCalcField_" + timestamp); |
| 237 | + cf.setType(CalculatedFieldType.ALARM); |
| 238 | + |
| 239 | + EntityId entityId = new EntityId(); |
| 240 | + entityId.setEntityType(EntityType.DEVICE); |
| 241 | + entityId.setId(createdDevice.getId().getId()); |
| 242 | + cf.setEntityId(entityId); |
| 243 | + cf.setConfiguration(config); |
| 244 | + |
| 245 | + CalculatedField created = client.saveCalculatedField(cf); |
| 246 | + assertNotNull(created); |
| 247 | + assertNotNull(created.getId()); |
| 248 | + assertEquals(cf.getName(), created.getName()); |
| 249 | + assertEquals(CalculatedFieldType.ALARM, created.getType()); |
| 250 | + AlarmCalculatedFieldConfiguration configuration = (AlarmCalculatedFieldConfiguration) created.getConfiguration(); |
| 251 | + AlarmConditionValueAlarmRuleSchedule createdSchedule = configuration.getCreateRules().get(AlarmSeverity.CRITICAL.name()).getCondition().getSchedule(); |
| 252 | + AlarmRuleSpecificTimeSchedule staticSchedule = (AlarmRuleSpecificTimeSchedule)createdSchedule.getStaticValue(); |
| 253 | + assertEquals(Set.of(3), staticSchedule.getDaysOfWeek()); |
| 254 | + |
| 255 | + // get by id and verify configuration |
| 256 | + CalculatedField fetched = client.getCalculatedFieldById(created.getId().getId().toString()); |
| 257 | + assertNotNull(fetched); |
| 258 | + assertEquals(created.getName(), fetched.getName()); |
| 259 | + assertEquals(CalculatedFieldType.ALARM, fetched.getType()); |
| 260 | + assertNotNull(fetched.getConfiguration()); |
| 261 | + AlarmCalculatedFieldConfiguration fetchedConfig = |
| 262 | + (AlarmCalculatedFieldConfiguration) fetched.getConfiguration(); |
| 263 | + assertNotNull(fetchedConfig.getCreateRules()); |
| 264 | + assertEquals(1, fetchedConfig.getCreateRules().size()); |
| 265 | + assertTrue(fetchedConfig.getCreateRules().containsKey("CRITICAL")); |
| 266 | + assertNotNull(fetchedConfig.getClearRule()); |
| 267 | + assertEquals(Boolean.TRUE, fetchedConfig.getPropagate()); |
| 268 | + |
| 269 | + // update: add a second create rule for CRITICAL_TEMPERATURE |
| 270 | + TbelAlarmConditionExpression criticalExpression = new TbelAlarmConditionExpression(); |
| 271 | + criticalExpression.setExpression("return temp > 80;"); |
| 272 | + AlarmRuleSimpleCondition criticalCondition = new AlarmRuleSimpleCondition(); |
| 273 | + criticalCondition.setExpression(criticalExpression); |
| 274 | + AlarmRuleDefinition criticalRule = new AlarmRuleDefinition(); |
| 275 | + criticalRule.setCondition(criticalCondition); |
| 276 | + fetchedConfig.putCreateRulesItem(AlarmSeverity.INDETERMINATE.name(), criticalRule); |
| 277 | + fetched.setConfiguration(fetchedConfig); |
| 278 | + |
| 279 | + CalculatedField updated = client.saveCalculatedField(fetched); |
| 280 | + AlarmCalculatedFieldConfiguration updatedConfig = |
| 281 | + (AlarmCalculatedFieldConfiguration) updated.getConfiguration(); |
| 282 | + assertEquals(2, updatedConfig.getCreateRules().size()); |
| 283 | + assertTrue(updatedConfig.getCreateRules().containsKey("INDETERMINATE")); |
| 284 | + |
| 285 | + // filter by entity and ALARM type |
| 286 | + PageDataCalculatedField deviceFields = client.getCalculatedFieldsByEntityIdV2( |
| 287 | + EntityType.DEVICE.toString(), createdDevice.getId().getId().toString(), |
| 288 | + 100, 0, CalculatedFieldType.ALARM, null, null, null); |
| 289 | + assertNotNull(deviceFields); |
| 290 | + assertEquals(1, deviceFields.getData().size()); |
| 291 | + |
| 292 | + // delete and verify |
| 293 | + UUID fieldId = created.getId().getId(); |
| 294 | + client.deleteCalculatedField(fieldId.toString()); |
| 295 | + assertReturns404(() -> client.getCalculatedFieldById(fieldId.toString())); |
| 296 | + } |
| 297 | + |
175 | 298 | } |
0 commit comments