MB26
ServiceNow Employee
ServiceNow Employee

Recently I came across a situation that required me, in a workflow, to loop a dynamic amount of times. Normally you could use the "Turnstyle" activity to accomplish this. However the "Turnstyle" activity is limited to a static number that you manually add in. This is extremely limiting which is why, I would guess, I do not see it used that often. I gave the "Turnstyle" activity the ability to calculate the number of times it runs based on a variable name (e.g. current.something, workflow.scratchpad.something, workflow.input.something (I have not tried this input one, but should work), or some other variable you can think of. You can also specify a script to calculate and return this number. With these additional capabilities this activity can be a true loop. Maybe this activity can become more useful now. Once created this new activity should appear in your workflow Utility activities with whatever name you have specified.

Use Case:
Here was my use case if you need one. I wanted a workflow to create "X" amount of subtasks based on how many related items there were. This could also be used for Runbook automation to run a diagnostic script or configuration based on how many network adapters, web sites, or databases a particular CI has.

Here is how I did it. The update set is also attached below. Be sure to take off the .txt. It has to end in .xml, but this blog does not allow .xml to be uploaded.

  1. Copy the current Turnstyle activity definition to maintain the current activity for any future upgrades.
    • Go to Workflow --> Activity Definition --> Turnstyle
      Change its name. Maybe something like "Turnstyle Looper". Then right click on the top bar and click "insert and stay".

  2. Copy the following code into the newly created activity script field



    // Workflow activity definition handler class
    //
    // Implement activity definition handling in the onExecute method
    //
    // Implement any event handlers for the activity definition as a method named 'on[event_name]'
    // For example, to handle the 'cancel' event, implement an 'onCancel' method
    //

    var Turnstyle_with_VariableActivityHandler = Class.create();
    Turnstyle_with_VariableActivityHandler.prototype = Object.extendsObject(WFActivityHandler, {

    initialize: function() {
    var schpdName = 'iterations_' + activity.activity.sys_id;
    WFActivityHandler.prototype.initialize.call(this);
    if (!workflow.scratchpad[schpdName]) {
    workflow.scratchpad[schpdName] = 1;
    }
    },

    onExecute: function() {
    // implement activity definition code here
    var schpdName = 'iterations_' + activity.activity.sys_id;

    var iterCountVar = parseInt(workflow.scratchpad[schpdName], 10);

    if(activity.vars.turnstyletype == 'variable'){
    var thevar = workflow.eval(activity.vars.workflowvar);
    var iterAllowedVar = parseInt(thevar, 10);
    }
    else if (activity.vars.turnstyletype == 'script') {
    var thevar = workflow.eval(activity.vars.varscript);
    var iterAllowedVar = parseInt(thevar, 10);
    }
    else {
    var iterAllowedVar = parseInt(activity.vars.iterations, 10);
    }

    if (iterCountVar > iterAllowedVar) {
    //Youve iterated too many times...stop iterating
    activity.result = 'cancel';

    } else {
    //Still iterating
    iterCountVar ++;

    workflow.scratchpad[schpdName] = iterCountVar;
    activity.result = 'continue';
    }
    },

    type: 'Turnstyle_with_VariableActivityHandler'
    });

  3. Add some variables
    Since we did an insert and stay the previous variables, conditions, and UI Policies get dropped out.
    • Column Name: turnstyletype , Label: "Turnstyle Type" , Type: string - make it a choice with no dropdown and default of "static" , Order: 10 , with the below choice list

      1. Label: "Static Value" , Value: static , Sequence: 10
      2. Label: "Variable" , Value: variable , Sequence: 20
      3. Label: "Script" , Value: script , Sequence: 30


    • Column Name: iterations , Label: "Allowed Iterations" , Type: integer , Order: 20
    • Column Name: workflowvar , Label: "Variable Name" , Type: string , Order: 30
    • Column Name: varscript , Label: "Script" , Type: script , Order: 40

  4. Add the same condition defaults as the standard Turnstyle activity
    • Name: "Continue" , Condition: activity.result == 'continue' , Short Description: Continue iterating
    • Name: "Cancel" , Condition: activity.result == 'cancel' , Short Description: You've looped too many times...cancel iterating

  5. Add some UI policies so that if the Static choice is selected, the "Allowed Iterations" is displayed. Or the Variable shows the "Variable Name", or the Script shows the script field.


Attached are some screenshots of what the Activity looks like in the workflow.

<script></script>
var _gaq = _gaq || [];
_gaq.push(['_setAccount', 'UA-22945975-1']);
_gaq.push(['_trackPageview']);

(function() {
var ga = document.createElement('script'); ga.type = 'text/javascript'; ga.async = true;
ga.src = ('https:' == document.location.protocol ? 'https://ssl' : 'http://www') + '.google-analytics.com/ga.js';
var s = document.getElementsByTagName('script')[0]; s.parentNode.insertBefore(ga, s);
})();

4 Comments