ecflow.Node

class ecflow.Node

Bases: pybind11_object

A Node class is the abstract base class for Suite, Family and Task

Every Node instance has a name, and a path relative to a suite

Node.add(self: ecflow.Node, *args, **kwargs) object

add(..) provides a way to append Nodes and attributes

This is best illustrated with an example:

defs = Defs().add(
    Suite('s1').add(
        Clock(1, 1, 2010, False),
        Autocancel(1, 10, True),
        Task('t1').add(
            Edit({'a':'12', 'b':'bb'}, c='v',d='b'),
            Edit(g='d'),
            Edit(h=1),
            Event(1),
            Event(11,'event'),
            Meter('meter',0,10,10),
            Label('label','c'),
            Trigger('1==1'),
            Complete('1==1'),
            Limit('limit',10),Limit('limit2',10),
            InLimit('limitName','/limit',2),
            Defstatus(DState.complete),
            Today(0,30),Today('00:59'),Today('00:00 11:30 00:01'),
            Time(0,30),Time('00:59'),Time('00:00 11:30 00:01'),
            Day('sunday'),Day(Days.monday),
            Date(1,1,0),Date(28,2,1960),
            Autocancel(3)
            ),
        [ Family('f{}'.format(i)) for i in range(1,6)]))

We can also use ‘+=’ with a list here are a few examples:

defs = Defs();
defs += [ Suite('s2'),Edit({ 'x1':'y', 'aa1':'bb'}, a='v',b='b') ]
defs += [ Suite('s{}'.format(i)) for i in range(1,6) ]
defs = Defs()
defs += [ Suite('suite').add(
             Task('x'),
             Family('f').add( [ Task('t{}'.format(i)) for i in range(1,6)] ),
             Task('y'),
             [ Family('f{}'.format(i)) for i in range(1,6) ],
             Edit(a='b'),
             [ Task('t{}'.format(i)) for i in range(1,6) ],
             )]

It is also possible to use ‘+’

defs = Defs() + Suite('s1')
defs.s1 += Autocancel(1, 10, True)
defs.s1 += Task('t1') + Edit({ 'e':1, 'f':'bb'}) +\
           Event(1) + Event(11,'event') + Meter('meter',0,10,10) + Label('label','c') + Trigger('1==1') +\
           Complete('1==1') + Limit('limit',10) + Limit('limit2',10) + InLimit('limitName','/limit',2) +\
           Defstatus(DState.complete) + Today(0,30) + Today('00:59') + Today('00:00 11:30 00:01') +\
           Time(0,30) + Time('00:59') + Time('00:00 11:30 00:01') + Day('sunday') + Day(Days.monday) +\
           Date(1,1,0) + Date(28,2,1960) + Autocancel(3)

Warning

We can only use ‘+’ when the left most object is a node, i.e Task(‘t1’) in this case

Node.add_autoarchive(*args, **kwargs)

Overloaded function.

  1. add_autoarchive(self: ecflow.Node, days: typing.SupportsInt | typing.SupportsIndex, idle: bool = False) -> ecflow.Node

Add a autoarchive attribute. See ecflow.Autoarchive

Provides a way to automatically archive a suite/family which has completed.(i.e remove children) This is required when dealing with super large suite/families, they can be archived off, and then restored later. The node can be recovered using ‘autorestore’,begin,re-queue and manually via ecflow_client –restore. The archived node is written to disk, as ECF_HOME/<host>.<port>.ECF_NAME.check, where ‘/’ is replaced with ‘:’ in ECF_NAME. The removal may be delayed by an amount of time in hours and minutes or expressed as days Node removal is not immediate. The nodes are checked once a minute A Node may only have one autoarchive attribute

Exception:

  • Throws a RuntimeError if more than one auto archive is added

Usage:

t1 = Task('t1')
t1.add_autoarchive( Autoarchive(20,10,False) )  # hour,min, relative
t2 = Task('t2')
t2.add_autoarchive( 3 )                        # 3 days
t3 = Task('t3')
t3.add_autoarchive( 20,10,True )               # hour,minutes,relative
t4 = Task('t4')
t4.add_autoarchive( TimeSlot(20,10),True )     # hour,minutes,relative

# we can also create a Autoarchive in the Task constructor like any other attribute
t2 = Task('t2',
          Autoarchive(20,10,False))
  1. add_autoarchive(self: ecflow.Node, hour: typing.SupportsInt | typing.SupportsIndex, min: typing.SupportsInt | typing.SupportsIndex, relative: bool, idle: bool = False) -> ecflow.Node

  2. add_autoarchive(self: ecflow.Node, TimeSlot: ecflow.TimeSlot, relative: bool, idle: bool = False) -> ecflow.Node

  3. add_autoarchive(self: ecflow.Node, arg0: ecflow.Autoarchive) -> ecflow.Node

Node.add_autocancel(*args, **kwargs)

Overloaded function.

  1. add_autocancel(self: ecflow.Node, arg0: typing.SupportsInt | typing.SupportsIndex) -> ecflow.Node

Add a autocancel attribute. See ecflow.Autocancel

This will delete the node on completion. The deletion may be delayed by an amount of time in hours and minutes or expressed as days Node deletion is not immediate. The nodes are checked once a minute and expired auto cancel nodes are deleted A node may only have one auto cancel attribute

Exception:

  • Throws a RuntimeError if more than one auto cancel is added

Usage:

t1 = Task('t1')
t1.add_autocancel( Autocancel(20,10,False) )  # hour,min, relative
t2 = Task('t2')
t2.add_autocancel( 3 )                        # 3 days
t3 = Task('t3')
t3.add_autocancel( 20,10,True )               # hour,minutes,relative
t4 = Task('t4')
t4.add_autocancel( TimeSlot(20,10),True )     # hour,minutes,relative

# we can also create a Autocancel in the Task constructor like any other attribute
t2 = Task('t2',
          Autocancel(20,10,False))
  1. add_autocancel(self: ecflow.Node, arg0: typing.SupportsInt | typing.SupportsIndex, arg1: typing.SupportsInt | typing.SupportsIndex, arg2: bool) -> ecflow.Node

  2. add_autocancel(self: ecflow.Node, arg0: ecflow.TimeSlot, arg1: bool) -> ecflow.Node

  3. add_autocancel(self: ecflow.Node, arg0: ecflow.Autocancel) -> ecflow.Node

Node.add_autorestore(*args, **kwargs)

Overloaded function.

  1. add_autorestore(self: ecflow.Node, arg0: ecflow.Autorestore) -> ecflow.Node

Add a autorestore attribute. See ecflow.Autorestore

Auto-restore is used to automatically restore a previously auto-archived node. The restore will fail if:

  • The node has not been archived

  • The node has children.

  • The file ECF_HOME/<host>.<port>.ECF_NAME.check does not exist

Exception:

  • Throws a RuntimeError if more than one autorestore is added

Usage:

t1 = Task('t1')
t1.add_autorestore( ['/s1/f1'] )
t2 = Task('t2')
t2.add_autorestore( Autorestore(['/s2/f1','/s1/f2']) )
# we can also create a Autorestore in the Task constructor like any other attribute
t2 = Task('t2', Autorestore(['/s2/f1','/s1/f2'] ))
  1. add_autorestore(self: ecflow.Node, arg0: list) -> ecflow.Node

Node.add_aviso(self: ecflow.Node, arg0: ecflow.AvisoAttr) ecflow.Node

Adds an aviso to a node. See ecflow.Aviso

Node.add_complete(*args, **kwargs)

Overloaded function.

  1. add_complete(self: ecflow.Node, arg0: str) -> ecflow.Node

Add a trigger or complete expression.Also see ecflow.Trigger

This defines a dependency for a node. There can only be one trigger or complete expression dependency per node. A node with a trigger can only be activated when the trigger has expired. A trigger holds a node as long as the expression returns false.

Exception:

  • Will throw RuntimeError if multiple trigger or complete expression are added

  • Will throw RuntimeError if first expression is added as ‘AND’ or ‘OR’ expression Like wise second and subsequent expression must have ‘AND’ or ‘OR’ booleans set

Usage:

Note we cannot make multiple add_trigger(..) calls on the same task! to add a simple trigger:

task1.add_trigger( 't2 == active' )
task2.add_trigger( 't1 == complete or t4 == complete' )
task3.add_trigger( 't5 == active' )

Long expression can be broken up using add_part_trigger:

task2.add_part_trigger( 't1 == complete or t4 == complete')
task2.add_part_trigger( 't5 == active',True)  # True means  AND
task2.add_part_trigger( 't7 == active',False) # False means OR

The trigger for task2 is equivalent to: ‘t1 == complete or t4 == complete and t5 == active or t7 == active’

  1. add_complete(self: ecflow.Node, arg0: ecflow.Expression) -> ecflow.Node

Node.add_cron(self: ecflow.Node, arg0: ecflow.Cron) ecflow.Node

Add a cron time dependency. See ecflow.Cron

Usage:

start = TimeSlot(0,0)
finish = TimeSlot(23,0)
incr = TimeSlot(0,30)
time_series = TimeSeries( start, finish, incr, True)
cron = Cron()
cron.set_week_days( [0,1,2,3,4,5,6] )
cron.set_days_of_month( [1,2,3,4,5,6] )
cron.set_months( [1,2,3,4,5,6] )
cron.set_time_series( time_series )
t1 = Task('t1')
t1.add_cron( cron )

# we can also create a Cron in the Task constructor like any other attribute
t2 = Task('t2',
          Cron('+00:00 23:00 00:30',days_of_week=[0,1,2,3,4,5,6],days_of_month=[1,2,3,4,5,6],months=[1,2,3,4,5,6]))
Node.add_date(*args, **kwargs)

Overloaded function.

  1. add_date(self: ecflow.Node, arg0: typing.SupportsInt | typing.SupportsIndex, arg1: typing.SupportsInt | typing.SupportsIndex, arg2: typing.SupportsInt | typing.SupportsIndex) -> ecflow.Node

Add a date time dependency. See ecflow.Date

A value of zero for day,month,year means every day, every month, every year

Exception:

  • Throws RuntimeError if an invalid date is added

Usage:

t1 = Task('t1',
          Date('1.*.*'),
          Date(1,1,2010)))    # Create Date in place

t1.add_date( Date(1,1,2010) ) # day,month,year
t1.add_date( 2,1,2010)        # day,month,year
t1.add_date( 1,0,0)           # day,month,year, the first of each month for every year
  1. add_date(self: ecflow.Node, arg0: ecflow.Date) -> ecflow.Node

Node.add_day(*args, **kwargs)

Overloaded function.

  1. add_day(self: ecflow.Node, arg0: ecflow.Days) -> ecflow.Node

Add a day time dependency. See ecflow.Day

Usage:

t1 = Task('t1',
          Day('sunday'))  # Create Day on Task creation

t1.add_day( Day(Days.sunday) )
t1.add_day( Days.monday)
t1.add_day( 'tuesday' )
  1. add_day(self: ecflow.Node, arg0: str) -> ecflow.Node

  2. add_day(self: ecflow.Node, arg0: ecflow.Day) -> ecflow.Node

Node.add_defstatus(*args, **kwargs)

Overloaded function.

  1. add_defstatus(self: ecflow.Node, arg0: ecflow.DState) -> ecflow.Node

Set the default status( defstatus ) of node at begin or re queue. See ecflow.Defstatus

A defstatus is useful in preventing suites from running automatically once begun, or in setting Task’s complete so they can be run selectively

Usage:

t1 = Task('t1') + Defstatus('complete')
t2 = Task('t2').add_defstatus( DState.suspended )

# we can also create a Defstatus in the Task constructor like any other attribute
t2 = Task('t3',
          Defstatus('complete'))
  1. add_defstatus(self: ecflow.Node, arg0: ecflow.Defstatus) -> ecflow.Node

Set the default status( defstatus ) of node at begin or re queue. See ecflow.Defstatus

A defstatus is useful in preventing suites from running automatically once begun, or in setting Task’s complete so they can be run selectively

Usage:

t1 = Task('t1') + Defstatus('complete')
t2 = Task('t2').add_defstatus( DState.suspended )

# we can also create a Defstatus in the Task constructor like any other attribute
t2 = Task('t3',
          Defstatus('complete'))
Node.add_event(*args, **kwargs)

Overloaded function.

  1. add_event(self: ecflow.Node, arg0: ecflow.Event) -> ecflow.Node

Add a event. See ecflow.Event Events can be referenced in trigger and complete expressions

Exception:

  • Throws RuntimeError if a duplicate is added

Usage:

t1 = Task('t1',
          Event(12),
          Event(11,'eventx'))             # Create events on Task creation

t1.add_event( Event(10) )                 # Create with function on Task
t1.add_event( Event(11,'Eventname') )
t1.add_event( 12 )
t1.add_event( 13, 'name')

To reference event ‘flag’ in a trigger:

t1.add_event('flag')
t2 = Task('t2',
          Trigger('t1:flag == set'))
  1. add_event(self: ecflow.Node, arg0: typing.SupportsInt | typing.SupportsIndex) -> ecflow.Node

  2. add_event(self: ecflow.Node, arg0: str) -> ecflow.Node

  3. add_event(self: ecflow.Node, arg0: typing.SupportsInt | typing.SupportsIndex, arg1: str) -> ecflow.Node

Node.add_generic(*args, **kwargs)

Overloaded function.

  1. add_generic(self: ecflow.Node, arg0: ecflow.Generic) -> ecflow.Node

  2. add_generic(self: ecflow.Node, arg0: str, arg1: list) -> ecflow.Node

Node.add_inlimit(*args, **kwargs)

Overloaded function.

  1. add_inlimit(self: ecflow.Node, limit_name: str, path_to_node_containing_limit: str = ‘’, tokens: typing.SupportsInt | typing.SupportsIndex = 1, limit_this_node_only: bool = False) -> ecflow.Node

Adds a inlimit to a node. See ecflow.InLimit

InLimit reference a limit/ecflow.Limit. Duplicate InLimits are not allowed

Exception:

  • Throws RuntimeError if a duplicate is added

Usage:

task2.add_inlimit( InLimit('limitName','/s1/f1',2) )
task2.add_inlimit( 'limitName','/s1/f1',2 )
  1. add_inlimit(self: ecflow.Node, arg0: ecflow.InLimit) -> ecflow.Node

Node.add_label(*args, **kwargs)

Overloaded function.

  1. add_label(self: ecflow.Node, arg0: str, arg1: str) -> ecflow.Node

Adds a label to a node. See ecflow.Label

Labels can be updated from the jobs files, via child command

Exception:

  • Throws RuntimeError if a duplicate label name is added

Usage:

task.add_label( Label('TEA','/me/'))
task.add_label( 'Joe','/me/')

The corresponding child command in the .ecf script file might be:

ecflow_client --label=TEA time
ecflow_client --label=Joe ninety
  1. add_label(self: ecflow.Node, arg0: ecflow.Label) -> ecflow.Node

Node.add_late(self: ecflow.Node, arg0: ecflow.Late) ecflow.Node

Add a late attribute. See ecflow.Late

Exception:

  • Throws a RuntimeError if more than one late is added

Usage:

late = Late()
late.submitted( 20,10 )     # hour,minute
late.active(    20,10 )     # hour,minute
late.complete(  20,10,True) # hour,minute,relative
t1 = Task('t1')
t1.add_late( late )

# we can also create a Late in the Task constructor like any other attribute
t2 = Task('t2',
          Late(submitted='20:10',active='20:10',complete='+20:10'))
Node.add_limit(*args, **kwargs)

Overloaded function.

  1. add_limit(self: ecflow.Node, arg0: str, arg1: typing.SupportsInt | typing.SupportsIndex) -> ecflow.Node

Adds a limit to a node for simple load management. See ecflow.Limit

Multiple limits can be added, however the limit name must be unique. For a node to be in a limit, a inlimit must be used.

Exception:

  • Throws RuntimeError if a duplicate limit name is added

Usage:

family.add_limit( Limit('load',12) )
family.add_limit( 'load',12 )
  1. add_limit(self: ecflow.Node, arg0: ecflow.Limit) -> ecflow.Node

Node.add_meter(*args, **kwargs)

Overloaded function.

  1. add_meter(self: ecflow.Node, arg0: ecflow.Meter) -> ecflow.Node

Add a meter. See ecflow.Meter Meters can be referenced in trigger and complete expressions

Exception:

  • Throws RuntimeError if a duplicate is added

Usage:

t1 = Task('t1',
          Meter('met',0,50))                   # create Meter on Task creation
t1.add_meter( Meter('metername',0,100,50) )  # create Meter using function
t1.add_meter( 'meter',0,200)

To reference in a trigger:

t2 = Task('t2')
t2.add_trigger('t1:meter >= 10')
  1. add_meter(self: ecflow.Node, arg0: str, arg1: typing.SupportsInt | typing.SupportsIndex, arg2: typing.SupportsInt | typing.SupportsIndex, arg3: typing.SupportsInt | typing.SupportsIndex) -> ecflow.Node

  2. add_meter(self: ecflow.Node, arg0: str, arg1: typing.SupportsInt | typing.SupportsIndex, arg2: typing.SupportsInt | typing.SupportsIndex) -> ecflow.Node

Node.add_mirror(self: ecflow.Node, arg0: ecflow.MirrorAttr) ecflow.Node

Adds a mirror to a node. See ecflow.Mirror

Node.add_part_complete(*args, **kwargs)

Overloaded function.

  1. add_part_complete(self: ecflow.Node, arg0: ecflow.PartExpression) -> ecflow.Node

Add a trigger or complete expression.Also see ecflow.Trigger

This defines a dependency for a node. There can only be one trigger or complete expression dependency per node. A node with a trigger can only be activated when the trigger has expired. A trigger holds a node as long as the expression returns false.

Exception:

  • Will throw RuntimeError if multiple trigger or complete expression are added

  • Will throw RuntimeError if first expression is added as ‘AND’ or ‘OR’ expression Like wise second and subsequent expression must have ‘AND’ or ‘OR’ booleans set

Usage:

Note we cannot make multiple add_trigger(..) calls on the same task! to add a simple trigger:

task1.add_trigger( 't2 == active' )
task2.add_trigger( 't1 == complete or t4 == complete' )
task3.add_trigger( 't5 == active' )

Long expression can be broken up using add_part_trigger:

task2.add_part_trigger( 't1 == complete or t4 == complete')
task2.add_part_trigger( 't5 == active',True)  # True means  AND
task2.add_part_trigger( 't7 == active',False) # False means OR

The trigger for task2 is equivalent to: ‘t1 == complete or t4 == complete and t5 == active or t7 == active’

  1. add_part_complete(self: ecflow.Node, arg0: str) -> ecflow.Node

  2. add_part_complete(self: ecflow.Node, arg0: str, arg1: bool) -> ecflow.Node

Node.add_part_trigger(*args, **kwargs)

Overloaded function.

  1. add_part_trigger(self: ecflow.Node, arg0: ecflow.PartExpression) -> ecflow.Node

Add a trigger or complete expression.Also see ecflow.Trigger

This defines a dependency for a node. There can only be one trigger or complete expression dependency per node. A node with a trigger can only be activated when the trigger has expired. A trigger holds a node as long as the expression returns false.

Exception:

  • Will throw RuntimeError if multiple trigger or complete expression are added

  • Will throw RuntimeError if first expression is added as ‘AND’ or ‘OR’ expression Like wise second and subsequent expression must have ‘AND’ or ‘OR’ booleans set

Usage:

Note we cannot make multiple add_trigger(..) calls on the same task! to add a simple trigger:

task1.add_trigger( 't2 == active' )
task2.add_trigger( 't1 == complete or t4 == complete' )
task3.add_trigger( 't5 == active' )

Long expression can be broken up using add_part_trigger:

task2.add_part_trigger( 't1 == complete or t4 == complete')
task2.add_part_trigger( 't5 == active',True)  # True means  AND
task2.add_part_trigger( 't7 == active',False) # False means OR

The trigger for task2 is equivalent to: ‘t1 == complete or t4 == complete and t5 == active or t7 == active’

  1. add_part_trigger(self: ecflow.Node, arg0: str) -> ecflow.Node

  2. add_part_trigger(self: ecflow.Node, arg0: str, arg1: bool) -> ecflow.Node

Node.add_queue(*args, **kwargs)

Overloaded function.

  1. add_queue(self: ecflow.Node, arg0: ecflow.Queue) -> ecflow.Node

  2. add_queue(self: ecflow.Node, arg0: str, arg1: list) -> ecflow.Node

Node.add_repeat(*args, **kwargs)

Overloaded function.

  1. add_repeat(self: ecflow.Node, arg0: ecflow.RepeatDate) -> ecflow.Node

Add a RepeatDate attribute. See ecflow.RepeatDate

A node can only have one repeat Reference to a RepeatDate in a trigger will use date arithmetic in a sub expression. i.e. Here (/suite/family:YMD + 1) uses date arithmetic only, the result is still an integer

trigger /suite/family:YMD + 1 > 20190101

Exception:

  • Throws a RuntimeError if more than one repeat is added

Usage:

t1 = Task('t1')
t1.add_repeat( RepeatDate('YMD',20100111,20100115) )

# we can also create a repeat in Task constructor like any other attribute
t2 = Task('t2',
          RepeatDate('YMD',20100111,20100115))
  1. add_repeat(self: ecflow.Node, arg0: ecflow.RepeatDateTime) -> ecflow.Node

Add a RepeatDateTime attribute. See ecflow.RepeatDateTime

A node can only have one repeat. When a RepeatDateTime is used in a trigger expression, the arithmetic value of the Repeat decays to second. For example, the expression /suite/family:DATETIME + 1 is evaluated as the number of seconds represented by /suite/family:DT (since the reference epoch, i.e. 19700101T000000) plus 1.The result is an integer.

trigger /suite/family:DT + 1 > 123456

Exception:

  • Throws a RuntimeError if more than one repeat is added

Usage:

t1 = Task('t1')
t1.add_repeat(RepeatDateTime('DT', '20100111T120000', '20100115T000000', '12:00:00'))

# we can also create a repeat in Task constructor like any other attribute
t2 = Task('t2',
          RepeatDateTime('DT', '20100101T000000', '20100115T000000', '1:00:00'))
  1. add_repeat(self: ecflow.Node, arg0: ecflow.RepeatDateList) -> ecflow.Node

Add a RepeatDateList attribute. See ecflow.RepeatDateList

A node can only have one repeat Reference to a RepeatDateList in a trigger will use date arithmetic. i.e. Here (/suite/family:YMD + 1) uses date arithmetic only, the result is still an integer:

trigger /suite/family:YMD + 1 > 20190101

Exception:

  • Throws a RuntimeError if more than one repeat is added

Usage:

t1 = Task('t1')
t1.add_repeat( RepeatDateList('YMD',[20100111,20100115]) )

# we can also create a repeat in Task constructor like any other attribute
t2 = Task('t2',
          RepeatDateList('YMD',[20100111,20100115]))
  1. add_repeat(self: ecflow.Node, arg0: ecflow.RepeatDateTimeList) -> ecflow.Node

Add a RepeatDateTimeList attribute. See ecflow.RepeatDateTimeList

A node can only have one repeat

Exception:

  • Throws a RuntimeError if more than one repeat is added

Usage:

t1 = Task('t1')
t1.add_repeat( RepeatDateTimeList('DT', ['20240101T000000', '20240102T120000']) )

# we can also create a repeat in Task constructor like any other attribute
t2 = Task('t2',
          RepeatDateTimeList('DT', ['20240101T000000', '20240102T120000']))
  1. add_repeat(self: ecflow.Node, arg0: ecflow.RepeatInteger) -> ecflow.Node

Add a RepeatInteger attribute. See ecflow.RepeatInteger

A node can only have one repeat

Exception:

  • Throws a RuntimeError if more than one repeat is added

Usage:

t1 = Task('t1')
t1.add_repeat( RepeatInteger('testInteger',0,100,2) )

# we can also create a repeat in Task constructor like any other attribute
t2 = Task('t2',
          RepeatInteger('testInteger',0,100,2))
  1. add_repeat(self: ecflow.Node, arg0: ecflow.RepeatString) -> ecflow.Node

Add a RepeatString attribute. See ecflow.RepeatString

A node can only have one repeat

Exception:

  • Throws a RuntimeError if more than one repeat is added

Usage:

t1 = Task('t1')
t1.add_repeat( RepeatString('test_string',['a', 'b', 'c' ] ) )

# we can also create a repeat in Task constructor like any other attribute
t2 = Task('t2',
          RepeatString('test_string',['a', 'b', 'c' ] ) )
  1. add_repeat(self: ecflow.Node, arg0: ecflow.RepeatEnumerated) -> ecflow.Node

Add a RepeatEnumerated attribute. See ecflow.RepeatEnumerated

A node can only have one repeat

Exception:

  • Throws a RuntimeError if more than one repeat is added

Usage:

t1 = Task('t1')
t1.add_repeat( RepeatEnumerated('test_string', ['red', 'green', 'blue' ] ) )

# we can also create a repeat in Task constructor like any other attribute
t2 = Task('t2',
          RepeatEnumerated('test_string', ['red', 'green', 'blue' ] ) )
  1. add_repeat(self: ecflow.Node, arg0: ecflow.RepeatDay) -> ecflow.Node

Add a RepeatDay attribute. See ecflow.RepeatDay

A node can only have one repeat

Exception:

  • Throws a RuntimeError if more than one repeat is added

Usage:

t2 = Task('t2',
          RepeatDay(1))
Node.add_time(*args, **kwargs)

Overloaded function.

  1. add_time(self: ecflow.Node, arg0: typing.SupportsInt | typing.SupportsIndex, arg1: typing.SupportsInt | typing.SupportsIndex) -> ecflow.Node

Add a time dependency. See ecflow.Time

Usage:

t1 = Task('t1', Time('+00:30 20:00 01:00')) # Create Time in Task constructor
t1.add_time( '00:30' )
t1.add_time( '+00:30' )
t1.add_time( '+00:30 20:00 01:00' )
t1.add_time( Time( 0,10 ))      # hour,min,relative =false
t1.add_time( Time( 0,12,True )) # hour,min,relative
t1.add_time( Time(TimeSlot(20,20),False))
t1.add_time( 0,1 ))              # hour,min,relative=false
t1.add_time( 0,3,False ))        # hour,min,relative=false
start = TimeSlot(0,0)
finish = TimeSlot(23,0)
incr = TimeSlot(0,30)
ts = TimeSeries( start, finish, incr, True)
task2.add_time( Time(ts) )
  1. add_time(self: ecflow.Node, arg0: typing.SupportsInt | typing.SupportsIndex, arg1: typing.SupportsInt | typing.SupportsIndex, arg2: bool) -> ecflow.Node

  2. add_time(self: ecflow.Node, arg0: str) -> ecflow.Node

  3. add_time(self: ecflow.Node, arg0: ecflow.Time) -> ecflow.Node

Node.add_today(*args, **kwargs)

Overloaded function.

  1. add_today(self: ecflow.Node, arg0: typing.SupportsInt | typing.SupportsIndex, arg1: typing.SupportsInt | typing.SupportsIndex) -> ecflow.Node

Add a today time dependency. See ecflow.Today

Usage:

t1 = Task('t1',
          Today('+00:30 20:00 01:00')) # Create Today in Task constructor

t1.add_today( '00:30' )
t1.add_today( '+00:30' )
t1.add_today( '+00:30 20:00 01:00' )
t1.add_today( Today( 0,10 ))      # hour,min,relative =false
t1.add_today( Today( 0,12,True )) # hour,min,relative
t1.add_today( Today(TimeSlot(20,20),False))
t1.add_today( 0,1 ))              # hour,min,relative=false
t1.add_today( 0,3,False ))        # hour,min,relative=false
start = TimeSlot(0,0)
finish = TimeSlot(23,0)
incr = TimeSlot(0,30)
ts = TimeSeries( start, finish, incr, True)
task2.add_today( Today(ts) )
  1. add_today(self: ecflow.Node, arg0: typing.SupportsInt | typing.SupportsIndex, arg1: typing.SupportsInt | typing.SupportsIndex, arg2: bool) -> ecflow.Node

  2. add_today(self: ecflow.Node, arg0: str) -> ecflow.Node

  3. add_today(self: ecflow.Node, arg0: ecflow.Today) -> ecflow.Node

Node.add_trigger(*args, **kwargs)

Overloaded function.

  1. add_trigger(self: ecflow.Node, arg0: str) -> ecflow.Node

Add a trigger or complete expression.Also see ecflow.Trigger

This defines a dependency for a node. There can only be one trigger or complete expression dependency per node. A node with a trigger can only be activated when the trigger has expired. A trigger holds a node as long as the expression returns false.

Exception:

  • Will throw RuntimeError if multiple trigger or complete expression are added

  • Will throw RuntimeError if first expression is added as ‘AND’ or ‘OR’ expression Like wise second and subsequent expression must have ‘AND’ or ‘OR’ booleans set

Usage:

Note we cannot make multiple add_trigger(..) calls on the same task! to add a simple trigger:

task1.add_trigger( 't2 == active' )
task2.add_trigger( 't1 == complete or t4 == complete' )
task3.add_trigger( 't5 == active' )

Long expression can be broken up using add_part_trigger:

task2.add_part_trigger( 't1 == complete or t4 == complete')
task2.add_part_trigger( 't5 == active',True)  # True means  AND
task2.add_part_trigger( 't7 == active',False) # False means OR

The trigger for task2 is equivalent to: ‘t1 == complete or t4 == complete and t5 == active or t7 == active’

  1. add_trigger(self: ecflow.Node, arg0: ecflow.Expression) -> ecflow.Node

Node.add_variable(*args, **kwargs)

Overloaded function.

  1. add_variable(self: ecflow.Node, arg0: str, arg1: str) -> ecflow.Node

Adds a name value variable. Also see ecflow.Edit

This defines a variable for use in variable substitution in a ecf script file. There can be any number of variables. The variables are names inside a pair of ‘%’ characters in an ecf script. The name are case sensitive. Special character in the value, must be placed inside single quotes if misinterpretation is to be avoided. The value of the variable replaces the variable name in the ecf script at job creation time. The variable names for any given node must be unique. If duplicates are added then the the last value added is kept.

Exception:

  • Writes warning to standard output, if a duplicate variable name is added

Usage:

task.add_variable( Variable('ECF_HOME','/tmp/'))
task.add_variable( 'TMPDIR','/tmp/')
task.add_variable( 'COUNT',2)
a_dict = { 'name':'value', 'name2':'value2', 'name3':'value3' }
task.add_variable(a_dict)
  1. add_variable(self: ecflow.Node, arg0: str, arg1: typing.SupportsInt | typing.SupportsIndex) -> ecflow.Node

  2. add_variable(self: ecflow.Node, arg0: ecflow.Variable) -> ecflow.Node

  3. add_variable(self: ecflow.Node, arg0: ecflow.Edit) -> ecflow.Node

  4. add_variable(self: ecflow.Node, arg0: object) -> ecflow.Node

Node.add_verify(self: ecflow.Node, arg0: ecflow.Verify) None

Add a Verify attribute.

Used in python simulation used to assert that a particular state was reached. t2 = Task(‘t2’,

Verify(State.complete, 6)) # verify task completes 6 times during simulation

Node.add_zombie(self: ecflow.Node, arg0: ecflow.ZombieAttr) ecflow.Node

The zombie attribute defines how a zombie should be handled in an automated fashion

Very careful consideration should be taken before this attribute is added as it may hide a genuine problem. It can be added to any node. But is best defined at the suite or family level. If there is no zombie attribute the default behaviour is to block the init,complete,abort child command. and fob the event,label,and meter child command This attribute allows the server to make a automated response. Please see: ecflow.ZombieType, ecflow.ChildCmdType, ecflow.ZombieUserActionType

Constructor:

ZombieAttr(ZombieType,ChildCmdTypes, ZombieUserActionType, lifetime)
   ZombieType            : Must be one of ZombieType.ecf, ZombieType.path, ZombieType.user
   ChildCmdType          : A list(ChildCmdType) of Child commands. Can be left empty in
                           which case the action affect all child commands
   ZombieUserActionType  : One of [ fob, fail, block, remove, adopt ]
   int lifetime<optional>: Defines the life time in seconds of the zombie in the server.
                           On expiration, zombie is removed automatically

Usage:

# Add a zombie attribute so that child commands(i.e ecflow_client --init)
# will fail the job if it is a zombie process.
s1 = Suite('s1')
child_list = [ ChildCmdType.init, ChildCmdType.complete, ChildCmdType.abort ]
s1.add_zombie( ZombieAttr(ZombieType.ecf, child_list, ZombieUserActionType.fob))

# create the zombie as part of the node constructor
s1 = Suite('s1',
           ZombieAttr(ZombieType.ecf, child_list, ZombieUserActionType.fail))
property Node.avisos

Returns a list of avisos

Node.change_complete(self: ecflow.Node, arg0: str) None
Node.change_trigger(self: ecflow.Node, arg0: str) None
property Node.crons

Returns a list of crons

property Node.dates

Returns a list of dates

property Node.days

Returns a list of days

Node.delete_complete(self: ecflow.Node) None
Node.delete_cron(*args, **kwargs)

Overloaded function.

  1. delete_cron(self: ecflow.Node, arg0: str) -> None

  2. delete_cron(self: ecflow.Node, arg0: ecflow.Cron) -> None

Node.delete_date(*args, **kwargs)

Overloaded function.

  1. delete_date(self: ecflow.Node, arg0: str) -> None

  2. delete_date(self: ecflow.Node, arg0: ecflow.Date) -> None

Node.delete_day(*args, **kwargs)

Overloaded function.

  1. delete_day(self: ecflow.Node, arg0: str) -> None

  2. delete_day(self: ecflow.Node, arg0: ecflow.Day) -> None

Node.delete_event(self: ecflow.Node, arg0: str) None
Node.delete_generic(self: ecflow.Node, arg0: str) None
Node.delete_inlimit(self: ecflow.Node, arg0: str) None
Node.delete_label(self: ecflow.Node, arg0: str) None
Node.delete_limit(self: ecflow.Node, arg0: str) None
Node.delete_meter(self: ecflow.Node, arg0: str) None
Node.delete_queue(self: ecflow.Node, arg0: str) None
Node.delete_repeat(self: ecflow.Node) None
Node.delete_time(*args, **kwargs)

Overloaded function.

  1. delete_time(self: ecflow.Node, arg0: str) -> None

  2. delete_time(self: ecflow.Node, arg0: ecflow.Time) -> None

Node.delete_today(*args, **kwargs)

Overloaded function.

  1. delete_today(self: ecflow.Node, arg0: str) -> None

  2. delete_today(self: ecflow.Node, arg0: ecflow.Today) -> None

Node.delete_trigger(self: ecflow.Node) None
Node.delete_variable(self: ecflow.Node, arg0: str) None
Node.delete_zombie(*args, **kwargs)

Overloaded function.

  1. delete_zombie(self: ecflow.Node, arg0: str) -> None

  2. delete_zombie(self: ecflow.Node, arg0: ecflow.ZombieType) -> None

Node.evaluate_complete(self: ecflow.Node) bool

evaluate complete expression

Node.evaluate_trigger(self: ecflow.Node) bool

evaluate trigger expression

property Node.events

Returns a list of events

Node.find_event(self: ecflow.Node, arg0: str) ecflow.Event

Find the event on the node only. Returns a object

Node.find_gen_variable(self: ecflow.Node, arg0: str) ecflow.Variable

Find generated variable on the node only. Returns an object

Node.find_generic(self: ecflow.Node, arg0: str) ecflow.Generic

Find the generic on the node only. Returns a Generic object

Node.find_label(self: ecflow.Node, arg0: str) ecflow.Label

Find the label on the node only. Returns a object

Node.find_limit(self: ecflow.Node, arg0: str) ecflow.Limit

Find the limit on the node only. returns a limit ptr

Node.find_meter(self: ecflow.Node, arg0: str) ecflow.Meter

Find the meter on the node only. Returns an object

Node.find_node_up_the_tree(self: ecflow.Node, arg0: str) ecflow.Node

Search immediate node, then up the node hierarchy

Node.find_parent_variable(self: ecflow.Node, arg0: str) ecflow.Variable

Find user variable variable up the parent hierarchy. Returns an object

Node.find_parent_variable_sub_value(self: ecflow.Node, arg0: str) str

Find user variable up node tree, then variable substitute the value, otherwise return empty string

Node.find_queue(self: ecflow.Node, arg0: str) ecflow.Queue

Find the queue on the node only. Returns a queue object

Node.find_variable(self: ecflow.Node, arg0: str) ecflow.Variable

Find user variable on the node only. Returns an object

property Node.generics

Returns a list of generics

Node.get_abs_node_path(self: ecflow.Node) str

returns a string which holds the path to the node

Node.get_all_nodes(self: ecflow.Node) ecflow.NodeVec

Returns all the child nodes

Node.get_autoarchive(self: ecflow.Node) ecflow.Autoarchive
Node.get_autocancel(self: ecflow.Node) ecflow.Autocancel
Node.get_autorestore(self: ecflow.Node) ecflow.Autorestore
Node.get_complete(self: ecflow.Node) ecflow.Expression
Node.get_defs(self: ecflow.Node) Defs
Node.get_defstatus(self: ecflow.Node) ecflow.DState
Node.get_dstate(self: ecflow.Node) ecflow.DState

Returns the state of node. This will include suspended state

Node.get_flag(self: ecflow.Node) ecflow.Flag

Return additional state associated with a node.

Node.get_generated_variables(*args, **kwargs)

Overloaded function.

  1. get_generated_variables(self: ecflow.Node) -> list

Returns the list of generated variables.

  1. get_generated_variables(self: ecflow.Node, arg0: ecflow.VariableList) -> None

Retrieves the list of generated variables. Pass in ecflow.VariableList as argument to hold variables.

Node.get_late(self: ecflow.Node) ecflow.Late
Node.get_parent(self: ecflow.Node) ecflow.Node
Node.get_repeat(self: ecflow.Node) ecflow.Repeat
Node.get_state(self: ecflow.Node) ecflow.State

Returns the state of the node. This excludes the suspended state

Node.get_state_change_time(self: ecflow.Node, format: str = 'iso_extended') str

Returns the time of the last state change as a string. Default format is iso_extended, (iso_extended, iso, simple)

Node.get_trigger(self: ecflow.Node) ecflow.Expression
Node.has_time_dependencies(self: ecflow.Node) bool
property Node.inlimits

Returns a list of inlimits

Node.is_suspended(self: ecflow.Node) bool

Returns true if the node is in a suspended state

property Node.labels

Returns a list of labels

property Node.limits

Returns a list of limits

property Node.meters

Returns a list of meters

property Node.mirrors

Returns a list of mirrors

Node.name(self: ecflow.Node) str
property Node.queues

Returns a list of queues

Node.remove(self: ecflow.Node) ecflow.Node

Remove the node from its parent. and returns it

Node.replace_on_server(*args, **kwargs)

Overloaded function.

  1. replace_on_server(self: ecflow.Node, suspend_node_first: bool = True, force: bool = True) -> None

replace node on the server.

  1. replace_on_server(self: ecflow.Node, host: str, port: str, suspend_node_first: bool = True, force: bool = True) -> None

replace node on the server.

  1. replace_on_server(self: ecflow.Node, host_port: str, suspend_node_first: bool = True, force: bool = True) -> None

replace node on the server.

  1. replace_on_server(self: ecflow.Node, client: ClientInvoker, suspend_node_first: bool = True, force: bool = True) -> None

replace node on the server.

Node.sort_attributes(*args, **kwargs)

Overloaded function.

  1. sort_attributes(self: ecflow.Node, arg0: ecflow.AttrType) -> None

  2. sort_attributes(self: ecflow.Node, arg0: ecflow.AttrType, arg1: bool) -> None

  3. sort_attributes(self: ecflow.Node, arg0: ecflow.AttrType, arg1: bool, arg2: list) -> None

  4. sort_attributes(self: ecflow.Node, attribute_type: str, recursive: bool = True, no_sort: list = []) -> None

  5. sort_attributes(self: ecflow.Node, attribute_type: ecflow.AttrType, recursive: bool = True, no_sort: collections.abc.Sequence[str] = []) -> None

property Node.times

Returns a list of times

property Node.todays

Returns a list of todays

Node.update_generated_variables(self: ecflow.Node) None
property Node.variables

Returns a list of user defined variables

property Node.verifies

Returns a list of Verify’s

property Node.zombies

Returns a list of zombies