• Using Rule Actions in Windows Azure Service Bus Subscriptions

    Published by on January 6th, 2012 7:50 pm under Service Bus, Windows Azure

    1 Comment

    Setting rule actions in Service Bus Subscriptions is a useful mechanism for automatically modify properties of BrokeredMessages when they are sent to a Topic.

    The easiest way for assigning a rule action to a subscription is to do it when the subscription is being created:

    namespaceManager.CreateSubscription(
        topicName, subscriptionName,
        new RuleDescription { Action = new SqlRuleAction("set dcount=[sys].DeliveryCount") });
    

    Here we are setting the value of the DeliveryCount property of the BrokeredMessage object to a property in the header of the message (these properties can be used to route messages to specific subscriptions).

    If we need to assign multiple rule actions to a single subscription, we have to create the subscription and afterwards create the rules and assign them to the subscription:

    namespaceManager.CreateSubscription(topicName, subscriptionName);
    
    var deliveryCountRule = new RuleDescription()
    {
        Action = new SqlRuleAction("set dcount=[sys].DeliveryCount"),
    Name = "DeliveryCountRule"
    };
    
    var sizeRule = new RuleDescription()
    {
        Action = new SqlRuleAction("set sz=[sys].Size"),
    Name = "SizeRule"
    };
    
    var subscriptionClient = messagingFactory.CreateSubscriptionClient(
        topicName, subscriptionName);
    
    subscriptionClient.AddRule(deliveryCountRule);
    subscriptionClient.AddRule(sizeRule);
    

    We can combine rule actions and filters in order to set property values based on conditions:

    namespaceManager.CreateSubscription(topicName, subscriptionName);
    
    var ruleLowPrice = new RuleDescription()
    {
        Action = new SqlRuleAction("set PriceRange='Low'"),
        Filter = new SqlFilter("TotalCost < 100"),
        Name = "LowPrice"
    };
    
    var ruleMediumPrice = new RuleDescription()
    {
        Action = new SqlRuleAction("set PriceRange='Medium'"),
        Filter = new SqlFilter("TotalCost >= 100 AND TotalCost < 500"),
        Name = "MediumPrice"
    };
    
    var ruleHighPrice = new RuleDescription()
    {
        Action = new SqlRuleAction("set PriceRange='High'"),
        Filter = new SqlFilter("TotalCost >= 500"),
        Name = "HighPrice"
    };
    
    var subscriptionClient = messagingFactory.CreateSubscriptionClient(
        topicName, subscriptionName);
    
    subscriptionClient.AddRule(ruleLowPrice);
    subscriptionClient.AddRule(ruleMediumPrice);
    subscriptionClient.AddRule(ruleHighPrice);
    

    We’re almost there… The last piece of code should work, except for the fact that when the subscription is created using the CreateSubscription method, a default rule with a TrueFilter is added, which means that every message will show up in that subscription.

    To avoid that, we should remove existing rules before adding ours.

    var rules = namespaceManager.GetRules(topicName, subscriptionName);
    
    ...
    
    var subscriptionClient = messagingFactory.CreateSubscriptionClient(
        topicName, subscriptionName);
    
    foreach (var rule in rules)
        subscriptionClient.RemoveRule(rule.Name);
    
    subscriptionClient.AddRule(ruleLowPrice);
    subscriptionClient.AddRule(ruleMediumPrice);
    subscriptionClient.AddRule(ruleHighPrice);
    
    ...
    

    For more detailed information about the expressions that can be used when defining rule actions, see http://msdn.microsoft.com/en-us/library/microsoft.servicebus.messaging.sqlruleaction.sqlexpression.aspx

    Tags: ,