def init_task(self):
     task_id = self.currentrow[0]
     status = self.currentrow[5]
     if status not in ('RUNNING', 'CONTINUING', 'SLEEPING'):
         bibsched_set_status(task_id, "WAITING")
         bibsched_set_progress(task_id, "")
         bibsched_set_host(task_id, "")
         self.update_rows()
         self.repaint()
         self.display_in_footer("process initialised")
     else:
         self.display_in_footer("Cannot initialise running processes")
 def init_task(self):
     task_id = self.currentrow[0]
     status = self.currentrow[5]
     if status not in ('RUNNING', 'CONTINUING', 'SLEEPING'):
         bibsched_set_status(task_id, "WAITING")
         bibsched_set_progress(task_id, "")
         bibsched_set_host(task_id, "")
         self.update_rows()
         self.repaint()
         self.display_in_footer("process initialised")
     else:
         self.display_in_footer("Cannot initialise running processes")
Exemple #3
0
def _task_run(task_run_fnc):
    """Runs the task by fetching arguments from the BibSched task queue.
    This is what BibSched will be invoking via daemon call.
    The task prints Fibonacci numbers for up to NUM on the stdout, and some
    messages on stderr.
    @param task_run_fnc: will be called as the main core function. Must return
    False in case of errors.
    Return True in case of success and False in case of failure."""

    from invenio.bibtasklet import _TASKLETS
    ## We prepare the pid file inside /prefix/var/run/taskname_id.pid
    check_running_process_user()
    try:
        pidfile_name = os.path.join(CFG_PREFIX, 'var', 'run',
            'bibsched_task_%d.pid' % _TASK_PARAMS['task_id'])
        pidfile = open(pidfile_name, 'w')
        pidfile.write(str(os.getpid()))
        pidfile.close()
    except OSError:
        register_exception(alert_admin=True)
        task_update_status("ERROR")
        return False

    ## check task status:
    task_status = task_read_status()
    if task_status not in ("WAITING", "SCHEDULED"):
        write_message("Error: The task #%d is %s.  I expected WAITING or SCHEDULED." %
            (_TASK_PARAMS['task_id'], task_status), sys.stderr)
        return False

    time_now = datetime.datetime.now()
    if _TASK_PARAMS['runtime_limit'] is not None and os.environ.get('BIBSCHED_MODE', 'manual') != 'manual':
        if not _TASK_PARAMS['runtime_limit'][0][0] <= time_now <= _TASK_PARAMS['runtime_limit'][0][1]:
            if time_now <= _TASK_PARAMS['runtime_limit'][0][0]:
                new_runtime = _TASK_PARAMS['runtime_limit'][0][0].strftime("%Y-%m-%d %H:%M:%S")
            else:
                new_runtime = _TASK_PARAMS['runtime_limit'][1][0].strftime("%Y-%m-%d %H:%M:%S")
            progress = run_sql("SELECT progress FROM schTASK WHERE id=%s", (_TASK_PARAMS['task_id'], ))
            if progress:
                progress = progress[0][0]
            else:
                progress = ''
            g =  re.match(r'Postponed (\d+) time\(s\)', progress)
            if g:
                postponed_times = int(g.group(1))
            else:
                postponed_times = 0
            if _TASK_PARAMS['sequence-id']:
                ## Also postponing other dependent tasks.
                run_sql("UPDATE schTASK SET runtime=%s, progress=%s WHERE sequenceid=%s AND status='WAITING'", (new_runtime, 'Postponed as task %s' % _TASK_PARAMS['task_id'], _TASK_PARAMS['sequence-id'])) # kwalitee: disable=sql
            run_sql("UPDATE schTASK SET runtime=%s, status='WAITING', progress=%s, host='' WHERE id=%s", (new_runtime, 'Postponed %d time(s)' % (postponed_times + 1), _TASK_PARAMS['task_id'])) # kwalitee: disable=sql
            write_message("Task #%d postponed because outside of runtime limit" % _TASK_PARAMS['task_id'])
            return True

    # Make sure the host field is updated
    # It will not be updated properly when we run
    # a task from the cli (without using the bibsched monitor)
    host = bibsched_get_host(_TASK_PARAMS['task_id'])
    if host and host != gethostname():
        write_message("Error: The task #%d is bound to %s." %
            (_TASK_PARAMS['task_id'], host), sys.stderr)
        return False
    else:
        bibsched_set_host(_TASK_PARAMS['task_id'], gethostname())

    ## initialize signal handler:
    signal.signal(signal.SIGUSR2, signal.SIG_IGN)
    signal.signal(signal.SIGTSTP, _task_sig_sleep)
    signal.signal(signal.SIGTERM, _task_sig_stop)
    signal.signal(signal.SIGQUIT, _task_sig_stop)
    signal.signal(signal.SIGABRT, _task_sig_suicide)
    signal.signal(signal.SIGINT, _task_sig_stop)
    ## we can run the task now:
    write_message("Task #%d started." % _TASK_PARAMS['task_id'])
    task_update_status("RUNNING")
    ## run the task:
    _TASK_PARAMS['task_starting_time'] = time.strftime("%Y-%m-%d %H:%M:%S", time.localtime())

    sleeptime = _TASK_PARAMS['sleeptime']
    try:
        try:
            if callable(task_run_fnc) and task_run_fnc():
                task_update_status("DONE")
            else:
                task_update_status("DONE WITH ERRORS")
        except SystemExit:
            pass
        except:
            write_message(traceback.format_exc()[:-1])
            register_exception(alert_admin=True)
            if task_get_task_param('stop_queue_on_error'):
                task_update_status("ERROR")
            else:
                task_update_status("CERROR")
    finally:
        task_status = task_read_status()
        if sleeptime:
            argv = _task_get_options(_TASK_PARAMS['task_id'], _TASK_PARAMS['task_name'])
            verbose_argv = 'Will execute: %s' % ' '.join([escape_shell_arg(str(arg)) for arg in argv])

            # Here we check if the task can shift away of has to be run at
            # a fixed time
            if task_get_task_param('fixed_time') or _TASK_PARAMS['task_name'] in CFG_BIBTASK_FIXEDTIMETASKS:
                old_runtime = run_sql("SELECT runtime FROM schTASK WHERE id=%s", (_TASK_PARAMS['task_id'], ))[0][0]
            else:
                old_runtime = None
            new_runtime = get_datetime(sleeptime, now=old_runtime)

            ## The task is a daemon. We resubmit it
            if task_status == 'DONE':
                ## It has finished in a good way. We recycle the database row
                run_sql("UPDATE schTASK SET runtime=%s, status='WAITING', progress=%s, host='' WHERE id=%s", (new_runtime, verbose_argv, _TASK_PARAMS['task_id']))
                write_message("Task #%d finished and resubmitted." % _TASK_PARAMS['task_id'])
            elif task_status == 'STOPPED':
                run_sql("UPDATE schTASK SET status='WAITING', progress=%s, host='' WHERE id=%s", (verbose_argv, _TASK_PARAMS['task_id'], ))
                write_message("Task #%d stopped and resubmitted." % _TASK_PARAMS['task_id'])
            else:
                ## We keep the bad result and we resubmit with another id.
                #res = run_sql('SELECT proc,user,sleeptime,arguments,priority FROM schTASK WHERE id=%s', (_TASK_PARAMS['task_id'], ))
                #proc, user, sleeptime, arguments, priority = res[0]
                #run_sql("""INSERT INTO schTASK (proc,user,
                            #runtime,sleeptime,status,arguments,priority)
                            #VALUES (%s,%s,%s,%s,'WAITING',%s, %s)""",
                            #(proc, user, new_runtime, sleeptime, arguments, priority))
                write_message("Task #%d finished but not resubmitted. [%s]" % (_TASK_PARAMS['task_id'], task_status))

        else:
            ## we are done:
            write_message("Task #%d finished. [%s]" % (_TASK_PARAMS['task_id'], task_status))
        ## Removing the pid
        os.remove(pidfile_name)

    #Lets call the post-process tasklets
    if task_get_task_param("post-process"):

        split = re.compile(r"(bst_.*)\[(.*)\]")
        for tasklet in task_get_task_param("post-process"):
            if not split.match(tasklet): # wrong syntax
                _usage(1, "There is an error in the post processing option "
                        "for this task.")

            aux_tasklet = split.match(tasklet)
            _TASKLETS[aux_tasklet.group(1)](**eval("dict(%s)" % (aux_tasklet.group(2))))
    return True