1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
|
import os
import sys
import time
import steuermann.config
import steuermann.run
import datetime
# bugs:
# - this is a hideous hack that works around run.py not being designed for this
# - the work directory on the target machine is poorly named
#
class fakenode(object):
pass
def main() :
if len(sys.argv) < 4 :
print("smcron host name command")
print("(from ",sys.argv,")")
sys.exit(1)
host = sys.argv[1]
name = sys.argv[2]
script = ' '.join(sys.argv[3:])
db = steuermann.config.open_db()
c = db.cursor()
start_time = datetime.datetime.now()
day, tod = str(start_time).split(' ')
name = name + '--' + tod
logfile = '%s/%s.%s' % (day, host, name)
# something to reduce the possibility of a collision to very small - in this case, we assume that
# we can't start multiple processes at the same time from the same process number. i.e. the
# pid can not wrap in less than 1 clock tick
decollision = os.getpid()
c.execute("INSERT INTO sm_crons ( host, name, start_time, logfile, decollision ) VALUES ( ?, ?, ?, ?, ? )",
( host, name, str(start_time), logfile, decollision ) )
db.commit()
# this is a hideous hack to plug on to an interface that was not designed for this
node = fakenode()
node.host = host
node.name = 'cron.' + name
node.table = None
node.cmd = None
node.script = script
node.resources = { }
if host == 'localhost' :
node.script_type = 'l' # local
else :
node.script_type = 'r' # remote
hosts_ini = os.path.join(os.path.dirname(__file__), 'hosts.ini')
if os.path.exists(steuermann.config.hosts_config):
hosts_ini = steuermann.config.hosts_config
runner = steuermann.run.runner( nodes = { node.name : node }, hosts_ini = hosts_ini )
logname = logfile_name = steuermann.config.logdir + '/cron/' + logfile
st = runner.run( node=node, run_name='', logfile_name = logname )
if st == 'D' :
fp = open(logname,"w")
fp.write('execution on host is disabled in hosts.ini\n')
fp.close()
status = 'S'
elif st == 'M' :
fp = open(logname,"w")
fp.write('host is at max proc limit - how did this happen?')
fp.close()
status = '?'
elif st == 'R' :
n = 0.1
while 1 :
exited = runner.poll()
if exited :
break
if n < 2.0 :
n = n * 2.0
time.sleep(n)
status = exited[1]
end_time = datetime.datetime.now()
td = end_time - start_time
# only 1 decimal place because we don't poll often enough to make more reasonable.
td = "%.1f" % ( td.microseconds/1e6 + td.seconds + td.days * 24 * 3600 )
c.execute("UPDATE sm_crons SET end_time = ?, status = ?, duration = ? WHERE host = ? AND name = ? ",
(str(end_time), status, td, host, name ) )
db.commit()
|