Stagger Jobs by time interval

Andrew (22 posts)
July 30, 2013 09:03 AM
Accepted Answer

Hi,

I am scheduling jobs to start processes on our accounting system. Due to a limitation in the system, I can't start two jobs at the same time so I need to stagger them by 5 minutes. There are 5 jobs that all need to start after 6:30pm. They are currently scheduled 5 minutes apart starting at 6:30pm. This schedule is not ideal since if we're running late, I have to Hold each job and then release them manually with 5 minutes in between.

Is there a way to code a condition that will start based on another job but add 5 minutes?

I have two approaches that will probably work but I'm not too crazy about. There are supportability problems with each of these options.

1. Write a script that will sleep for 5 minutes and use it as a condition in the job.
2. Write a script that will sleep for 5 minutes and set it as Step 1 of the job.

 

Does anyone have any thoughts on this? My end goal is to be able to trigger the first job and then have the rest kick off in 5 minute intervals.

Thank you,
Andrew

 

Bill Staff (599 posts)
July 30, 2013 11:04 AM
Accepted Answer

That's a good question, and I'm surprised it hasn't come up before and we don't have some built-in support for it. I think your option 1 is the best bet. You would want to schedule the first job for 6:30, then use Responses to chain the other jobs together (so that they don't need their own triggers).

Create a Shared Script that sleeps for 5 minutes, and add that as a Script Condition for each of the remaining jobs.

A few notes:

Make sure, when you set up the Job  Control Actions in your Responses, that you don't check the option to ignore conditions for the target job.

To do the sleep, call the adTempus.Sleep method rather than Thread.Sleep:

adTempus.Sleep(5*60*1000)

 

That way you should be able to cancel the wait by forcing execution of a job that's waiting for the condition.

What are the supportability problems that see with this approach?

Andrew (22 posts)
August 9, 2013 01:20 PM
Accepted Answer

Thanks for the feedback. I had some dualing priorities and had to put this down for a little bit. I'm back with an update though. I was able to get this working successfully with this approach:

1. Trigger job fires and completes successfully.
2. A response on the trigger job starts each downstream job
3. Each downstream job has a variable that stores it's wait time.
4. A script condition on each downstream job reads the variable and does a Thread.Sleep for that length of time.

I was not able to use adTempus.Sleep. I got an error that the method does not exist in the adTempus object. I would prefer to use this if it will let me force the execution of the job.

The supportability issue is that in a re-run scenario, if the operator does not ignore conditions on a job with a 20 minute wait, there's no way to terminate the execution. It sounds like the adTempus.Sleep method would take care of this if you can help me resolve my issue using that method.

 

Bill Staff (599 posts)
August 9, 2013 02:19 PM
Accepted Answer

You're right--there's no Sleep method on the adTempus object for .NET scripts.  It's there for VBScript but we left it out for .NET. It's been added for .NET in adTempus 4.

You can configure things so that the script only applies the timeout if the job is being run by a Response. To do this, the script should retrieve the value of the "ADTExecutionReason" JobVariable. This will be a string description of the reason the job is being run. If it was started by a Response, the reason will start with "Job control action".

Here's the full script (in case anyone else needs to do something similar), assuming that the variable where you're setting the delay time is called "DelayMinutes":

Imports System
Imports System.Collections
Imports ArcanaDevelopment.adTempus.Server
 
Public Class UserScript
    Inherits ArcanaDevelopment.adTempus.ScriptEngine.UserScriptBase
 
    Public Overrides Function Run() As Object
 
        Dim waitTime As Integer
        If adTempus.JobVariables("ADTExecutionReason").StartsWith("Job control action") Then
            'only apply delay if job is being run by a Job Control Action from a Response
            If Integer.TryParse(adTempus.JobVariables("DelayMinutes"),waitTime) Then
            'waitTime value is delay in minutes; convert to milliseconds
                System.Threading.Thread.Sleep(waitTime*60*1000)
            End If
        End If
        Return 0
    End Function
End Class

Replies are disabled for this topic.