Custom rule created via Rules Engine API does not trigger on property changes

We’re dynamically creating alert rules through the Rules Engine API to monitor equipment temperature thresholds, but the rules never trigger even when property values clearly exceed the configured thresholds. This is causing missed alerts for critical equipment conditions.

The rule activation status shows as enabled in Composer, and API logging confirms the rule was created successfully. However, event binding validation shows no active subscriptions for the property changes we’re monitoring.

var ruleConfig = {
  name: 'TempAlert_' + equipmentId,
  property: 'temperature',
  condition: 'greaterThan',
  threshold: 85,
  action: 'SendAlert'
};
Things['RulesEngine'].CreateRule(ruleConfig);

Manually created rules work fine, but API-generated rules don’t fire. What’s different about rules created programmatically versus through the UI?

How do I call BindToProperty? I don’t see that method documented in the Rules Engine API. Is there a specific service or do I need to create the subscription separately using the event framework?

Don’t forget to enable logging on the Rules Engine subsystem. Set the log level to DEBUG and you’ll see exactly what’s happening when property changes occur - whether the rule is being evaluated, what values it’s seeing, and why it might not be triggering. This is essential for debugging API-created rules.

Check your rule’s enabled state in the configuration table, not just in Composer. Sometimes rules show as enabled in the UI but are actually disabled in the database due to validation failures during creation. Query the Rules table directly to see the actual status.

Also verify that the property you’re monitoring has its pushType set to ‘ALWAYS’ or ‘VALUE’. If it’s set to ‘NEVER’, property changes won’t generate events and your rule will never trigger regardless of how it’s configured. This is a common oversight when working with remote Things.

You need to create a subscription on the Thing that owns the property, not on the RulesEngine. After creating the rule, add a subscription that calls the rule’s Evaluate service whenever the temperature property changes. The subscription is what actually triggers rule evaluation - the rule itself is just the logic.

Rules created via API don’t automatically bind to property change events. You need to explicitly call BindToProperty after creating the rule. The UI does this automatically, but the API requires you to set up the subscription manually. Check if your rule has an active event binding in the Subscription table.

Here’s the complete solution covering all three focus areas:

Event Binding Validation: The core issue is that API-created rules don’t automatically establish event bindings. You must create the subscription explicitly:

// First, create the rule
var ruleConfig = {
  name: 'TempAlert_' + equipmentId,
  property: 'temperature',
  condition: 'greaterThan',
  threshold: 85,
  alertMessage: 'Temperature exceeded',
  enabled: true
};
var ruleName = Things['RulesEngine'].CreateRule(ruleConfig);

// Then bind it to the property via subscription
var equipmentThing = Things[equipmentId];
equipmentThing.AddPropertyChangeSubscription({
  propertyName: 'temperature',
  eventName: 'DataChange',
  source: equipmentId,
  sourceProperty: 'temperature'
});

The subscription creates the actual event binding that monitors property changes. Without it, the rule exists but never executes.

Validate bindings after creation:

var subscriptions = equipmentThing.GetPropertySubscriptions();
logger.info('Active subscriptions: ' + JSON.stringify(subscriptions));

Ensure you see your temperature property in the list with an active binding to the Rules Engine.

Rule Activation Status: Verify the rule is truly active at multiple levels:

  1. Check configuration status:
var rule = Things['RulesEngine'].GetRule({ruleName: ruleName});
if (!rule.enabled) {
  Things['RulesEngine'].EnableRule({ruleName: ruleName});
}
  1. Verify the Thing property configuration:
var propDef = equipmentThing.GetPropertyDefinition({
  propertyName: 'temperature'
});
if (propDef.pushType !== 'ALWAYS') {
  logger.warn('Property pushType must be ALWAYS for rules');
}
  1. Test the rule manually:
Things['RulesEngine'].EvaluateRule({
  ruleName: ruleName,
  currentValue: 90
});

This forces evaluation and confirms the rule logic works correctly.

API Logging: Enable comprehensive logging to diagnose rule execution:

  1. Set Rules Engine logging to DEBUG in log4j.properties:

log4j.logger.com.thingworx.rules=DEBUG
  1. Add custom logging in your rule action:
var ruleConfig = {
  name: 'TempAlert_' + equipmentId,
  property: 'temperature',
  condition: 'greaterThan',
  threshold: 85,
  action: function(value) {
    logger.warn('RULE TRIGGERED: ' + equipmentId +
      ' temp=' + value);
    Things['AlertService'].SendAlert({
      equipment: equipmentId,
      value: value,
      threshold: 85
    });
  },
  enabled: true
};
  1. Monitor the ApplicationLog for rule evaluation entries:

    • Look for “Evaluating rule: TempAlert_XXX”
    • Check for “Rule condition met” or “Rule condition not met”
    • Verify property values being evaluated match expectations
  2. Create a diagnostic service to verify rule setup:

function ValidateRule(equipmentId) {
  var ruleName = 'TempAlert_' + equipmentId;
  var rule = Things['RulesEngine'].GetRule({ruleName: ruleName});
  var thing = Things[equipmentId];
  var subs = thing.GetPropertySubscriptions();

  return {
    ruleExists: rule !== undefined,
    ruleEnabled: rule ? rule.enabled : false,
    hasSubscription: subs.some(s => s.property === 'temperature'),
    currentValue: thing.temperature,
    threshold: rule ? rule.threshold : null
  };
}

Run this diagnostic for each equipment item to identify configuration gaps.

Additional considerations:

  • Rules created via API don’t persist across server restarts unless you save them to a persistent Thing or configuration table
  • Use Thing Templates for equipment that needs identical rules - create the subscription in the template rather than via API
  • Implement rule health monitoring that periodically validates all API-created rules are still active and bound correctly

The key difference between UI-created and API-created rules is that the UI automatically handles subscription creation and property binding, while the API requires explicit configuration of each component.