Starting Point

  • Users would like to check in individual job scripts or monitor scripts
    • if a job has been executed in the current period, e.g. for the current day
    • what execution result (success/failure) was created on completion of the job
  • The intention for checking the job execution history is to automate decision making based on the point in time or execution result of a previous job start.

Feature

  • FEATURE AVAILABILITY STARTING FROM RELEASE 1.10.2
  • This feature 
    • is available with
      JITL-217 - Getting issue details... STATUS
    • is a subset of
      JITL-212 - Getting issue details... STATUS
  • A JobHistory object is provided for job history checks that can be used
    • in individual jobs that are implemented with Java or JavaScript.
    • in individual job monitors that are implemented with Java or JavaScript.
  • The JobHistory object returns a JobHistoryInformation object for a given job that contains the history of the job runs.
  • The JobHistoryInformation object provides a set of JobHistoryInformationEntry objects that expose the history information for the respective job runs.

JobHistory Object

This object is instantiated by a job or job monitor and provides the method to retrieve a JobHistoryInformation object for a given job.

ObjectDescription
jobHistory = new Packages.com.sos.jitl.checkrunhistory.JobHistory( spooler.delegate )
object for use with jobs and job monitors that are implemented with Java or JavaScript
Methods 
jobHistoryInfo = jobHistory.getJobInfo( jobname, limit, timelimit )

retrieves the JobHistoryInformation object within the specified limits:

  • jobname: for a specific job (a relative name or absolute path)
  • limit: for the specified number of entries from the job history
  • timelimit: for a specific point in time up to that the job history is considered
    • it is a from to intervall
    • the default for from is 00:00:00
    • the default for to is the current time
    • the interval is specified with from..to
    • if a single time is given, it is the from time.
jobHistory.getNumberOfCompleted()The number of completed entries
jobHistory.getNumberOfStarts()The number of starts
jobHistory.getNumberOfCompletedSuccessful()The number of completed runs with a state that is not an error state
jobHistory.getNumberOfCompletedWithError()The number of completed runs with a state that is an error state
jobHistory.getCount()The number of entries

JobHistoryInformation Object

This object is returned by the JobHistory object for a given job and provides a set of JobHistoryInformationEntry objects for the respective job runs.

ObjectDescription
jobHistoryInfo = jobHistory.getJobInfo( jobname, limit, timelimit )
The JobHistoryInformation object is retrieved from the JobHistory object for a given job.
Methods Description
Retrieve JobHistoryInformationEntry objects
JobSchedulerHistoryInfoEntry jobHistoryInfo.getRunning()Get the JobSchedulerHistoryInfoEntry object for the current job run.
JobSchedulerHistoryInfoEntry jobHistoryInfo.getLastExecution()Get the JobSchedulerHistoryInfoEntry object for the most recently started job run including running jobs and jobs that completed successfully or failed with error.
JobSchedulerHistoryInfoEntry jobHistoryInfo.getLastCompleted()Get the JobSchedulerHistoryInfoEntry object for the most recently completed job run including jobs that completed successfully or failed with error.
JobSchedulerHistoryInfoEntry jobHistoryInfo.getLastCompletedSuccessful()Get the JobSchedulerHistoryInfoEntry object for the most recently successfully completed job run.
JobSchedulerHistoryInfoEntry jobHistoryInfo.getLastCompletedWithError()Get the JobSchedulerHistoryInfoEntry object for the most recently completed job run that failed with error.
Checks for any job runs in the period of the current day
boolean jobHistoryInfo.isStartedToday()Indicates that a job run started within the current period and applies to running jobs and completed job runs.
boolean jobHistoryInfo.isStartedTodayCompleted()Indicates that a job run started and completed within the current period and applies to job runs that completed successfully or failed with errror.
boolean jobHistoryInfo.isStartedTodayCompletedSuccessful()Indicates that a job run started and completed successfully within the current period.
boolean jobHistoryInfo.isStartedTodayCompletedWithError()Indicates that a job run started and completed with error within the current period.
Checks for any job runs that completed today 
boolean jobHistoryInfo.isCompletedToday()Indicates that a job run completed in the current period and applies to job runs that completed successfully or failed with error.
boolean jobHistoryInfo.isCompletedTodaySuccessful()

Indicates that a job run completed successfully within the current period.

boolean jobHistoryInfo.isCompletedTodayWithError()Indicates that a job run completed with error within the current period.
Checks for any job runs that ended after a specific point in time

boolean jobHistoryInfo.isCompletedAfter( "03:00:00" )

boolean jobHistoryInfo.endedAfter( "03:00:00" )

indicates that a job run completed after the given date

boolean jobHistoryInfo.isCompletedWithSuccessfulAfter( "03:00:00" )

boolean jobHistoryInfo.endedWithSuccessfulAfter( "03:00:00" )

indicates that a job run completed successfully after the given date

boolean jobHistoryInfo.isCompletedWithErrorAfter( "03:00:00" )

boolean jobHistoryInfo.endedWithErrorAfter( "03:00:00" )

indicates that a job run completed with error after the given date
Checks for any job runs that started after a specific point in time
boolean jobHistoryInfo.startedAfter( "03:00:00" )

indicates that a job run started after the given date, the job might be completed or running

boolean jobHistoryInfo.startedSuccessfulAfter( "03:00:00" )indictes that a job run started after the given date and does not report any errors, the job might be completed or running
boolean jobHistoryInfo.startedWithErrorAfter( "03:00:00" )indicates that a job run started after the given date and does report errors, the job might be completed or running

JobHistoryInformationEntry Object

The object represents the history for a specific job run and is provided by the JobHistoryInformation object.

ObjectDescription
JobSchedulerHistoryInfoEntry jobHistoryInfo.getRunning()Get the JobSchedulerHistoryInfoEntry object for the current job run. If used in a job's pre-processing monitor then this method will return an empty object as the job is not currently running.
JobSchedulerHistoryInfoEntry jobHistoryInfo.getLastExecution()Get the JobSchedulerHistoryInfoEntry object for the most recently started job run including running jobs and jobs that completed successfully or failed with error.
... 
PropertyDescription
nameContains the job name.
foundIndicates if the associated object is not null.
idExposes the unique task identification as provided by JobScheduler.
positionReturns the position of the object in the job execution history: a value 0 signals the most recent entry, larger values suggest older entries.
startReturns the start date of the job run.
endReturns the end date of the job run.
durationReturns the duration in the format hh:mm:ss. If longer the one day d:hh:mm:ss
executionResultProvides the exit code for shell jobs or -1 if no exit code is provided, e.g. for API jobs.
errorIndicats an error status, 1=error, 0=no error.
errorMessageReturns the error message as provided e.g. for shell jobs by the operating system, for API jobs from exceptions.
errorCodeOptionally returns an error code, e.g. from API jobs that raise defined exceptions.

Usage

Use with a Job Script

A complete sample files demonstrates the use of 


function spooler_process()  {

    // using the current job name and default limit
    var jobHistoryInfo = getJobHistoryInfoObject();

    // using the current job name and the given limit        
    // var jobHistoryInfo = getJobHistoryInfoObject( "", 30 );

    // using the given job name and default limit
    // var jobHistoryInfo = getJobHistoryInfoObject( "job1" );

    // using the given job name and the given limit
    // var jobHistoryInfo = getJobHistoryInfoObject( "job1", 20 );

    // reporting some info on job runs
    report( jobHistoryInfo.getRunning() );
    report( jobHistoryInfo.getLastCompleted() );
    report( jobHistoryInfo.getLastCompletedSuccessful() );
    report( jobHistoryInfo.getLastCompletedWithError() );

    // report on currently running job
    report( jobHistoryInfo.getLastExecution() );
 
    spooler_log.info("isStartedToday: " + jobHistoryInfo.isStartedToday());
    spooler_log.info("isStartedTodayCompletedSuccessful: " + jobHistoryInfo.isStartedTodayCompletedSuccessful());
    spooler_log.info("isStartedTodayCompletedWithError: " + jobHistoryInfo.isStartedTodayCompletedWithError());
    spooler_log.info("isStartedTodayCompleted: " + jobHistoryInfo.isStartedTodayCompleted());
    spooler_log.info("isCompletedToday: " + jobHistoryInfo.isCompletedToday());
    spooler_log.info("isCompletedTodaySuccessful: " + jobHistoryInfo.isCompletedTodaySuccessful());
    spooler_log.info("isCompletedTodayWithError: " + jobHistoryInfo.isCompletedTodayWithError());

    spooler_log.info("endedAfter: " + jobHistoryInfo.endedAfter("03:00:00"));
    spooler_log.info("endedWithErrorAfter: " + jobHistoryInfo.endedWithErrorAfter("03:00:00"));
    spooler_log.info("endedSuccessfulAfter: " + jobHistoryInfo.endedSuccessfulAfter("03:00:00"));

    spooler_log.info("startedAfter: " + jobHistoryInfo.startedAfter("03:00:00"));
    spooler_log.info("startedWithErrorAfter: " + jobHistoryInfo.startedWithErrorAfter("03:00:00"));
    spooler_log.info("startedSuccessfulAfter: " + jobHistoryInfo.startedSuccessfulAfter("03:00:00"));

    // example how to convert Date fields (start date)
    if ( jobHistoryInfo.getLastCompletedSuccessful().found ) {
        var d = jobHistoryInfo.getLastCompletedSuccessful().start;
        if (d != null) {
            var d2 = new Date(d.getTime());
            spooler_log.info ("------->" + d2.getFullYear() );
        }
    }

    spooler_log.info ( "check if the job started on the previous day before a specific point in time" );
    var jobHistoryInfo = getJobHistoryInfoObject( "", "", "-1:10:43:56" );
    spooler_log.info ( "endedBefore -1:10:43:56: " + jobHistoryInfo.getLastCompleted().found );
    spooler_log.info( "endedBeforeWithError -1:10:43:56: " + jobHistoryInfo.getLastComletedWithError().found );
    spooler_log.info( "endedBeforeSuccessful -1:10:43:56: " + jobHistoryInfo.getLastCompletedSuccessful().found );
     
    return false;
}

function getJobHistoryInfoObject(jobname, limit, timelimit) {
    var jobHistory = new Packages.com.sos.jitl.checkrunhistory.JobHistory( spooler.delegate );

    if ((jobname === undefined) || (jobname === "")) {
      jobname = spooler_task.job.name;
    }
    if (limit === undefined || limit === "") {
       limit = "100";
    }
    if (timelimit === undefined) {
       timelimit = "";
    }

    var jobHistoryInfo = jobHistory.getJobInfo( jobname, limit, timelimit );
   
     spooler_log.info("Number of completed: " + jobHistory.getNumberOfCompleted());
    spooler_log.info("Number of starts: " + jobHistory.getNumberOfStarts());
    spooler_log.info("Number of completed successfull: " + jobHistory.getNumberOfCompletedSuccessful());
    spooler_log.info("Number of completed with error: " + jobHistory.getNumberOfCompletedWithError());
    spooler_log.info("Number of entries: " + jobHistory.getCount());

    return jobHistoryInfo;
}

function report( reportItem ) {
    spooler_log.info( "_____________________________" );
    if (reportItem.found) {
        spooler_log.info( "Name:" + reportItem.name );
        spooler_log.info( "Task ID: " + reportItem.id );
        spooler_log.info( "Job Name: " + reportItem.jobName );
        spooler_log.info( "Position: " + reportItem.position );
        spooler_log.info( "Start Time: " + reportItem.start );
        spooler_log.info( "End Time: " + reportItem.end );
        spooler_log.info( "Exit Code: " + reportItem.executionResult );
        spooler_log.info( "Error Message: " + reportItem.errorMessage );
        spooler_log.info( "Error: " + reportItem.error );
        spooler_log.info( "ErrorCode: " + reportItem.errorCode );
    } else {
        spooler_log.info( "Name: " + reportItem.name + " not found" );
    }
}

Use with a Monitor Script

To identify if a running job is a rerun of a previously failed job execution you can use the following script for a pre-processing monitor. The script will expose the information if a rerun has been identified with the environment variable SCHEDULER_PARAM_IS_RERUN


function spooler_task_before() {
    var jobHistory = new Packages.com.sos.jitl.checkrunhistory.JobHistory( spooler.delegate );
    var jobHistoryInfo = jobHistory.getJobInfo( spooler_task.job.name, 100, "" );
    var isRerun = (jobHistoryInfo.getLastCompletedWithError().found && jobHistoryInfo.getLastCompletedWithError().position == 0);

    var params = spooler_task.params;
    params.set_var("IS_RERUN", isRerun );
    spooler_log.info("Job rerun identified: " + isRerun);

    return true;
}

Explanations

  • The script retrieves the last job execution that completed with error and checks if the position of the object provided is the first in the recent history list. The first position of a job that recently completed with error is
    • 0 if the script is executed as a pre-processing monitor script before a task start.
    • 1 if the script is executed as a job script for a running task. That task would be added to the begin of the recent history list.
  • In order to check if a job did run before a given point in time you can query a job history object that takes a time limit into consideration as from the following samples:
    • jobHistoryInfo = jobHistory.getJobInfo( "job1", 100, "-1:10:43:56" );
      
      spooler_log.info( "endedBefore -1:10:43:16:" + jobHistoryInfo.getLastCompleted().found );
      spooler_log.info( "endedBeforeWithError -1:10:43:16:" + jobHistoryInfo.getLastComletedWithError().found );
      spooler_log.info( "endedBeforeSuccessful -1:10:43:16:" + jobHistoryInfo.getLastCompletedSuccessful().found );
    • jobHistory.setTimeLimit( "-1:10:43:56" );
      jobHistoryInfo = jobHistory.getJobInfo( "job1", 100, "" );
      
      spooler_log.info( "endedBefore -1:10:43:16:" + jobHistoryInfo.getLastCompleted().found );
      spooler_log.info( "endedBeforeWithError -1:10:43:16:" + jobHistoryInfo.getLastComletedWithError().found );
      spooler_log.info( "endedBeforeSuccessful -1:10:43:16:" + jobHistoryInfo.getLastCompletedSuccessful().found );

Implementation

  • The implementation makes use of API methods, i.e. XML commands, to retrieve the job history instead of a database connection.
  • The solution can be used with Agents.
  • No separate HTTP connection is created, the solution makes use of the HTTP(S) connection that is established between Master and Agent.

References

Change Management References

T Key Linked Issues Fix Version/s Status P Summary Updated
Loading...
Refresh

Documentation