Job and Folder Properties¶
[1]:
from aapi import *
Allowed arguments for both Folder, SubFolder and Jobs:
application: Descriptive name for a set of related Jobs, Folders or SubFolders
sub_application: Descriptive name for a set of related Jobs, Folders or SubFolders with a same application
run_as : The OS user responsible for running a job (or all jobs in a folder or subfolder). By default, jobs are run by the user account where the Control-M/Agent is installed. To specify a diferent user, the agent must be running as root
days_keep_active : Defines the number of days to keep a job if the job did not run at its scheduled date. You can set this property for a Job, Folder, or SubFolder. Jobs in a folder are kept until the maximum DaysKeepActive value for any of the jobs in the folder has passed. This enables you to retrieve job status of all the jobs in the folder
confirm : Defines a job, folder, or subfolder that requires user confirmation
created_by: Specifies the Control‑M user responsible for job definitions. You can define this property for a Job object or Folder object
description : Description of th Job, Folder or SubFolder
priority : Defines the priority that a job has over other jobs. You can set this property for a Job, Folder, or SubFolder
run_as_dummy : (boolean) Runs any job as a dummy job
retroactive_order : (boolean) Orders a job retroactively to make up for days on which the job did not run. For example, Control-M was down for two days due to a hardware issue; as soon as jobs can run again, this job is scheduled retroactively to run an additional two times, to make up for the days that Control-M was inactive
rerun : See below
Rerun
sectiontime_zone : Adds the time zone to jobs, folder, or subfolder. Time zones should be defined at least 48 hours before the intended execution date. We recommend to define the same time zone for all jobs in a folder
variables : list of variables in a key, value format. See below
Variables
when : See below
When
sectionif_list : List of
If
objects. See belowIf
sectionnotify_list List of
Notify
objects. See belowNotify
[2]:
folder = Folder('SampleFolder',
controlm_server='ctmserver',
site_standard='sitestd',
business_fields=[{'Department': 'HR'}, {'Company': 'BMC'}],
order_method=Folder.OrderMethod.Manual,
application='ApplicationName',
sub_application='SubApplication',
run_as='controlm',
when=Folder.When(week_days=['SUN']),
active_retention_policy=Folder.ActiveRetentionPolicy.KeepAll,
days_keep_active='41',
confirm=True,
created_by='user',
description='FolderSample with lot of properties set',
priority=Folder.Priority.High,
rerun=Folder.Rerun(every='2'),
rerun_limit=Folder.RerunLimit(times='3'),
time_zone='HAW',
variables=[{'var1': 'val'}, {'var2': 'val2'}]
)
folder.sub_folder_list.append(
SubFolder('MySubFolder1', job_list=[
# this job will run as dummy, the command will not be executed
JobCommand('MyFirstJob', command='ls', run_as_dummy=True),
# This job is marked as 'confirm', it will not run until user confirms
JobCommand('OtherJob', command='ls', confirm=True),
],
if_list=[
IfCompletionStatus('goodScenario', completion_status='OK', on_list=[
ActionMail('sendMail', message='All jobs ran successfully',
to='team@comp.com', subject='Jobs notification')
]),
IfCompletionStatus('badScenario', completion_status='NOK', on_list=[
ActionRun('runCorrectiveJob',
folder='REMEDY_FOLDER', job='RemedyJob')
])
],
notify_list=[
NotifyNotOK(
'alertIfNOK', destination=Notify.Destination.Alerts, message='Jobs not ok'),
NotifyDoesNotEnd('alertIfJobIsStuck', by='1200',
destination=Notify.Destination.Alerts, message='Jobs didnt end'),
]
)
)
When¶
Enables you to define scheduling parameters for Jobs, Folders and SubFolders, including the option of using calendars. If When is used in a Folder or SubFolder, those parameters apply to all Jobs in the Folder or Subfolder.
Note: Several parameters under the When parameter enable you to reference previously defined calendars.
When working in a Control-M Workbench environment, jobs will not wait for time constants and will run in an ad-hoc manner. Once deployed to a Control-M instance, all time constraints will be obeyed.
Parameters:
week_days
Note: Not supported in SubFolder
One or more of the following: “SUN”,”MON”,”TUE”,”WED”,”THU”,”FRI”,”SAT”
For all days of the week, use “ALL” (the default value). In addition, you can specify a specific day in a specific week of the month using a value with the following format: DdayWn
For example, DMONW2 means Monday of the 2nd week of the month. Valid values for n are 1-6.
months
Note: Not supported in SubFolder
One or more of the following:
“JAN”, “FEB”, “MAR”, “APR”,”MAY”,”JUN”, “JUL”, “AUG”,
“SEP”, “OCT”, “NOV”, “DEC”
For all months of the year, use “ALL” (the default value).
month_days
Note: Not supported in SubFolder
One or more days in the range of 1 to 31
For all days of the month, use “ALL” (the default value).
from_time
FromTime specifies that a job will not start before this time
Format: HHMM
to_time
ToTime specifies that a job will not start after this time
Format: HHMM
To allow the job to be submitted even after its original scheduling date (if it was not submitted on the original date), specify a value of “>”.
schedule
Note: Not supported in SubFolder
One of the following options:
- "Everyday" - scheduling is applied every day, provided that the running criteria are met
- "Never" - no scheduling is defined, and the job must be ordered manually
specific_dates
Note: Not supported in SubFolder
Specific dates for running jobs.
For each date, use the format “MM/DD” (enclosed in quotes). Separate multiple dates with commas.
Note: The SpecificDates option cannot be used in combination with options WeekDays, Months, or MonthDays. However, since the default for these options is “ALL”, you must specify these options with a value of “NONE”.
[3]:
when = Job.When(
schedule='Never',
months=['JAN', 'OCT', 'DEC'],
month_days=['22', '1', '11'],
week_days=['MON', 'TUE'],
from_time='1500',
to_time='1800'
)
# example with specific dates
when = Job.When(
week_days=['NONE'],
months=['NONE'],
month_days=['NONE'],
specific_dates=['03/10', '03/01']
)
If¶
If statements trigger one or more actions when job-related criteria are fulfilled (for example, the job ended with a specific status or the job failed several times).
IfCompletionStatus¶
Triggers actions based on job completion status. In this example, if the job runs unsuccessfully, it sends an email and runs another job. You can set this property for a Job, Folder, or SubFolder
[4]:
job = JobCommand('Job1', command='echo Hello')
job.if_list.append(
IfCompletionStatus('action_if_failure',
completion_status='NOTOK',
on_list=[
ActionMail(
'mailToTeam', message='Job %%JOBNAME failed', to='myteam@mail.com'),
ActionRun('runcorrectiveJob',
folder='FolderName', job='JobName')
]
)
)
IfNumberOfReruns¶
Trigger an action based on number of job reruns. You can set this property for a Job, Folder, or SubFolder
[5]:
job = JobCommand('Job2', command='echo Hello')
job.if_list.append(
IfNumberOfReruns('actionByNumberOfReruns',
number_of_reruns='>=4',
on_list=[ActionRun('RunJob', folder='Folder1', job='Job1')])
)
IfNumberOfFailures¶
Triggers an action based on number of job failures. You can set this property for a Job, Folder, or SubFolder
[6]:
job = JobCommand('Job2', command='echo Hello')
job.if_list.append(
IfNumberOfFailures('ActionByNumberOfFailures',
number_of_failures='1',
on_list=[ActionRun('RunJob', folder='Folder1', job='Job1')])
)
IfJobNotSubmitted¶
Triggers an action based on whether the job is not submitted
[7]:
job = JobCommand('Job2', command='echo Hello')
job.if_list.append(
IfJobNotSubmitted('ActionByJobNotSubmitted',
on_list=[ActionRun('RunJob', folder='Folder1', job='Job1')])
)
IfJobOutputNotFound¶
Triggers an action based on whether the job output is not found
[8]:
job = JobCommand('Job2', command='echo Hello')
job.if_list.append(
IfJobOutputNotFound('ActionByOutputNotFound',
on_list=[ActionRun('RunJob', folder='Folder1', job='Job1')])
)
IfNumberOfExecutions¶
Triggers an action based on number of job executions. You can set this property for a Job, Folder, or SubFolder
[9]:
job = JobCommand('Job2', command='echo Hello')
job.if_list.append(
IfNumberOfExecutions('ActionByNumberExecutions',
number_of_executions='>=5',
on_list=[ActionRun('RunJob', folder='Folder1', job='Job1')])
)
IfOutput¶
Triggers an action based on whether a specified string is found within the job output. You can set this property for a Job, Folder, or SubFolde
[10]:
job = JobCommand('Job2', command='echo Hello')
job.if_list.append(
IfOutput('OutputFound',
code='myfile.sh',
statement='ls -l',
on_list=[ActionRun('RunJob', folder='Folder1', job='Job1')])
)
IfVariableValue¶
Note: This feature requires Control-M/Enterprise Manager version 9.0.21 Triggers an action based on whether a logical condition defined for a variable value is true
[11]:
job = JobCommand('Job2', command='echo Hello')
job.if_list.append(
IfVariableValue('VariableValue',
variable_name='IpAddress',
variable_value='1',
operator=IfVariableValue.Operator.EndWith,
on_list=[ActionRun('RunJob', folder='Folder1', job='Job1')],
do_list=[ActionRun('RunJob1', folder='Folder1', job='Job1')])
)
print(job.dumps_aapi(indent=2))
{
"Type": "Job:Command",
"VariableValue": {
"Type": "If:VariableValue",
"RunJob": {
"Type": "Action:Run",
"Folder": "Folder1",
"Job": "Job1"
},
"RunJob1": {
"Type": "Action:Run",
"Folder": "Folder1",
"Job": "Job1"
},
"VariableName": "IpAddress",
"VariableValue": "1",
"Operator": "EndWith"
},
"Command": "echo Hello"
}
If Actions¶
Actions that can be triggered in response to an If statement that is fulfilled
ActionMail¶
Action that sends an e-mail
Arguments:
urgency : level of urgency of the message. Default: Regular
subject : subject line for the message
message : the message text
to : List of recipients separated by semicolon (;)
cc : List of recipients who receive a copy of the message separated by semicolon (;)
attach_output : whether to include the job output as an email attachement
[12]:
action = ActionMail(
'mailToTeam',
urgency=ActionMail.Urgency.Urgent,
subject='Completion Mail',
message='%%JOBNAME just completed',
to='team@comp.com',
cc='other@comp.com',
attach_output=True
)
ActionRerun¶
Action that reruns the job
[13]:
action = ActionRerun('rerunAction')
ActionSet¶
Action that sets a variable
[14]:
action = ActionSet('SetVariable', variable='var1', value='1')
ActionSetToOk¶
Action that sets the job status to OK
[15]:
action = ActionSetToOK('SetToOk')
ActionSetToNotOK¶
Action that sets the job status to NotOK
[16]:
action = ActionSetToNotOK('SetToNotOk')
ActionStopCyclicRun¶
Action that disables the cyclic attribute of the job
[17]:
action = ActionStopCyclicRun('SetToOk')
ActionRun¶
Action that runs another job
[18]:
action = ActionRun('CorrectiveJob',
folder='FolderName',
job='JobName',
controlm_server='ctmserver',
date='010218',
variables=[{'cvar1': 'val1'}, {'cvar2': 'val2'}],
run_as_independent_flow=True
)
ActionNotify¶
Action that sends a notification
[19]:
action = ActionNotify('NotifyAction',
message='job just ran',
destination=ActionNotify.Destination.JobLog,
urgency=ActionNotify.Urgency.VeryUrgent)
ActionRemedy¶
Action that creates a Remedy ticket
[20]:
action = ActionRemedy('RemedyTicket',
summary='CONTROL-M job %%JOBNAME on node %%NODEID return code %%COMPSTAT',
message='CONTROL-M job %%JOBNAME run %%RUNCOUNT ended on node %%NODEID return code %%COMPSTAT Application: %%APPLIC',
urgency=ActionRemedy.Urgency.Low
)
ActionOutput¶
Action that copies the output to a specified destination
[21]:
action = ActionOutput(
'CopyOutput', operation=ActionOutput.Operation.Copy,
destination='/home/copyHere')
Notify¶
Create a notification for certain scenarios before, during and after job execution. You can set notifications for a Job, Folder, or SubFolder
NotifyOk¶
Notify if jobs is executed without errors
[22]:
job = JobCommand('Job1', command='ls -l')
job.notify_list.append(
NotifyOK('Notify1',
message='Job OK',
destination=Notify.Destination.JobLog)
)
NotifyNotOk¶
Notify if the job is executed with errors
[23]:
job = JobCommand('Job1', command='ls -l')
job.notify_list.append(
NotifyNotOK('Notify1',
message='Job NOT OK',
destination=Notify.Destination.Alerts)
)
NotifyDoesNotStart¶
Notify if the job has not started
[24]:
job = JobCommand('Job1', command='ls -l')
job.notify_list.append(
NotifyDoesNotStart('Notify1',
message='Job did not start',
by='1510',
destination=Notify.Destination.Console)
)
NotifyExecutionTime¶
Notify if the execution time is different than expected
[25]:
job = JobCommand('Job1', command='ls -l')
job.notify_list.append(
NotifyExecutionTime('Notify1',
message="Job didn't complete in less than 3 minutes",
destination=Notify.Destination.JobLog,
criteria=NotifyExecutionTime.Criteria.LessThan,
value='3'
)
)
NotifyDoesNotEnd¶
Notify if the job does not end by the specified time
[26]:
job = JobCommand('Job1', command='ls -l')
job.notify_list.append(
NotifyDoesNotEnd('Notify1',
message="Job didn't by 12h20",
destination=Notify.Destination.JobLog,
by='1220'
)
)
NotifyReRun¶
Notify if the job reruns
[27]:
job = JobCommand('Job1', command='ls -l')
job.notify_list.append(
NotifyRerun('Notify1',
message="Job reran",
destination=Notify.Destination.JobLog
)
)
NotifyLateCyclicSubmit¶
Note: This feature requires Control-M/Enterprise Manager version 9.0.21
Notify if the second or subsequent cyclic submission is late by a specified number of minutes
[28]:
job = JobCommand('Job1', command='ls -l')
job.notify_list.append(
NotifyLateCyclicSubmit('Notify1',
message="Cyclic job did not submit on time",
destination=Notify.Destination.JobLog,
by='10' # Job cyclic is late by 10 minutes
)
)
Resources¶
ResourcePool¶
Sets a pool (previously known as quantitative resources or semaphore) on a job, to control access to a resource that is concurrently shared by other jobs
[29]:
folder = Folder('ResourceSample',
job_list=[
JobCommand('job1', command='ls', resource_list=[
ResourcePool('semaphore1', quantity='3')
]
)
]
)
ResourceLock¶
Sets a lock (previously known as a control resource or mutex) as shared or exclusive. If the resource is shared, other jobs can use the resource concurrently. If set to exclusive, the job has to wait until the resource is available before it can run. You can set a lock on a Job, Folder, or SubFolder
[30]:
folder = Folder('ResourceSample',
job_list=[
JobCommand('job1', command='ls', resource_list=[
ResourceLock(
'lock1', lock_type=ResourceLock.LockType.Exclusive)
]
)
]
)
Rerun¶
Allows to define cyclic jobs or folders
Arguments:
every : The frequency at which to run the cyclic job or folder, expressed as a whole number of the specified time unit
units : One of the following: “Minutes” “Hours” or “Days”. The default is “Minutes”
from_ : Start - next run time is calculated an N Units from the start time of the current run, End - next run time is calculated as N Units from the end time of current run, Target - run starts every N units
times : Number of cycles to run (as a string). To run forever, define “0”
[31]:
job = JobCommand('Job1', command='ls', rerun=Job.Rerun(
every='4',
from_=Job.Rerun.From.End,
times='3',
units=Job.Rerun.Units.Days))
Variables¶
Events¶
Events can be generated by Control-M or can trigger jobs. Events are defined by a name and a date.
Here is a list of the various capabilities of event usages:
A job can wait for events before running, add events after running, or delete events after running. See WaitForEvents, AddEvents, and DeleteEvents
You can set events for a Job, Folder, or SubFolder. For “Date”, you can use the following values:
Date Type |
Description |
---|---|
AnyDate |
Any scheduled date |
OrderDate |
Control-M scheduled date.If you do not specify a Date value, this is the default. |
PreviousOrderDate |
Previous Control-M scheduled date |
NextOrderDate |
Next Control-M scheduled date |
MMDD |
Specific date Example: “0511” |
WaitForEvents¶
The following example shows how to define events that the job must wait for before running:
[32]:
waitForEventList = WaitForEvents([Event(event="e1"), Event(event="e2"), Event(event="e3", date=Event.Date.AnyDate)])
job = JobCommand('Job1', command='echo Hello')
job.event_list.append(waitForEventList)
AddEvents¶
The following example shows how to specify events for the job to add after running:
[33]:
addEventListObject = AddEvents([EventOutAdd(event="e4",date=Event.Date.NoDate)])
job = JobCommand('Job1', command='echo Hello')
job.event_list.append(addEventListObject)
DeleteEvents¶
The following example shows how to specify events for the job to remove after running:
[34]:
deleteEventListObject = DeleteEvents([EventOutDelete(event="e5",date=Event.Date.NextOrderDate)])
job = JobCommand('Job1', command='echo Hello')
job.event_list.append(deleteEventListObject)