Exemple #1
0
class SayulitaMain(threading.Thread):

	def __init__(self):
		threading.Thread.__init__(self)

		self.speaker = Synthetizer("festival", "spanish")
		self.scheduler = Scheduler()
		self.scheduler.start()
	
	def initialization(self):
		self.speaker.speechit("Aqui proyecto Sayulita operado por x e uno gol yanqui quebec")
		self.speaker.speechit("Estacion experimental de texto a voz")

	def features(self):
		self.clock = Clock()
		self.news = FeedParserRss()

	def logging(self, command):
		if command == 'start':
			logging.basicConfig(filename='sayulita.log', filemode='w', level=logging.INFO)
			logging.basicConfig(format='%(asctime)s %(message)s')
			logging.info('Started')

	def scheduling(self):
		#self.scheduler.interval_schedule(seconds=1)
		#self.clock.clockget()
		self.news.getitems
		self.scheduler.add_cron_job(self.clock.clockget,month='*',day='*',hour='*',minute ='*',second='0')
		self.scheduler.add_cron_job(self.initialization,month='*',day='*',hour='*',minute ='*',second='15')
                self.scheduler.add_cron_job(self.news.getitems,month='*',day='*',hour='*',minute ='15,30,45',second='15')

		self.scheduler.print_jobs()
Exemple #2
0
	def handle(self, *args, **options):
		sched = Scheduler(daemonic=True)
		sched.add_cron_job(job_function,  minute='*')
		sched.configure()
		try:
		    sched.start()
		except (KeyboardInterrupt, SystemExit):
		    pass
		print sched.print_jobs()
def restart_file_schedule():

    scheduler = Scheduler(daemonic = False)

    scheduler.print_jobs()

    #scheduler.remove_jobstore('file',close=True)

    #scheduler.shutdown(wait=False)

    scheduler.add_jobstore(ShelveJobStore('/tmp/db_schedule'), 'file')

    scheduler.start()

    print 'success!'

    scheduler.print_jobs()
Exemple #4
0
def main():
    d = date.today()
    t = time(00,30)
    startDate = datetime.combine(d,t)
    startDate = startDate.replace(tzinfo=tz.tzutc())
    startDate = startDate.astimezone(tz.tzlocal())
    timeStr = startDate.strftime("%Y-%m-%d %H:%M:%S")
    print timeStr
    startDate = datetime.strptime(timeStr, "%Y-%m-%d %H:%M:%S")
    if (datetime.now() - startDate) > timedelta(seconds=1):
        startDate = startDate + timedelta(days=1)
    sched = Scheduler()
    sched.start()
    sched.add_interval_job(runDateDump, days=1, start_date=startDate.strftime("%Y-%m-%d %H:%M:%S"))
    sched.print_jobs()
    while True:
        sleep(1)
        print "."
    atexit.register(lambda: sched.shutdown(wait=True))
def start_schedule():

#if __name__ == '__main__':

    
    scheduler_pl = Scheduler(daemonic = False)

    scheduler_pl.print_jobs()


    scheduler_pl.shutdown()

    
    scheduler_pl.add_jobstore(ShelveJobStore('/tmp/db_pl_schedule'), 'file')

    v_current_jobs = scheduler_pl.get_jobs()

    print v_current_jobs

    if v_current_jobs:  # 如果job存在的话,先请客


        scheduler_pl.unschedule_func(upload_processlist) 

    scheduler_pl.add_interval_job(upload_processlist, minutes=1)
            



    scheduler_pl.start()

    print 'success!'

    scheduler_pl.print_jobs()

    '''
JOBS_DATABASE = "postgresql://*****:*****@localhost/test_jobs"

# Start the scheduler
sched = Scheduler()
sched.add_jobstore(SQLAlchemyJobStore(url=JOBS_DATABASE, tablename='apscheduler_jobs'), 'default')
sched.start()

def print_reservation_id(reservation_id):
	print "====> Reservation id is " + str(reservation_id)


if __name__ == '__main__':

	print "====> Printing jobs..."
	print sched.print_jobs()
	 
	now = datetime.datetime.now()
	start_time =  now + datetime.timedelta(seconds=3)
	later = now + datetime.timedelta(seconds=10)

	print "====> now is " + str(now)
	print "====> start_time is " + str(start_time)
	print "====> later is " + str(later)


	reservation_id = 1

	job_name = "print_reservation_id_" + str(reservation_id)

	print "====> adding start_time job"
Exemple #7
0
class PyFlowScheduler(object):
    """
    This object schedules the submission of the tasks in an :class:`Flow`.
    There are two types of errors that might occur during the execution of the jobs:

        #. Python exceptions
        #. Abinit Errors.

    Python exceptions are easy to detect and are usually due to a bug in abinitio or random errors such as IOError.
    The set of Abinit Errors is much much broader. It includes wrong input data, segmentation
    faults, problems with the resource manager, etc. Abinitio tries to handle the most common cases
    but there's still a lot of room for improvement.
    Note, in particular, that `PyFlowScheduler` will shutdown automatically if

        #. The number of python exceptions is > MAX_NUM_PYEXC

        #. The number of Abinit Errors (i.e. the number of tasks whose status is S_ERROR) is > MAX_NUM_ERRORS

        #. The number of jobs launched becomes greater than (SAFETY_RATIO * total_number_of_tasks).

        #. The scheduler will send an email to the user (specified by mailto) every REMINDME_S seconds.
           If the mail cannot be sent, it will shutdown automatically.
           This check prevents the scheduler from being trapped in an infinite loop.
    """
    # Configuration file.
    YAML_FILE = "scheduler.yml"
    USER_CONFIG_DIR = os.path.join(os.getenv("HOME"), ".abinit", "abipy")

    DEBUG = 0

    Error = PyFlowSchedulerError

    def __init__(self, **kwargs):
        """
        Args:
            weeks: number of weeks to wait
            days: number of days to wait
            hours: number of hours to wait
            minutes: number of minutes to wait
            seconds: number of seconds to wait
            verbose: (int) verbosity level
            max_njobs_inque: Limit on the number of jobs that can be present in the queue
            use_dynamic_manager: True if the :class:`TaskManager` must be re-initialized from
                file before launching the jobs. Default: False
            max_nlaunch: Maximum number of tasks launched by radpifire (default -1 i.e. no limit)
        """
        # Options passed to the scheduler.
        self.sched_options = AttrDict(
            weeks=kwargs.pop("weeks", 0),
            days=kwargs.pop("days", 0),
            hours=kwargs.pop("hours", 0),
            minutes=kwargs.pop("minutes", 0),
            seconds=kwargs.pop("seconds", 0),
            #start_date=kwargs.pop("start_date", None),
        )

        if all(not v for v in self.sched_options.values()):
            raise self.Error("Wrong set of options passed to the scheduler.")

        self.mailto = kwargs.pop("mailto", None)
        self.verbose = int(kwargs.pop("verbose", 0))
        self.use_dynamic_manager = kwargs.pop("use_dynamic_manager", False)
        self.max_njobs_inqueue = kwargs.pop("max_njobs_inqueue", 200)

        self.REMINDME_S = float(kwargs.pop("REMINDME_S", 4 * 24 * 3600))
        self.MAX_NUM_PYEXCS = int(kwargs.pop("MAX_NUM_PYEXCS", 0))
        self.MAX_NUM_ABIERRS = int(kwargs.pop("MAX_NUM_ABIERRS", 0))
        self.SAFETY_RATIO = int(kwargs.pop("SAFETY_RATIO", 5))
        #self.MAX_ETIME_S = kwargs.pop("MAX_ETIME_S", )
        self.max_nlaunch = kwargs.pop("max_nlaunch", -1)

        if kwargs:
            raise self.Error("Unknown arguments %s" % kwargs)

        if has_sched_v3:
            from apscheduler.schedulers.blocking import BlockingScheduler
            self.sched = BlockingScheduler()
        else:
            from apscheduler.scheduler import Scheduler
            self.sched = Scheduler(standalone=True)

        self.nlaunch = 0
        self.num_reminders = 1

        # Used to keep track of the exceptions raised while the scheduler is running
        self.exceptions = collections.deque(maxlen=self.MAX_NUM_PYEXCS + 10)

        # Used to push additional info during the execution.
        self.history = collections.deque(maxlen=100)

    @classmethod
    def from_file(cls, filepath):
        """Read the configuration parameters from a Yaml file."""
        with open(filepath, "r") as fh:
            return cls(**yaml.load(fh))

    @classmethod
    def from_string(cls, s):
        """Create an istance from string s containing a YAML dictionary."""
        stream = cStringIO(s)
        stream.seek(0)

        return cls(**yaml.load(stream))

    @classmethod
    def from_user_config(cls):
        """
        Initialize the :class:`PyFlowScheduler` from the YAML file 'scheduler.yml'.
        Search first in the working directory and then in the configuration directory of abipy.

        Raises:
            RuntimeError if file is not found.
        """
        # Try in the current directory.
        path = os.path.join(os.getcwd(), cls.YAML_FILE)

        if os.path.exists(path):
            return cls.from_file(path)

        # Try in the configuration directory.
        path = os.path.join(cls.USER_CONFIG_DIR, cls.YAML_FILE)

        if os.path.exists(path):
            return cls.from_file(path)

        err_msg = "Cannot locate %s neither in current directory nor in %s" % (
            cls.YAML_FILE, path)
        raise cls.Error(err_msg)

    def __str__(self):
        """String representation."""
        lines = [self.__class__.__name__ + ", Pid: %d" % self.pid]
        app = lines.append

        app("Scheduler options: %s" % str(self.sched_options))
        app(80 * "=")
        app(str(self.flow))

        return "\n".join(lines)

    @property
    def pid(self):
        """The pid of the process associated to the scheduler."""
        try:
            return self._pid

        except AttributeError:
            self._pid = os.getpid()
            return self._pid

    @property
    def pid_file(self):
        """
        Absolute path of the file with the pid.
        The file is located in the workdir of the flow
        """
        return self._pid_file

    @property
    def flow(self):
        """`Flow`."""
        return self._flow

    @property
    def num_excs(self):
        """Number of exceptions raised so far."""
        return len(self.exceptions)

    def get_delta_etime(self):
        """Returns a `timedelta` object representing with the elapsed time."""
        return timedelta(seconds=(time.time() - self.start_time))

    def add_flow(self, flow):
        """Add an :class:`Flow` flow to the scheduler."""
        if hasattr(self, "_flow"):
            raise self.Error("Only one flow can be added to the scheduler.")

        pid_file = os.path.join(flow.workdir, "_PyFlowScheduler.pid")

        if os.path.isfile(pid_file):
            flow.show_status()

            err_msg = ("""
                pid_file %s already exists
                There are two possibilities:

                   1) There's an another instance of PyFlowScheduler running
                   2) The previous scheduler didn't exit in a clean way

                To solve case 1:
                   Kill the previous scheduler (use 'kill pid' where pid is the number reported in the file)
                   Then you can restart the new scheduler.

                To solve case 2:
                   Remove the pid_file and restart the scheduler.

                Exiting""" % pid_file)

            raise self.Error(err_msg)

        with open(pid_file, "w") as fh:
            fh.write(str(self.pid))

        self._pid_file = pid_file
        self._flow = flow

    def start(self):
        """
        Starts the scheduler in a new thread. Returns True if success.
        In standalone mode, this method will block until there are no more scheduled jobs.
        """
        self.history.append("Started on %s" % time.asctime())
        self.start_time = time.time()

        if has_sched_v3:
            self.sched.add_job(self.callback, "interval", **self.sched_options)
        else:
            self.sched.add_interval_job(self.callback, **self.sched_options)

        errors = self.flow.look_before_you_leap()
        if errors:
            print(errors)
            self.exceptions.append(errors)
            return False

        # Try to run the job immediately. If something goes wrong return without initializing the scheduler.
        self._runem_all()

        if self.exceptions:
            self.cleanup()
            self.send_email(
                msg=
                "Error while trying to run the flow for the first time!\n %s" %
                self.exceptions)
            return False

        self.sched.start()
        return True

    def _runem_all(self):
        """
        This function checks the status of all tasks,
        tries to fix tasks that went unconverged, abicritical, or queuecritical
        and tries to run all the tasks that can be submitted.+
        """
        excs = []
        flow = self.flow

        # Allow to change the manager at run-time
        if self.use_dynamic_manager:
            from pymatgen.io.abinitio.tasks import TaskManager
            new_manager = TaskManager.from_user_config()
            for work in flow:
                work.set_manager(new_manager)

        nqjobs = flow.get_njobs_in_queue()
        if nqjobs is None:
            nqjobs = 0
            print('Cannot get njobs_inqueue')

        if nqjobs >= self.max_njobs_inqueue:
            print("Too many jobs in the queue, returning")
            return

        if self.max_nlaunch == -1:
            max_nlaunch = self.max_njobs_inqueue - nqjobs
        else:
            max_nlaunch = min(self.max_njobs_inqueue - nqjobs,
                              self.max_nlaunch)

        # check status
        flow.check_status()
        flow.show_status()

        # fix problems
        # Try to restart the unconverged tasks
        # todo donot fire here but prepare for fireing in rapidfire
        for task in self.flow.unconverged_tasks:
            try:
                logger.info("Flow will try restart task %s" % task)
                fired = task.restart()
                if fired:
                    self.nlaunch += 1
                    max_nlaunch -= 1
                    if max_nlaunch == 0:
                        print("Restart: too many jobs in the queue, returning")
                        flow.pickle_dump()
                        return
            except Exception:
                excs.append(straceback())

        # move here from withing rapid fire ...
        # fix only prepares for restarting, and sets to ready
        flow.fix_critical()

        # update database
        flow.pickle_dump()

        #if self.num_restarts == self.max_num_restarts:
        #    info_msg = "Reached maximum number of restarts. Cannot restart anymore Returning"
        #    logger.info(info_msg)
        #    self.history.append(info_msg)
        #    return 1

        # Submit the tasks that are ready.
        try:
            nlaunch = PyLauncher(flow).rapidfire(max_nlaunch=max_nlaunch,
                                                 sleep_time=10)
            self.nlaunch += nlaunch

            if nlaunch:
                print("[%s] Number of launches: %d" %
                      (time.asctime(), nlaunch))

        except Exception:
            excs.append(straceback())

        flow.show_status()

        if excs:
            logger.critical("*** Scheduler exceptions:\n *** %s" %
                            "\n".join(excs))
            self.exceptions.extend(excs)

    def callback(self):
        """The function that will be executed by the scheduler."""
        try:
            return self._callback()
        except:
            # All exceptions raised here will trigger the shutdown!
            self.exceptions.append(straceback())
            self.shutdown(msg="Exception raised in callback!")

    def _callback(self):
        """The actual callback."""
        if self.DEBUG:
            # Show the number of open file descriptors
            print(">>>>> _callback: Number of open file descriptors: %s" %
                  get_open_fds())
        #print('before _runem_all in _callback')

        self._runem_all()

        # Mission accomplished. Shutdown the scheduler.
        all_ok = self.flow.all_ok
        if self.verbose:
            print("all_ok", all_ok)

        if all_ok:
            self.shutdown(
                msg=
                "All tasks have reached S_OK. Will shutdown the scheduler and exit"
            )

        # Handle failures.
        err_msg = ""

        # Shall we send a reminder to the user?
        delta_etime = self.get_delta_etime()

        if delta_etime.total_seconds() > self.num_reminders * self.REMINDME_S:
            self.num_reminders += 1
            msg = (
                "Just to remind you that the scheduler with pid %s, flow %s\n has been running for %s "
                % (self.pid, self.flow, delta_etime))
            retcode = self.send_email(msg, tag="[REMINDER]")

            if retcode:
                # Cannot send mail, shutdown now!
                msg += (
                    "\nThe scheduler tried to send an e-mail to remind the user\n"
                    + " but send_email returned %d. Aborting now" % retcode)
                err_msg += msg

        #if delta_etime.total_seconds() > self.MAX_ETIME_S:
        #    err_msg += "\nExceeded MAX_ETIME_S %s. Will shutdown the scheduler and exit" % self.MAX_ETIME_S

        # Too many exceptions. Shutdown the scheduler.
        if self.num_excs > self.MAX_NUM_PYEXCS:
            msg = "Number of exceptions %s > %s. Will shutdown the scheduler and exit" % (
                self.num_excs, self.MAX_NUM_PYEXCS)
            err_msg += boxed(msg)

        # Paranoid check: disable the scheduler if we have submitted
        # too many jobs (it might be due to some bug or other external reasons
        # such as race conditions between difference callbacks!)
        if self.nlaunch > self.SAFETY_RATIO * self.flow.num_tasks:
            msg = "Too many jobs launched %d. Total number of tasks = %s, Will shutdown the scheduler and exit" % (
                self.nlaunch, self.flow.num_tasks)
            err_msg += boxed(msg)

        # Count the number of tasks with status == S_ERROR.
        if self.flow.num_errored_tasks > self.MAX_NUM_ABIERRS:
            msg = "Number of tasks with ERROR status %s > %s. Will shutdown the scheduler and exit" % (
                self.flow.num_errored_tasks, self.MAX_NUM_ABIERRS)
            err_msg += boxed(msg)

        # Count the number of tasks with status == S_UNCONVERGED.
        #if self.flow.num_unconverged_tasks:
        #    # TODO: this is needed to avoid deadlocks, automatic restarting is not available yet
        #    msg = ("Found %d unconverged tasks."
        #           "Automatic restarting is not available yet. Will shutdown the scheduler and exit"
        #           % self.flow.num_unconverged_tasks)
        #    err_msg += boxed(msg)

        #deadlocks = self.detect_deadlocks()
        #if deadlocks:
        #    msg = ("Detected deadlocks in flow. Will shutdown the scheduler and exit"
        #           % self.flow.num_unconverged_tasks)
        #    err_msg += boxed(msg)

        if err_msg:
            # Something wrong. Quit
            self.shutdown(err_msg)

        return len(self.exceptions)

    def cleanup(self):
        """Cleanup routine: remove the pid file and save the pickle database"""
        try:
            os.remove(self.pid_file)
        except OSError:
            logger.critical("Could not remove pid_file")
            pass

        # Save the final status of the flow.
        self.flow.pickle_dump()

    def shutdown(self, msg):
        """Shutdown the scheduler."""
        try:
            self.cleanup()

            #if False and self.flow.has_db:
            #    try:
            #        self.flow.db_insert()
            #    except Exception:
            #         logger.critical("MongoDb insertion failed.")

            self.history.append("Completed on %s" % time.asctime())
            self.history.append("Elapsed time %s" % self.get_delta_etime())

            if self.DEBUG:
                print(">>>>> shutdown: Number of open file descriptors: %s" %
                      get_open_fds())

            retcode = self.send_email(msg)
            if self.DEBUG:
                print("send_mail retcode", retcode)

            # Write file with the list of exceptions:
            if self.exceptions:
                dump_file = os.path.join(self.flow.workdir, "_exceptions")
                with open(dump_file, "w") as fh:
                    fh.writelines(self.exceptions)
                    fh.write("Shutdown message:\n%s" % msg)

        finally:
            # Shutdown the scheduler thus allowing the process to exit.
            print('this should be the shutdown of the scheduler')

            # Unschedule all the jobs before calling shutdown
            self.sched.print_jobs()
            for job in self.sched.get_jobs():
                self.sched.unschedule_job(job)
            self.sched.print_jobs()

            self.sched.shutdown()
            # Uncomment the line below if shutdown does not work!
            #os.system("kill -9 %d" % os.getpid())

    def send_email(self, msg, tag=None):
        """
        Send an e-mail before completing the shutdown.
        Returns 0 if success.
        """
        try:
            return self._send_email(msg, tag)
        except:
            self.exceptions.append(straceback())
            return -2

    def _send_email(self, msg, tag):
        if self.mailto is None:
            return -1

        header = msg.splitlines()
        app = header.append

        app("Submitted on %s" % time.ctime(self.start_time))
        app("Completed on %s" % time.asctime())
        app("Elapsed time %s" % str(self.get_delta_etime()))
        app("Number of errored tasks: %d" % self.flow.num_errored_tasks)
        app("Number of unconverged tasks: %d" %
            self.flow.num_unconverged_tasks)

        strio = cStringIO()
        strio.writelines("\n".join(header) + 4 * "\n")

        # Add the status of the flow.
        self.flow.show_status(stream=strio)

        if self.exceptions:
            # Report the list of exceptions.
            strio.writelines(self.exceptions)

        if tag is None:
            tag = " [ALL OK]" if self.flow.all_ok else " [WARNING]"

        return sendmail(subject=self.flow.name + tag,
                        text=strio.getvalue(),
                        mailto=self.mailto)
Exemple #8
0
class PyFlowScheduler(object):
    """
    This object schedules the submission of the tasks in an `AbinitFlow`.
    There are two types of errors that might occur during the execution of the jobs:

        #. Python exceptions
        #. Abinit Errors.

    Python exceptions are easy to detect and are usually due to a bug in abinitio or random errors such as IOError.
    The set of Abinit Errors is much much broader. It includes wrong input data, segmentation
    faults, problems with the resource manager, etc. Abinitio tries to handle the most common cases
    but there's still a lot of room for improvement.
    Note, in particular, that `PyFlowScheduler` will shutdown automatically if

        #. The number of python exceptions is > MAX_NUM_PYEXC

        #. The number of Abinit Errors (i.e. the number of tasks whose status is S_ERROR) is > MAX_NUM_ERRORS

        #. The number of jobs launched becomes greater than (SAFETY_RATIO * total_number_of_tasks).

        #. The scheduler will send an email to the user (specified by mailto) every REMINDME_S seconds.
           If the mail cannot be sent, it will shutdown automatically.
           This check prevents the scheduler from being trapped in an infinite loop.
    """
    # Configuration file.
    YAML_FILE = "scheduler.yml"
    USER_CONFIG_DIR = os.path.join(os.getenv("HOME"), ".abinit", "abipy")

    DEBUG = 0

    Error = PyFlowSchedulerError

    def __init__(self, **kwargs):
        """
        Args:
            weeks:
                number of weeks to wait
            days:
                number of days to wait
            hours:
                number of hours to wait
            minutes:
                number of minutes to wait
            seconds:
                number of seconds to wait
            verbose:
                (int) verbosity level
            max_njobs_inque:
                Limit on the number of jobs that can be present in the queue
            use_dynamic_manager:
                True if the task manager must be re-initialized from 
                file before launching the jobs. Default: False
            max_nlaunch:
                Maximum number of tasks launched by radpifire (default -1 i.e. no limit)
        """
        # Options passed to the scheduler.
        self.sched_options = AttrDict(
            weeks=kwargs.pop("weeks", 0),
            days=kwargs.pop("days", 0),
            hours=kwargs.pop("hours", 0),
            minutes=kwargs.pop("minutes", 0),
            seconds=kwargs.pop("seconds", 0),
            #start_date=kwargs.pop("start_date", None),
        )

        if all(not v for v in self.sched_options.values()):
            raise self.Error("Wrong set of options passed to the scheduler.")

        self.mailto = kwargs.pop("mailto", None)
        self.verbose = int(kwargs.pop("verbose", 0))
        self.use_dynamic_manager = kwargs.pop("use_dynamic_manager", False)
        self.max_njobs_inqueue = kwargs.pop("max_njobs_inqueue", 200)

        self.REMINDME_S = float(kwargs.pop("REMINDME_S", 4 * 24 * 3600))
        self.MAX_NUM_PYEXCS = int(kwargs.pop("MAX_NUM_PYEXCS", 0))
        self.MAX_NUM_ABIERRS = int(kwargs.pop("MAX_NUM_ABIERRS", 0))
        self.SAFETY_RATIO = int(kwargs.pop("SAFETY_RATIO", 5))
        #self.MAX_ETIME_S = kwargs.pop("MAX_ETIME_S", )
        self.max_nlaunch = kwargs.pop("max_nlaunch", -1)

        if kwargs:
            raise self.Error("Unknown arguments %s" % kwargs)

        if has_sched_v3:
            from apscheduler.schedulers.blocking import BlockingScheduler
            self.sched = BlockingScheduler()
        else:
            from apscheduler.scheduler import Scheduler
            self.sched = Scheduler(standalone=True)

        self.nlaunch = 0
        self.num_reminders = 1

        # Used to keep track of the exceptions raised while the scheduler is running
        self.exceptions = collections.deque(maxlen=self.MAX_NUM_PYEXCS + 10)

        # Used to push additional info during the execution.
        self.history = collections.deque(maxlen=100)

    @classmethod
    def from_file(cls, filepath):
        """Read the configuration parameters from a Yaml file."""
        with open(filepath, "r") as fh:
            return cls(**yaml.load(fh))

    @classmethod
    def from_string(cls, s):
        """Create an istance from string s containing a YAML dictionary."""
        stream = cStringIO(s)
        stream.seek(0)

        return cls(**yaml.load(stream))

    @classmethod
    def from_user_config(cls):
        """
        Initialize the `PyFlowScheduler` from the YAML file 'scheduler.yml'.
        Search first in the working directory and then in the configuration
        directory of abipy.

        Raises:
            RuntimeError if file is not found.
        """
        # Try in the current directory.
        path = os.path.join(os.getcwd(), cls.YAML_FILE)

        if os.path.exists(path):
            return cls.from_file(path)

        # Try in the configuration directory.
        path = os.path.join(cls.USER_CONFIG_DIR, cls.YAML_FILE)

        if os.path.exists(path):
            return cls.from_file(path)

        err_msg = "Cannot locate %s neither in current directory nor in %s" % (cls.YAML_FILE, path)
        raise cls.Error(err_msg)

    def __str__(self):
        """String representation."""
        lines = [self.__class__.__name__ + ", Pid: %d" % self.pid]
        app = lines.append

        app("Scheduler options: %s" % str(self.sched_options))
        app(80 * "=")
        app(str(self.flow))

        return "\n".join(lines)

    @property
    def pid(self):
        """The pid of the process associated to the scheduler."""
        try:
            return self._pid

        except AttributeError:
            self._pid = os.getpid()
            return self._pid

    @property
    def pid_file(self):
        """
        Absolute path of the file with the pid.
        The file is located in the workdir of the flow
        """
        return self._pid_file

    @property
    def flow(self):
        """`AbinitFlow`."""
        return self._flow

    @property
    def num_excs(self):
        """Number of exceptions raised so far."""
        return len(self.exceptions)

    def get_delta_etime(self):
        """Returns a `timedelta` object representing with the elapsed time."""
        return timedelta(seconds=(time.time() - self.start_time))

    def add_flow(self, flow):
        """Add an `AbinitFlow` flow to the scheduler."""
        if hasattr(self, "_flow"):
            raise self.Error("Only one flow can be added to the scheduler.")

        pid_file = os.path.join(flow.workdir, "_PyFlowScheduler.pid")

        if os.path.isfile(pid_file):
            flow.show_status()

            err_msg = ("""
                pid_file %s already exists
                There are two possibilities:

                   1) There's an another instance of PyFlowScheduler running
                   2) The previous scheduler didn't exit in a clean way

                To solve case 1:
                   Kill the previous scheduler (use 'kill pid' where pid is the number reported in the file)
                   Then you can restart the new scheduler.

                To solve case 2:
                   Remove the pid_file and restart the scheduler.

                Exiting""" % pid_file)

            raise self.Error(err_msg)

        with open(pid_file, "w") as fh:
            fh.write(str(self.pid))

        self._pid_file = pid_file
        self._flow = flow

    def start(self):
        """
        Starts the scheduler in a new thread. Returns True if success.
        In standalone mode, this method will block until there are no more scheduled jobs.
        """
        self.history.append("Started on %s" % time.asctime())
        self.start_time = time.time()

        if has_sched_v3:
            self.sched.add_job(self.callback, "interval", **self.sched_options)
        else:
            self.sched.add_interval_job(self.callback, **self.sched_options)

        errors = self.flow.look_before_you_leap()
        if errors:
            print(errors)
            self.exceptions.append(errors)
            return False

        # Try to run the job immediately. If something goes wrong return without initializing the scheduler.
        self._runem_all()

        if self.exceptions:
            self.cleanup()
            self.send_email(msg="Error while trying to run the flow for the first time!\n %s" % self.exceptions)
            return False

        self.sched.start()
        return True

    def _runem_all(self):
        """
        This function checks the status of all tasks,
        tries to fix tasks that went unconverged, abicritical, or queuecritical
        and tries to run all the tasks that can be submitted.+
        """
        excs = []
        flow = self.flow

        # Allow to change the manager at run-time
        if self.use_dynamic_manager:
            from pymatgen.io.abinitio.tasks import TaskManager
            new_manager = TaskManager.from_user_config()
            for work in flow:
                work.set_manager(new_manager)

        nqjobs = flow.get_njobs_in_queue()
        if nqjobs is None:
            nqjobs = 0
            print('Cannot get njobs_inqueue')

        if nqjobs >= self.max_njobs_inqueue:
            print("Too many jobs in the queue, returning")
            return

        if self.max_nlaunch == -1:
            max_nlaunch = self.max_njobs_inqueue - nqjobs
        else:
            max_nlaunch = min(self.max_njobs_inqueue - nqjobs, self.max_nlaunch)

        # check status
        flow.check_status()
        flow.show_status()

        # fix problems
        # Try to restart the unconverged tasks
        # todo donot fire here but prepare for fireing in rapidfire
        for task in self.flow.unconverged_tasks:
            try:
                logger.info("AbinitFlow will try restart task %s" % task)
                fired = task.restart()
                if fired: 
                    self.nlaunch += 1
                    max_nlaunch -= 1
                    if max_nlaunch == 0:
                        print("Restart: too many jobs in the queue, returning")
                        flow.pickle_dump()
                        return
            except Exception:
                excs.append(straceback())

        # move here from withing rapid fire ...
        # fix only prepares for restarting, and sets to ready
        flow.fix_critical()

        # update database
        flow.pickle_dump()

        #if self.num_restarts == self.max_num_restarts:
        #    info_msg = "Reached maximum number of restarts. Cannot restart anymore Returning"
        #    logger.info(info_msg)
        #    self.history.append(info_msg)
        #    return 1

        # Submit the tasks that are ready.
        try:
            nlaunch = PyLauncher(flow).rapidfire(max_nlaunch=max_nlaunch, sleep_time=10)
            self.nlaunch += nlaunch

            if nlaunch:
                print("[%s] Number of launches: %d" % (time.asctime(), nlaunch))

        except Exception:
            excs.append(straceback())

        flow.show_status()

        if excs:
            logger.critical("*** Scheduler exceptions:\n *** %s" % "\n".join(excs))
            self.exceptions.extend(excs)

    def callback(self):
        """The function that will be executed by the scheduler."""
        try:
            return self._callback()
        except:
            # All exceptions raised here will trigger the shutdown!
            self.exceptions.append(straceback())
            self.shutdown(msg="Exception raised in callback!")

    def _callback(self):
        """The actual callback."""
        if self.DEBUG:
            # Show the number of open file descriptors
            print(">>>>> _callback: Number of open file descriptors: %s" % get_open_fds())
        #print('before _runem_all in _callback')

        self._runem_all()

        # Mission accomplished. Shutdown the scheduler.
        all_ok = self.flow.all_ok
        if self.verbose:
            print("all_ok", all_ok)

        if all_ok:
            self.shutdown(msg="All tasks have reached S_OK. Will shutdown the scheduler and exit")

        # Handle failures.
        err_msg = ""

        # Shall we send a reminder to the user?
        delta_etime = self.get_delta_etime()

        if delta_etime.total_seconds() > self.num_reminders * self.REMINDME_S:
            self.num_reminders += 1
            msg = ("Just to remind you that the scheduler with pid %s, flow %s\n has been running for %s " %
                  (self.pid, self.flow, delta_etime))
            retcode = self.send_email(msg, tag="[REMINDER]")

            if retcode:
                # Cannot send mail, shutdown now!
                msg += ("\nThe scheduler tried to send an e-mail to remind the user\n" +
                        " but send_email returned %d. Aborting now" % retcode)
                err_msg += msg

        #if delta_etime.total_seconds() > self.MAX_ETIME_S:
        #    err_msg += "\nExceeded MAX_ETIME_S %s. Will shutdown the scheduler and exit" % self.MAX_ETIME_S

        # Too many exceptions. Shutdown the scheduler.
        if self.num_excs > self.MAX_NUM_PYEXCS:
            msg = "Number of exceptions %s > %s. Will shutdown the scheduler and exit" % (
                self.num_excs, self.MAX_NUM_PYEXCS)
            err_msg += boxed(msg)

        # Paranoid check: disable the scheduler if we have submitted
        # too many jobs (it might be due to some bug or other external reasons 
        # such as race conditions between difference callbacks!)
        if self.nlaunch > self.SAFETY_RATIO * self.flow.num_tasks:
            msg = "Too many jobs launched %d. Total number of tasks = %s, Will shutdown the scheduler and exit" % (
                self.nlaunch, self.flow.num_tasks)
            err_msg += boxed(msg)

        # Count the number of tasks with status == S_ERROR.
        if self.flow.num_errored_tasks > self.MAX_NUM_ABIERRS:
            msg = "Number of tasks with ERROR status %s > %s. Will shutdown the scheduler and exit" % (
                self.flow.num_errored_tasks, self.MAX_NUM_ABIERRS)
            err_msg += boxed(msg)

        # Count the number of tasks with status == S_UNCONVERGED.
        #if self.flow.num_unconverged_tasks:
        #    # TODO: this is needed to avoid deadlocks, automatic restarting is not available yet
        #    msg = ("Found %d unconverged tasks."
        #           "Automatic restarting is not available yet. Will shutdown the scheduler and exit"
        #           % self.flow.num_unconverged_tasks)
        #    err_msg += boxed(msg)

        #deadlocks = self.detect_deadlocks()
        #if deadlocks:
        #    msg = ("Detected deadlocks in flow. Will shutdown the scheduler and exit"
        #           % self.flow.num_unconverged_tasks)
        #    err_msg += boxed(msg)

        if err_msg:
            # Something wrong. Quit
            self.shutdown(err_msg)

        return len(self.exceptions)

    def cleanup(self):
        """
        Cleanup routine: remove the pid file and save the pickle database
        """
        try:
            os.remove(self.pid_file)
        except OSError:
            logger.critical("Could not remove pid_file")
            pass

        # Save the final status of the flow.
        self.flow.pickle_dump()

    def shutdown(self, msg):
        """Shutdown the scheduler."""
        try:
            self.cleanup()

            #if False and self.flow.has_db:
            #    try:
            #        self.flow.db_insert()
            #    except Exception:
            #         logger.critical("MongoDb insertion failed.")

            self.history.append("Completed on %s" % time.asctime())
            self.history.append("Elapsed time %s" % self.get_delta_etime())

            if self.DEBUG:
                print(">>>>> shutdown: Number of open file descriptors: %s" % get_open_fds())

            retcode = self.send_email(msg)
            if self.DEBUG:
                print("send_mail retcode", retcode)

            # Write file with the list of exceptions:
            if self.exceptions:
                dump_file = os.path.join(self.flow.workdir, "_exceptions")
                with open(dump_file, "w") as fh:
                    fh.writelines(self.exceptions)
                    fh.write("Shutdown message:\n%s" % msg)

        finally:
            # Shutdown the scheduler thus allowing the process to exit.
            print('this should be the shutdown of the scheduler')

            # Unschedule all the jobs before calling shutdown
            self.sched.print_jobs()
            for job in self.sched.get_jobs():
                self.sched.unschedule_job(job)
            self.sched.print_jobs()
                
            self.sched.shutdown()
            # Uncomment the line below if shutdown does not work!
            #os.system("kill -9 %d" % os.getpid())

    def send_email(self, msg, tag=None):
        """
        Send an e-mail before completing the shutdown.
        Returns 0 if success.
        """
        try:
            return self._send_email(msg, tag)
        except:
            self.exceptions.append(straceback())
            return -2

    def _send_email(self, msg, tag):
        if self.mailto is None:
            return -1

        header = msg.splitlines()
        app = header.append

        app("Submitted on %s" % time.ctime(self.start_time))
        app("Completed on %s" % time.asctime())
        app("Elapsed time %s" % str(self.get_delta_etime()))
        app("Number of errored tasks: %d" % self.flow.num_errored_tasks)
        app("Number of unconverged tasks: %d" % self.flow.num_unconverged_tasks)

        strio = cStringIO()
        strio.writelines("\n".join(header) + 4 * "\n")

        # Add the status of the flow.
        self.flow.show_status(stream=strio)

        if self.exceptions:
            # Report the list of exceptions.
            strio.writelines(self.exceptions)

        if tag is None:
            tag = " [ALL OK]" if self.flow.all_ok else " [WARNING]"

        return sendmail(subject=self.flow.name + tag, text=strio.getvalue(), mailto=self.mailto)
Exemple #9
0
        '-leases',
        dest='leases',
        default='/home/router/dnsmasq.leases')
    parser.add_argument(
        '-assoclist',
        dest='assoclist',
        default='/home/router/assoclist')
    args = parser.parse_args()

    if not os.path.isfile(args.leases):
        logger.debug('Not a file: %s' % args.leases)
        exit(1)

    global DATA, OPEN_IMAGE, CLOSE_IMAGE, LEASES_FILENAME, ASSOCLIST_FILENAME
    ASSOCLIST_FILENAME = args.assoclist
    LEASES_FILENAME = args.leases
    OPEN_IMAGE = get_file_content('xcj_open_badge.gif')
    CLOSE_IMAGE = get_file_content('xcj_closed_badge.gif')

    DATA = WifiData(client())

    update_macs()
    update_leases()
    update_excluded()

    SCHED.start()
    SCHED.print_jobs()

    logger.info('Starting API server')
    run(host='0.0.0.0', reloader=True, port=9000, debug=True)
Exemple #10
0
class Controller:
    def __init__(self):

        # Start the scheduler
        self.sched = Scheduler()
        self.sched.start()

        # set default turn on and turn off times
        # default to everyday
        self.daysLabel=dayLabels[0]
        self.days=dayOptions[self.daysLabel]
        # turn on at 7am
        self.turnOnHour = 7
        self.turnOnMin = 0
        self.DisplayOnJob = self.sched.add_cron_job(self.displayPowerOn, day_of_week=self.days, hour=self.turnOnHour, minute=self.turnOnMin)

        # turn off at 7pm
        self.turnOffHour = 19
        self.turnOffMin = 0
        self.DisplayOffJob = self.sched.add_cron_job(self.displayPowerOff, day_of_week=self.days, hour=self.turnOffHour, minute=self.turnOffMin)

        # print the menu
        self.printMenu()

    def printMenu(self):
        print("""
        Timer Test Menu

            1. Set Turn On/Off Days
            2. Set Turn On Time
            3. Set Turn Off Time
            4. Get On-Off Times
            5. Quit/Exit
            """)

        # get the selection
        self.main_selection = input("Please select: ")
        print("\n")

        if self.main_selection == '1':
            print('Current Turn On/Off days:',self.daysLabel)
            print('1. Daily')
            print('2. WeekDays')
            self.newDays = input("Select which days to use: ")
            # validate entry
            if int(self.newDays)==1 or int(self.newDays)==2:
                self.daysLabel = dayLabels[int(self.newDays)-1]
                self.days = dayOptions[self.daysLabel]
                # cancel old jobs and start new ones
                self.schedDisplayOn()
                self.schedDisplayOff()
                print('New Turn On/Off days:', self.daysLabel)
            else:
                print('Invalid entry')
            self.printMenu()
        elif self.main_selection == '2':
            print('Current Turn On time ', str(self.turnOnHour), ':', str(self.turnOnMin).zfill(2), sep='')
            self.newTurnOnHour = input("Enter new turn on hour (in 24 hour clock): ")
            # validate hour entry
            if int(self.newTurnOnHour) < 24 and int(self.newTurnOnHour) >= 0:
                self.newTurnOnMin = input("Enter new turn on minute: ")
                # validate min entry
                if int(self.newTurnOnMin) < 60 and int(self.newTurnOnMin) >= 0:
                    # assign new hour
                    self.turnOnHour = int(self.newTurnOnHour)
                    # assign new minute
                    self.turnOnMin = int(self.newTurnOnMin)
                    # cancel old job and start new one
                    self.schedDisplayOn()
                    # print new turn on time
                    print('New Turn On time ', str(self.turnOnHour), ':', str(self.turnOnMin).zfill(2), sep='')
                else:
                    print('Invalid Turn On Min')
            else:
                print('Invalid Turn On Hour')
            self.printMenu()
        elif self.main_selection == '3':
            print('Current Turn Off time ', str(self.turnOffHour), ':', str(self.turnOffMin).zfill(2), sep='')
            self.newTurnOffHour = input("Enter new turn off hour (in 24 hour clock): ")
            # validate hour entry
            if int(self.newTurnOffHour) < 24 and int(self.newTurnOffHour) >= 0:
                self.newTurnOffMin = input("Enter new turn off minute: ")
                # validate min entry
                if int(self.newTurnOffMin) < 60 and int(self.newTurnOffMin) >= 0:
                    # assign new hour
                    self.turnOffHour = int(self.newTurnOffHour)
                    # assign new minute
                    self.turnOffMin = int(self.newTurnOffMin)
                    # cancel old job and start new one
                    self.schedDisplayOff()
                    # print new turn off time
                    print('New Turn Off time ', str(self.turnOffHour), ':', str(self.turnOffMin).zfill(2), sep='')
                else:
                    print('Invalid Turn Off Min')
            else:
                print('Invalid Turn Off Hour')
            self.printMenu()
        elif self.main_selection == '4':
            print('Turn On ',self.daysLabel,' at ',str(self.turnOnHour),':',str(self.turnOnMin).zfill(2), sep='')
            print('Turn Off ',self.daysLabel,' at ', str(self.turnOffHour), ':', str(self.turnOffMin).zfill(2), sep='')
            self.sched.print_jobs()
            self.printMenu()
        elif self.main_selection == '5':
            sys.exit()
        else:
            print("Invalid selection.\n")
            self.printMenu()

    def displayPowerOn(self):
        print("Display On")

    def displayPowerOff(self):
        print("Display Off")

    def schedDisplayOn(self):
        # cancel the old job
        self.sched.unschedule_job(self.DisplayOnJob)
        # schedule the new job
        self.DisplayOnJob = self.sched.add_cron_job(self.displayPowerOn, day_of_week=self.days,
                                                    hour=self.turnOnHour, minute=self.turnOnMin)

    def schedDisplayOff(self):
        # cancel the old job
        self.sched.unschedule_job(self.DisplayOffJob)
        # schedule the new job
        self.DisplayOffJob = self.sched.add_cron_job(self.displayPowerOff, day_of_week=self.days,
                                                     hour=self.turnOffHour, minute=self.turnOffMin)
Exemple #11
0
 try:
     opts, args = getopt(sys.argv[1:], "dp")
 except GetoptError as err:
     # print help information and exit:
     print(str(err))
 for flag, value in opts:
     if flag == '-d':
         daemon = True
     if flag == '-p':
         process = True
 if daemon:
     scheduler = Scheduler(standalone=False, daemonic=True)
     scheduler.add_cron_job(agent.main,
                            month=config['scheduler']['month'],
                            day=config['scheduler']['day'],
                            hour=config['scheduler']['hour'],)
     scheduler.start()
 elif process:
     print("Initializing growpy without scheduler")
     import time
     while True:
         start = time.time()
         agent.main()
         print("Threads Time Elapsed: ", time.time() - start)
         sleep(60)
 else:
     print("Initializing Scheduler standalone")
     scheduler = Scheduler(standalone=True)
     scheduler.add_cron_job(agent.main, minute='*', day='*', hour='17')
     scheduler.print_jobs()
     scheduler.start()
Exemple #12
0
class Sched(Basemodule):

  # ################################################################################
  # initialization of module and optional load of config files
  # ################################################################################
  def __init__(self, instance_queue, global_queue):
    #
    # "sched|port|command or action"
    #

    self.logger = logging.getLogger('Hasip.sched')
    self.sched = Scheduler()
    self.items  = ConfigItemReader()
    self.mod_list = self.items.get_items_dict()     # getting module list from item file
    self.queue_identifier = 'sched'       # this is the 'module address'  
    self.instance_queue = instance_queue  # worker queue to receive jobs 
    self.global_queue = global_queue      # queue to communicate back to main thread

    self.sched.start()

    # read jobs configuration
    self.config = ConfigBaseReader('config/jobs/')
    if self.config.has_config_files(): # true
      self.logger.info('Loading config files...')
      self.jobs = self.config.get_values()
    else:
      self.logger.info('No config files present.')
      self.jobs = []

    sched_params={}
    for section in self.jobs:
      for item in self.jobs[section]:
        if self.jobs[section][item] != '':
          sched_params.update({item : self.jobs[section][item]})
        else:
          sched_params.update({item : None})
 
      
      self.sched.add_cron_job(self.send_msg,
        year   = sched_params['year'], 
        month  = sched_params['month'],
        day    = sched_params['day'],
        week   = sched_params['week'],
        day_of_week = sched_params['day_of_week'],
        hour   = sched_params['hour'],
        minute = sched_params['minute'],
        second = sched_params['second'],
        args=(sched_params['module'],sched_params['action']))

    
    self.logger.debug(self.sched.print_jobs())

  # @TODO loading jobs from persistent store and create them in the scheduler


  # ################################################################################
  # main thread of this module file which runs in background and constanly
  # checks working queue for new tasks. 
  # ################################################################################

  def worker(self):
    while True:
      instance_queue_element = self.instance_queue.get(True)

      _senderport = instance_queue_element.get("module_from_port")
      _sender	  = instance_queue_element.get("module_from")
      _port       = instance_queue_element.get("module_addr")
      _action     = instance_queue_element.get("cmd")
      _optargs    = instance_queue_element.get("opt_args")
      
      options = {
        "create"   : self.create,
        "delete"  : self.delete
      }
      options[_action](_sender, _senderport, _port, _optargs)

  # ################################################################################
  #
  # "private" methods from here on...
  #
  # ################################################################################

  def create(self, sender, senderport, port, optargs):
    # @TODO
    print "Function to put jobs in the running scheduler job queue and store them persistent"
    pass

  def delete(self, sender, senderport, port, optargs):
    # @TODO
    print "Function to delete running and persistent jobs"
    pass
  
  def send_msg(self, module, action):               # ########################################
    if module in self.mod_list.keys():              # checking existence of requested module
      rcpt = self.mod_list[module][0]               # setting receiving module from item file
      mid = self.mod_list[module][1]                # setting module id from item file
      msg = {                                       # creating queue message
        'module_from_port': 0,                      # ########################################
        'module_from':    'sched',
        'module_rcpt':    rcpt,
        'module_addr':    mid,
        'cmd':            action,
        'opt_args':       ''
      }                                                 
      self.global_queue.put(msg)
Exemple #13
0
    mC(auth['account_sid'],auth['auth_token'],targetNumber,ngrokURL)

    print "Call Queued Up"

    time.sleep(60) # Twilio default call timeout is 60 sec
    #kill = raw_input("Kill proceses? (y/n):")
    #while kill in ['n']:
    #    kill = raw_input("Kill proceses? (y/n):")

    print "Killing processes"
    ngrok.kill() # kill ngrok process
    os.system('killall -KILL Python') # kill web server and this thread

# Start the scheduler
sched = Scheduler()
sched.start()

# Convert UTC target to local time
localTarget = utc2local(datetime.strptime(targetTimeUTC,'%Y-%m-%d %H:%M:%S'))

job = sched.add_date_job(main, localTarget, [filename,targetNumber,ngrokURL])

sched.print_jobs()

print 'Current time is %s' % datetime.now()

# Keep scheduler alive until you hit Ctrl+C!
while True:
    time.sleep(1)
sched.shutdown()
Exemple #14
0
class ServiceManager(object):

    def __init__(self, irlp):

        self.irlp = irlp
        self.pidfile = None
        self.scheduler_status = False
        self.pidfile = "/tmp/nuupxe.pid"

    def __del__(self):
        pass

    def voicesynthetizer(self):
        self.voicesynthetizer = VoiceSynthetizer("google", "spanish")

    def voicesynthetizerget(self):
        return self.voicesynthetizer

    def modules_setup(self):

        # Production Modules
        self.aprstracker = AprsTracker(self.voicesynthetizer)
        self.aprstt = Aprstt(self.voicesynthetizer)
        self.clock = Clock(self.voicesynthetizer)
        self.identification = Identification(self.voicesynthetizer)
        self.meteorology = Meteorology(self.voicesynthetizer)
        self.news = News(self.voicesynthetizer)
        self.selfie = Selfie(self.voicesynthetizer)
        self.voicecommand = VoiceCommand(self.voicesynthetizer)
        self.voicemail = VoiceMail(self.voicesynthetizer)
        self.weather = Weather(self.voicesynthetizer)
        self.wolframalpha = WolframAlpha(self.voicesynthetizer)

        # Experimental Modules
        self.assistant = Assistant(self.voicesynthetizer)
        self.messages = Messages(self.voicesynthetizer)
        self.morseteacher = MorseTeacher(self.voicesynthetizer)
        self.seismology = Seismology(self.voicesynthetizer)
        self.sstv = SSTV(self.voicesynthetizer)
        self.voiceapp = VoiceApp(self.voicesynthetizer)
        self.voiceexperimental = VoiceExperimental(self.voicesynthetizer)
        self.voicemailer = VoiceMailer(self.voicesynthetizer)

    def dtmf_setup(self,dtmf):
        dtmf_codes = {
        'PS0'  : 'alive',
        'PS1'  : 'aprstracker',
        'PS2'  : 'news',
        'PS3'  : 'meteorology',
        'PS4'  : 'seismology',
        'PS5'  : 'selfie',
        'PS6'  : 'voicecommand',
        'PS7'  : 'voiceexperimental',
        'PS8'  : 'wolframalpha',
        'PS9'  : 'voicemail',
        'PS10' : 'sstv',
        'PS11' : 'voiceapp',
        }
        return dtmf_codes.get(dtmf)

    def enabled(self):
        return os.path.isfile(self.pidfile)

    def enable(self):

        pid = str(os.getpid())
        logging.info('Process Id' + pid)
        file(self.pidfile, 'w').write(pid)

    def disable(self):

        if self.enabled():
            os.unlink(self.pidfile)
        if self.scheduler_status:
            self.scheduler.shutdown()

    def bing_mode(self):

        logging.info('Mode Bing')
        self.sstv = SSTV(self.voicesynthetizer)
        self.sstv.download()

    def observer_mode(self):

        logging.info('Mode Observer')
        pub = Publisher(['text', 'voice'])

        # Radio, Twitter, Email, Telegram, Whatsapp

        radio = Subscriber('radio')
        twitter = Subscriber('twitter')
        email = Subscriber('email')
        telegram = Subscriber('telegram')

        pub.register("text", radio)
        pub.register("voice", radio)
        pub.register("text", twitter)
        pub.register("text", email)
        pub.register("text", telegram)
        pub.register("voice", telegram)

        pub.dispatch("text", "this is text")
        pub.dispatch("voice", "this is voice")

    def scheduler_mode(self):

        logging.info('Mode Scheduler')
        self.voicesynthetizer.speechit("Modo Planificador")
        self.scheduler = Scheduler(misfire_grace_time=900, coalesce=True, threadpool=ThreadPool(max_threads=1))
        self.schedule()
        self.scheduler.start()
        self.schedule_print()
        self.scheduler_status = True

        while True:
            time.sleep(5)
            if self.irlp.active():
                time.sleep(5)
                self.irlp.busy()
                self.voicesynthetizer.speechit("Se ha activado el nodo, Proyecto NuupXe dice hasta pronto!")
                break

        self.disable()

    def writing_mode(self):

        logging.info('Mode Writing')
        # self.voicesynthetizer.speechit("Modo Escritura")

        while True:
            print " Type any text to make use of Text to Speech infraestructure"
            x = raw_input(" Type 'e' for exit: ")
            if x.lower() == 'e':
                self.disable()
                break;
            else:
                self.voicesynthetizer.speechit(x)
            time.sleep(1)

    def module_mode(self, module, dtmf=None):

        logging.info('Mode Module ' + module)

        # Custom Decode Activated Modules

        if module == 'identification':
            self.identification = Identification(self.voicesynthetizer)
            self.identification.identify()
        elif module == 'date':
            self.clock = Clock(self.voicesynthetizer)
            self.clock.date()
        elif module == 'hour':
            self.clock = Clock(self.voicesynthetizer)
            self.clock.hour()
        elif module == 'temperature':
            self.weather = Weather(self.voicesynthetizer)
            self.weather.temperature()
        elif module == 'weather':
            self.weather = Weather(self.voicesynthetizer)
            self.weather.report()

        # PS Activated Modules

        elif module == 'alive':
            alive()
        elif module == 'aprstracker':
            self.aprstracker = AprsTracker(self.voicesynthetizer)
            self.aprstracker.localize()
        elif module == 'news':
            self.news = News(self.voicesynthetizer)
            self.news.getitems()
        elif module == 'meteorology':
            self.meteorology = Meteorology(self.voicesynthetizer)
            self.meteorology.conagua_clima()
        elif module == 'selfie':
            self.selfie = Selfie(self.voicesynthetizer)
            self.selfie.get()
        elif module == 'voicecommand':
            self.voicecommand = VoiceCommand(self.voicesynthetizer)
            self.voicecommand.listen()
        elif module == 'voiceapp':
            self.voiceapp = VoiceApp(self.voicesynthetizer)
            self.voiceapp.application()
        elif module == 'voicemail':
            self.voicemail = VoiceMail(self.voicesynthetizer)
            self.voicemail.run(dtmf)
        elif module == 'wolframalpha':
            self.wolframalpha = WolframAlpha(self.voicesynthetizer)
            self.wolframalpha.ask()

        # SS Activated Modules

        # Experimental Modules

        elif module == 'aprstt':
            self.aprstt = Aprstt(self.voicesynthetizer)
            self.aprstt.query(dtmf)
        elif module == 'seismology':
            self.seismology = Seismology(self.voicesynthetizer)
            self.seismology.SismologicoMX()
        elif module == 'morselearn':
            self.morseteacher = MorseTeacher(self.voicesynthetizer)
            self.morseteacher.learn()
        elif module == 'morsecontest'	:
            self.morseteacher = MorseTeacher(self.voicesynthetizer)
            self.morseteacher.contest()
	elif module == 'regulations':
            self.messages = Messages(self.voicesynthetizer)
            self.messages.readfile('learning/reglamentos.1')
	elif module == 'radioclub':
            self.messages = Messages(self.voicesynthetizer)
            self.messages.readfile('learning/arej.radioclubs')
        elif module == 'stations':
            self.messages = Messages(self.voicesynthetizer)
            self.messages.stations()
        elif module == 'sstv':
            self.sstv = SSTV(self.voicesynthetizer)
            self.sstv.decode()
        elif module == 'assistant':
            self.assistant = Assistant(self.voicesynthetizer)
            self.assistant.demo1()
        elif module == 'voicebackground':
            self.voicecommand = VoiceCommand(self.voicesynthetizer)
            self.voicecommand.background()
        elif module == 'voiceexperimental':
            self.voiceexperimental = VoiceExperimental(self.voicesynthetizer)
            self.voiceexperimental.listen()
        elif module == 'voicemailer':
            self.voicemailer = VoiceMailer(self.voicesynthetizer)
            self.voicemailer.attend(dtmf)
        else:
            self.voicesynthetizer.speechit("No hemos implementado tu comando! Lo siento!")

        self.disable()

    def voice_mode(self, text):
        logging.info('Voice Mode')
        try:
            self.voicesynthetizer.speechit(text)
        except (StopIteration, KeyboardInterrupt, SystemExit):
            pass

    def phonetic_mode(self, text):
        logging.info('Phonetic Mode')
        phonetic = Phonetic()
        try:
            text = ' '.join(phonetic.decode(text))
            self.voicesynthetizer.speechit(text)
        except (StopIteration, KeyboardInterrupt, SystemExit):
            pass

    def schedule_print(self):
        self.scheduler.print_jobs()

    def schedule(self):

        # Production Modules
        self.scheduler.add_cron_job(self.clock.date, month='*', day_of_week='*', hour='06,12,22', minute ='00', second='00')
        self.scheduler.add_cron_job(self.clock.hour, month='*', day_of_week='*', hour='*', minute ='*/15', second='00')
        self.scheduler.add_cron_job(self.identification.identify, month='*', day_of_week='*', hour='*', minute ='*/30', second='00')
        self.scheduler.add_cron_job(self.selfie.get, month='*', day_of_week='*', hour='00,04,08,14,19', minute ='00', second='00')
        self.scheduler.add_cron_job(self.weather.report, month='*', day_of_week='*', hour='*/2', minute ='00', second='00')

        # Experimental Modules
        self.scheduler.add_cron_job(self.seismology.SismologicoMX, month='*', day='*', hour='*/4', minute ='00', second='00')
        self.scheduler.add_cron_job(self.news.getitems, month='*', day='*', hour='*/4', minute ='00', second='00')
        self.scheduler.add_cron_job(self.meteorology.conagua_clima, month='*', day='*', hour='*', minute ='15', second='00')
        self.scheduler.add_cron_job(self.messages.stations, month='*', day='*', hour='*/4', minute ='00', second='00')
        self.scheduler.add_cron_job(self.sstv.decode, month='*', day='*', hour='00,04,08,14,19', minute ='00', second='00')

	# Learning Modules, AREJ
        self.scheduler.add_cron_job(self.messages.readfile,args=['learning/arej.radioclubs'],month='*',day_of_week='*',hour='7,12,17',minute ='00',second='00')

        # Learning Modules, Morse
        self.scheduler.add_cron_job(self.morseteacher.learn, month='*', day='*', hour='07,12,17', minute ='30', second='00')
        self.scheduler.add_cron_job(self.morseteacher.contest, month='*', day='*', hour='07,12,17', minute ='45', second='00')

        # Learning Modules, Reglamentos
        self.scheduler.add_cron_job(self.messages.readfile,args=['learning/reglamentos.1'], month='*', day_of_week='mon', hour='08,13,18', minute ='00', second='00')
        self.scheduler.add_cron_job(self.messages.readfile,args=['learning/reglamentos.2'], month='*', day_of_week='tue', hour='08,13,18', minute ='00', second='00')
        self.scheduler.add_cron_job(self.messages.readfile,args=['learning/reglamentos.3'], month='*', day_of_week='wed', hour='08,13,18', minute ='00', second='00')
        self.scheduler.add_cron_job(self.messages.readfile,args=['learning/reglamentos.4'], month='*', day_of_week='thu', hour='08,13,18', minute ='00', second='00')
        self.scheduler.add_cron_job(self.messages.readfile,args=['learning/reglamentos.5'], month='*', day_of_week='fri', hour='08,13,18', minute ='00', second='00')
Exemple #15
0
                board.last_notification = board.last_request
                board.save()
        if len(message) > 0:
            recipients = User.objects.filter(
                is_staff=True,
                location__building=building).values_list('email', flat=True)
            if len(recipients) > 0:
                send_mail('%s | %s' % (building.title, 'Warnung!'),
                          message,
                          '*****@*****.**',
                          recipients,
                          fail_silently=False)


cron.start()
cron.print_jobs()


@receiver(post_save, sender=User)
def create_user_profile(sender, instance, created, **kwargs):
    from api.models import UserProfile
    if created:
        profile, is_new = UserProfile.objects.get_or_create(user=instance)


def validate_pdf_file(value):
    if not value.name.endswith('.pdf'):
        raise ValidationError(u'Dieses Feld erlaubt nur PDF-Dateien.')


def user_unicode(user):
            ov.o(3) # always open valve 3 (main valve)
            time.sleep(3)
            ov.o(valve)
            time.sleep(25)



if __name__ == "__main__":
    conf = json.loads(open("/home/pi/garden/python/config.json").read())
    ig = IrrigationClient(conf)
    # Start the scheduler
    sched = Scheduler()
    sched.start()

    for ii in range(len(conf['valve'])):
        wateringHour = conf['valve'][ii]['wateringHour']
        vv =  int(conf['valve'][ii]['nr'])
        print "scheduling", wateringHour, vv
        logging.info("scheduling {0} {1}".format( wateringHour, vv))
        
        sched.add_cron_job(ig.irrigate,args=[vv], hour = wateringHour, minute=40)

    ## endless loop ##
    while True:
        with open('/home/pi/garden/python/schedlog.log','a') as f:
            sched.print_jobs(f)

        time.sleep(1800)
        

Exemple #17
0

    # camera 
    job = scheduler.add_cron_job(useCamera.takeSinglePicture, hour="*", args=['main',50])    
    # send daily picture
    job = scheduler.add_cron_job(sendPictureEmail.sendPictureEmail, hour="22",minute="20", args=['main',0])    

    # restart solar at 22:02 because there is no turbine left!
    # job = scheduler.add_cron_job(selectSolar.selectSolar, hour="22",minute="02", args=['main',0])



    sys.stdout.write('Press Ctrl+C to exit\n')
    scheduler.start()

    scheduler.print_jobs()

    while True:
        sys.stdout.write('.'); sys.stdout.flush()
	myDateString = time.strftime("%Y-%m-%d", time.gmtime())
	myTimeString = time.strftime("%H:%M:%S", time.gmtime())
	print "-%s %s-" % (myDateString, myTimeString)

	print ("hasBW=", hasBWInterrupted)
	# respond to interrupt
	#if (hasBWInterrupted == True):
	#if ((GPIO.event_detected(11) == True) or (hasBWInterrupted == True)):
	if ((GPIO.input(11) == True) or (hasBWInterrupted == True)):
		# The routine will be executed now 
		hasBWInterrupted = True;
		result = recieveInterruptFromBW.recieveInterruptFromBW("test", 1)	
def start_schedule():

#if __name__ == '__main__':
    os_user = config.OS_USER

    os_password = config.OS_APPS_PASSWD

    
    scheduler = Scheduler(daemonic = False)

    scheduler.print_jobs()

    #scheduler.remove_jobstore('file',close=True)

    #scheduler.shutdown(wait=False)

    

    scheduler.shutdown()

    #scheduler.unschedule_func(backup)

    scheduler.add_jobstore(ShelveJobStore('/tmp/db_schedule'), 'file')

    v_current_jobs = scheduler.get_jobs()

    print v_current_jobs

    if v_current_jobs:  # 如果job存在的话,先请客

     

        scheduler.unschedule_func(backup)

    

    #scheduler = Scheduler(standalone=True)
    #scheduler = Scheduler(daemon=True)
    #连接配置中心库,获取数据库备份周期等信息
    db = Connection('/tmp/mysql3306.sock',
                    config.DB_NAME,
                    config.DB_USER,
                    config.DB_PASSWD,
                    time_zone='+8:00')

    v_sql = r"""SELECT a.instance_id,b.ip,b.port,a.backup_interval_type,a.backup_start_time from mysql_ins_bak_setup a,tag b where 
        a.instance_id=b.id """

    print v_sql

    bak_server_list = db.query(v_sql)

    if bak_server_list: # 有server需要配置

        i=0

        # 把还没有开始的调度任务,置为手工结束 backup_result_type=4
        v_manual_end_sql = 'update mysql_ins_bak_log set backup_result_type=4 where backup_result_type=0'

        db.execute(v_manual_end_sql)

        for bak_server in bak_server_list:

            instance_id = bak_server['instance_id']

            from_host = bak_server['ip']

            #print from_host

            mysql_port = bak_server['port']

            backup_interval_type = bak_server['backup_interval_type']

            backup_start_time = bak_server['backup_start_time']

            str_start_date= time.strftime("%Y-%m-%d") + ' ' + backup_start_time

            print str_start_date 

            if backup_interval_type == 1: # every day

                #内存jobstore

                #scheduler.add_interval_job(backup, days=1, start_date=str_start_date, args=[from_host, mysql_port, os_user, os_password])

                #文件jobstore jobstore='file'

                scheduler.add_interval_job(backup, days=1, start_date=str_start_date, args=[from_host, mysql_port, os_user, os_password], jobstore='file')
               
                #scheduler.add_interval_job(backup, days=1, start_date='2014-07-18 18:17:01', args=[from_host, mysql_port, os_user, os_password])

            elif backup_interval_type == 2: # every week

                scheduler.add_interval_job(backup, weeks=1, start_date=str_start_date, args=[from_host, mysql_port, os_user, os_password])

            elif backup_interval_type == 3: # every hour

                scheduler.add_interval_job(backup, hours=1, start_date=str_start_date, args=[from_host, mysql_port, os_user, os_password])

            # 开始在数据库记录备份的调度任务状态 0:调度任务已启动,实际备份还没有开始

            v_sche_start_sql = """insert into mysql_ins_bak_log(instance_id,backup_result_type) 
            values(%d,0)""" % (instance_id)

            db.execute(v_sche_start_sql)

            i=i+1


    db.close()


    if bak_server_list: # 有server需要配置

        scheduler.start()

        print 'success!'

        scheduler.print_jobs()

        '''
class HMScheduler( Base ):
    '''
    The HMSceduler is used to periodically to send messages to HouseMonitor.  The commands can anything including:

    # Report status
    # Turn on and off devices.

    You control the scheduler by sending messages to the scheduler using pubsub.
    '''

    ''' The queue that is used to send messages to the rest of the system. '''
    __input_queue = None

    ''' The scheduler object '''
    scheduler = None

    ''' A dictionary of the current jobs that are running '''
    jobs = defaultdict( list )

    previous_datetime = datetime.utcnow()

    def __init__( self, queue ):
        '''
        Initialize the MHScheduler.

        # Store the queue into __input_queue
        # Associate **add_interval** with Constants.TopicNames.SchedulerAddIntervalStep
        # Associate **add_cron** with Constants.TopicNames.SchedulerAddCronStep
        # Associate **add_date** with Constants.TopicNames.SchedulerAddDateStep
        # Associate **add_one_shot with Constants.TopicNames.SchedulerAddOneShotStepSchedulerAddOneShotStep
        # Associate **delete_job** with Constants.TopicNames.SchedulerDeleteJob
        '''
        super( HMScheduler, self ).__init__()
        self.__input_queue = queue
        pub.subscribe( self.add_interval, Constants.TopicNames.SchedulerAddIntervalStep )
        pub.subscribe( self.add_cron, Constants.TopicNames.SchedulerAddCronStep )
        pub.subscribe( self.add_date, Constants.TopicNames.SchedulerAddDateStep )
        pub.subscribe( self.add_one_shot, Constants.TopicNames.SchedulerAddOneShotStep )
        pub.subscribe( self.deleteJob, Constants.TopicNames.SchedulerDeleteJob )
        pub.subscribe( self.print_jobs, Constants.TopicNames.SchedulerPrintJobs )

    @property
    def scheduler_topic_name( self ):
        ''' The topic name to which this routine subscribes.'''
        return Constants.TopicNames.SchedulerStep

    @property
    def logger_name( self ):
        ''' Set the logger level. '''
        return Constants.LogKeys.Scheduler

    def start( self ):
        '''
        Start the Scheduler.

        For more information on the parameter see:

        .. seealso:: http://packages.python.org/APScheduler/#starting-the-scheduler

        '''
        self.logger.debug( 'Scheduler starting' )
        self.scheduler = Scheduler()
#        self.logger.debug( 'Setting jobstore to HouseMonitor.db' )
#        self.scheduler.add_jobstore(ShelveJobStore('HouseMonitor.db'), 'shelve')
        self.scheduler.start()

        name = 'scheduled status check'
        device = 'status'
        port = 'scheduler'
        listeners = [Constants.TopicNames.Statistics, Constants.TopicNames.CurrentValueStep]
        scheduler_id = str( uuid.uuid4() )
        args = name, device, port, listeners, scheduler_id
        self.scheduler.add_interval_job( self.sendCommand, minutes=10, args=args )

        name = 'uptime'
        device = 'HouseMonitor'
        port = 'uptime'
        listeners = [Constants.TopicNames.UpTime, Constants.TopicNames.CurrentValueStep]
        scheduler_id = str( uuid.uuid4() )
        args = name, device, port, listeners, scheduler_id
        self.scheduler.add_interval_job( self.sendCommand, seconds=5, args=args )

        name = 'Pulse'
        device = '0x13a20040902a02'
        port = 'DIO-0'
        listeners = [ Constants.TopicNames.StatusPanel_SystemCheck, Constants.TopicNames.ZigBeeOutput]
        scheduler_id = str( uuid.uuid4() )
        args = name, device, port, listeners, scheduler_id
        self.scheduler.add_interval_job( self.sendCommand, seconds=5, args=args )

    def add_interval( self, weeks=0, days=0, hours=0, minutes=0, seconds=0, start_date=None, args=None, kwargs=None ):
        '''
        Schedule an interval at which sendCommand will be called.

        For more information on the parameter see:

            .. seealso:: http://packages.python.org/APScheduler/intervalschedule.html

        :param name: the name of the job to start. This will be used to identify the job if there is a need to delete it latter.
        :type name: str
        :param weeks: the number of weeks between calls.
        :type weeks: int
        :param days: the number of days between calls.
        :type days: int
        :param hours: the number of hours between calls.
        :type hours: int
        :param minutes: the number of minutes between calls.
        :type minutes: int
        :param seconds: the number of seconds between calls.
        :type seconds: int
        :param start_date: the time and date to start the interval.
        :type start_date: datetime
        :param args: the args to pass to sendCommand
        :param kwargs: the kwargs to pass to sendCommand
        :raises: None

        '''
        name = args[0]
        self.logger.debug( 'interval ({}) add {} {} {} {} {} {} {}'.format( name, weeks, days, hours, hours, minutes, seconds, start_date ) )
        token = self.scheduler.add_interval_job( self.sendCommand, weeks=weeks,
                        days=days, hours=hours, minutes=minutes, seconds=seconds,
                        start_date=start_date, args=args, kwargs=kwargs, name=name )
        self.jobs[name].append( token )

    def add_cron( self, year=None, month=None, day=None, week=None, day_of_week=None,
                  hour=None, minute=None, second=None, start_date=None, args=None, kwargs=None ):
        '''
        Schedule a cron command to call sendCommand.

        For more information on the parameter see:

            .. seealso:: http://packages.python.org/APScheduler/cronschedule.html

        :param name: the name of the cron job to start. This will be used to identify the job if there is a need to delete it latter.
        :type weeks: str
        :param weeks: the number of weeks between calls.
        :type weeks: int
        :param days: the number of days between calls.
        :type days: int
        :param hours: the number of hours between calls.
        :type hours: int
        :param minutes: the number of minutes between calls.
        :type minutes: int
        :param seconds: the number of seconds between calls.
        :type seconds: int
        :param start_date: the time and date to start the interval.
        :type start_date: datetime
        :param args: the args to pass to sendCommand
        :param kwargs: the kwargs to pass to sendCommand
        :raises: None

        '''
        name = args[0]
        self.logger.debug( 'set cron({}) at {}/{}/{} {}:{}:{} {} {} {}'.format( name, year, month,
                                day, hour, minute, second, week, day_of_week, start_date ) )
        token = self.scheduler.add_cron_job( self.sendCommand, year=year,
                    month=month, day=day, week=week, day_of_week=day_of_week, hour=hour,
                    minute=minute, second=second, start_date=start_date, args=args, kwargs=kwargs )
        self.jobs[name].append( token )

    def add_date( self, date, args, **kwargs ):
        '''
        Schedule a specific data and time to call sendCommand.

        For more information on the parameter see:

            .. seealso:: http://packages.python.org/APScheduler/dateschedule.html

        :param name: the name of the cron job to start. This will be used to identify the job if there is a need to delete it latter.
        :type weeks: str
        :param date: Set the time to call sendCommand
        :type date: datetime
        :param args: the arguments to call sendCommand with
        :type weeks: tuple
        :param date: the kwwargs to call sendCommand with
        :type date: dictionary

        '''
        name = args[0]

        self.logger.debug( 'add date({}) at {}'.format( name, date ) )
        token = self.scheduler.add_date_job( self.sendCommand, date=date,
                                                             args=args, kwargs=kwargs )
        self.jobs[name].append( token )

    def add_one_shot( self, delta, args=None, kwargs=None ):
        '''
        Schedule sendCommand to be called after some interval. (ie. in 5 seconds or one hour).  For more information
        on timeDelta see:

        .. seealso:: http://docs.python.org/2/library/datetime.html#timedelta-objects

        :param name: delta the time until sendCommand is called
        :type weeks: timedelta
        :param date: Set the time to call sendCommand
        :type date: datetime
        :param args: the arguments to call sendCommand with
        :type weeks: tuple
        :param date: the kwwargs to call sendCommand with
        :type date: dictionary

        '''
        name = args[0]
        now = GetDateTime()
        dt = now.datetime()
        dt = dt + delta
        token = self.scheduler.add_date_job( self.sendCommand, date=dt,
                                name=name, args=args, kwargs=kwargs )
        self.jobs[name].append( token )

    def deleteJob( self, name ):
        '''
        Delete a specified job

        :param name: the name of the job to delete.
        :type weeks: str

        '''
        item = None
        if name in self.jobs:
            for number, item in enumerate( self.jobs[name] ):
                try:
                    self.scheduler.unschedule_job( item )
                except KeyError:
                    pass
                self.logger.info( '{} "{}" removed from scheduler'.format( number, name ) )
            self.jobs[name] = []

    def shutdown( self, wait=True ):
        '''
        shutdown the scheduler

        .. seealso: http://packages.python.org/APScheduler/#shutting-down-the-scheduler

        :param wait: determines whether to wait on threads to commplete.
        :type wait: boolean

        '''

        if ( self.scheduler != None ):
            self.scheduler.shutdown( wait=wait )
            self.scheduler = None

    def print_jobs( self ):
        '''
        print tye currently scheduled jobs

        .. seealso: http://packages.python.org/APScheduler/#getting-a-list-of-scheduled-jobs

        '''
        self.scheduler.print_jobs()

    def sendCommand( self, name, device, port, listeners=[], scheduler_id=str( uuid.uuid4() ) ):
        """
        send command will send the cammand to the HouseMonitor system

        :param device: the device name.
        :type device: str
        :param port: the port name.
        :type days: str
        :param listeners: the listeners that this command will be routed to.
        :type listeners: list of strings that contains the topic name of the listeners.  Most can be found in Constants.TopicNames

        """
        try:
            data = {
                Constants.EnvelopeContents.VALUE: 1,
                Constants.EnvelopeContents.DEVICE: device,
                Constants.EnvelopeContents.PORT: port,

                Constants.EnvelopeContents.SCHEDULER_ID: scheduler_id,
                Constants.EnvelopeContents.ARRIVAL_TIME: datetime.utcnow(),
                Constants.EnvelopeContents.STEPS: copy.copy( listeners ),
                Constants.EnvelopeContents.NAME: name,
            }
            de = DataEnvelope( Constants.EnvelopeTypes.STATUS, **data )
            self.logger.debug( 'name: {} listeners: {} scheduler_id:  {}'.
                               format( name, listeners,
                                       data[Constants.EnvelopeContents.STEPS] ) )
            self.__input_queue.transmit( de, self.__input_queue.LOW_PRIORITY )
        except Exception as ex:
            self.logger.exception( "Exception in SendCommand: {}".format( ex ) )
Exemple #20
0
class TestJobExecution(object):
    def setup(self):
        self.scheduler = Scheduler(threadpool=FakeThreadPool())
        self.scheduler.add_jobstore(RAMJobStore(), 'default')

        # Make the scheduler think it's running
        self.scheduler._thread = FakeThread()

        self.logstream = StringIO()
        self.loghandler = StreamHandler(self.logstream)
        self.loghandler.setLevel(ERROR)
        scheduler.logger.addHandler(self.loghandler)

    def teardown(self):
        scheduler.logger.removeHandler(self.loghandler)
        if scheduler.datetime == FakeDateTime:
            scheduler.datetime = datetime
        FakeDateTime._now = original_now

    @raises(TypeError)
    def test_noncallable(self):
        date = datetime.now() + timedelta(days=1)
        self.scheduler.add_date_job('wontwork', date)

    def test_job_name(self):
        def my_job():
            pass

        job = self.scheduler.add_interval_job(my_job,
                                              start_date=datetime(2010, 5, 19))
        eq_(
            repr(job), '<Job (name=my_job, '
            'trigger=<IntervalTrigger (interval=datetime.timedelta(0, 1), '
            'start_date=datetime.datetime(2010, 5, 19, 0, 0))>)>')

    def test_schedule_object(self):
        # Tests that any callable object is accepted (and not just functions)
        class A:
            def __init__(self):
                self.val = 0

            def __call__(self):
                self.val += 1

        a = A()
        job = self.scheduler.add_interval_job(a, seconds=1)
        self.scheduler._process_jobs(job.next_run_time)
        self.scheduler._process_jobs(job.next_run_time)
        eq_(a.val, 2)

    def test_schedule_method(self):
        # Tests that bound methods can be scheduled (at least with RAMJobStore)
        class A:
            def __init__(self):
                self.val = 0

            def method(self):
                self.val += 1

        a = A()
        job = self.scheduler.add_interval_job(a.method, seconds=1)
        self.scheduler._process_jobs(job.next_run_time)
        self.scheduler._process_jobs(job.next_run_time)
        eq_(a.val, 2)

    def test_unschedule_job(self):
        def increment():
            vals[0] += 1

        vals = [0]
        job = self.scheduler.add_cron_job(increment)
        self.scheduler._process_jobs(job.next_run_time)
        eq_(vals[0], 1)
        self.scheduler.unschedule_job(job)
        self.scheduler._process_jobs(job.next_run_time)
        eq_(vals[0], 1)

    def test_unschedule_func(self):
        def increment():
            vals[0] += 1

        def increment2():
            vals[0] += 1

        vals = [0]
        job1 = self.scheduler.add_cron_job(increment)
        job2 = self.scheduler.add_cron_job(increment2)
        job3 = self.scheduler.add_cron_job(increment)
        eq_(self.scheduler.get_jobs(), [job1, job2, job3])

        self.scheduler.unschedule_func(increment)
        eq_(self.scheduler.get_jobs(), [job2])

    @raises(KeyError)
    def test_unschedule_func_notfound(self):
        self.scheduler.unschedule_func(copy)

    def test_job_finished(self):
        def increment():
            vals[0] += 1

        vals = [0]
        job = self.scheduler.add_interval_job(increment, max_runs=1)
        self.scheduler._process_jobs(job.next_run_time)
        eq_(vals, [1])
        assert job not in self.scheduler.get_jobs()

    def test_job_exception(self):
        def failure():
            raise DummyException

        job = self.scheduler.add_date_job(failure, datetime(9999, 9, 9))
        self.scheduler._process_jobs(job.next_run_time)
        assert 'DummyException' in self.logstream.getvalue()

    def test_misfire_grace_time(self):
        self.scheduler.misfire_grace_time = 3
        job = self.scheduler.add_interval_job(lambda: None, seconds=1)
        eq_(job.misfire_grace_time, 3)

        job = self.scheduler.add_interval_job(lambda: None,
                                              seconds=1,
                                              misfire_grace_time=2)
        eq_(job.misfire_grace_time, 2)

    def test_coalesce_on(self):
        # Makes sure that the job is only executed once when it is scheduled
        # to be executed twice in a row
        def increment():
            vals[0] += 1

        vals = [0]
        events = []
        scheduler.datetime = FakeDateTime
        self.scheduler.add_listener(events.append,
                                    EVENT_JOB_EXECUTED | EVENT_JOB_MISSED)
        job = self.scheduler.add_interval_job(increment,
                                              seconds=1,
                                              start_date=FakeDateTime.now(),
                                              coalesce=True,
                                              misfire_grace_time=2)

        # Turn the clock 14 seconds forward
        FakeDateTime._now += timedelta(seconds=2)

        self.scheduler._process_jobs(FakeDateTime.now())
        eq_(job.runs, 1)
        eq_(len(events), 1)
        eq_(events[0].code, EVENT_JOB_EXECUTED)
        eq_(vals, [1])

    def test_coalesce_off(self):
        # Makes sure that every scheduled run for the job is executed even
        # when they are in the past (but still within misfire_grace_time)
        def increment():
            vals[0] += 1

        vals = [0]
        events = []
        scheduler.datetime = FakeDateTime
        self.scheduler.add_listener(events.append,
                                    EVENT_JOB_EXECUTED | EVENT_JOB_MISSED)
        job = self.scheduler.add_interval_job(increment,
                                              seconds=1,
                                              start_date=FakeDateTime.now(),
                                              coalesce=False,
                                              misfire_grace_time=2)

        # Turn the clock 2 seconds forward
        FakeDateTime._now += timedelta(seconds=2)

        self.scheduler._process_jobs(FakeDateTime.now())
        eq_(job.runs, 3)
        eq_(len(events), 3)
        eq_(events[0].code, EVENT_JOB_EXECUTED)
        eq_(events[1].code, EVENT_JOB_EXECUTED)
        eq_(events[2].code, EVENT_JOB_EXECUTED)
        eq_(vals, [3])

    def test_interval(self):
        def increment(amount):
            vals[0] += amount
            vals[1] += 1

        vals = [0, 0]
        job = self.scheduler.add_interval_job(increment, seconds=1, args=[2])
        self.scheduler._process_jobs(job.next_run_time)
        self.scheduler._process_jobs(job.next_run_time)
        eq_(vals, [4, 2])

    def test_interval_schedule(self):
        @self.scheduler.interval_schedule(seconds=1)
        def increment():
            vals[0] += 1

        vals = [0]
        start = increment.job.next_run_time
        self.scheduler._process_jobs(start)
        self.scheduler._process_jobs(start + timedelta(seconds=1))
        eq_(vals, [2])

    def test_cron(self):
        def increment(amount):
            vals[0] += amount
            vals[1] += 1

        vals = [0, 0]
        job = self.scheduler.add_cron_job(increment, args=[3])
        start = job.next_run_time
        self.scheduler._process_jobs(start)
        eq_(vals, [3, 1])
        self.scheduler._process_jobs(start + timedelta(seconds=1))
        eq_(vals, [6, 2])
        self.scheduler._process_jobs(start + timedelta(seconds=2))
        eq_(vals, [9, 3])

    def test_cron_schedule_1(self):
        @self.scheduler.cron_schedule()
        def increment():
            vals[0] += 1

        vals = [0]
        start = increment.job.next_run_time
        self.scheduler._process_jobs(start)
        self.scheduler._process_jobs(start + timedelta(seconds=1))
        eq_(vals[0], 2)

    def test_cron_schedule_2(self):
        @self.scheduler.cron_schedule(minute='*')
        def increment():
            vals[0] += 1

        vals = [0]
        start = increment.job.next_run_time
        next_run = start + timedelta(seconds=60)
        eq_(increment.job.get_run_times(next_run), [start, next_run])
        self.scheduler._process_jobs(start)
        self.scheduler._process_jobs(next_run)
        eq_(vals[0], 2)

    def test_date(self):
        def append_val(value):
            vals.append(value)

        vals = []
        date = datetime.now() + timedelta(seconds=1)
        self.scheduler.add_date_job(append_val, date, kwargs={'value': 'test'})
        self.scheduler._process_jobs(date)
        eq_(vals, ['test'])

    def test_print_jobs(self):
        out = StringIO()
        self.scheduler.print_jobs(out)
        expected = 'Jobstore default:%s'\
                   '    No scheduled jobs%s' % (os.linesep, os.linesep)
        eq_(out.getvalue(), expected)

        self.scheduler.add_date_job(copy, datetime(2200, 5, 19))
        out = StringIO()
        self.scheduler.print_jobs(out)
        expected = 'Jobstore default:%s    '\
            'copy (trigger: date[2200-05-19 00:00:00], '\
            'next run at: 2200-05-19 00:00:00)%s' % (os.linesep, os.linesep)
        eq_(out.getvalue(), expected)

    def test_jobstore(self):
        self.scheduler.add_jobstore(RAMJobStore(), 'dummy')
        job = self.scheduler.add_date_job(lambda: None,
                                          datetime(2200, 7, 24),
                                          jobstore='dummy')
        eq_(self.scheduler.get_jobs(), [job])
        self.scheduler.remove_jobstore('dummy')
        eq_(self.scheduler.get_jobs(), [])

    @raises(KeyError)
    def test_remove_nonexistent_jobstore(self):
        self.scheduler.remove_jobstore('dummy2')

    def test_job_next_run_time(self):
        # Tests against bug #5
        def increment():
            vars[0] += 1

        vars = [0]
        scheduler.datetime = FakeDateTime
        job = self.scheduler.add_interval_job(increment,
                                              seconds=1,
                                              misfire_grace_time=3,
                                              start_date=FakeDateTime.now())
        start = job.next_run_time

        self.scheduler._process_jobs(start)
        eq_(vars, [1])

        self.scheduler._process_jobs(start)
        eq_(vars, [1])

        self.scheduler._process_jobs(start + timedelta(seconds=1))
        eq_(vars, [2])
class TestJobExecution(object):
    def setup(self):
        self.scheduler = Scheduler(threadpool=FakeThreadPool())
        self.scheduler.add_jobstore(RAMJobStore(), "default")

        # Make the scheduler think it's running
        self.scheduler._thread = FakeThread()

        self.logstream = StringIO()
        self.loghandler = StreamHandler(self.logstream)
        self.loghandler.setLevel(ERROR)
        scheduler.logger.addHandler(self.loghandler)

    def teardown(self):
        scheduler.logger.removeHandler(self.loghandler)
        if scheduler.datetime == FakeDateTime:
            scheduler.datetime = datetime
        FakeDateTime._now = original_now

    def test_job_name(self):
        def my_job():
            pass

        job = self.scheduler.add_interval_job(my_job, start_date=datetime(2010, 5, 19))
        eq_(
            repr(job),
            "<Job (name=my_job, trigger=<IntervalTrigger (interval=datetime.timedelta(0, 1), "
            "start_date=datetime.datetime(2010, 5, 19, 0, 0))>)>",
        )

    def test_schedule_object(self):
        # Tests that any callable object is accepted (and not just functions)
        class A:
            def __init__(self):
                self.val = 0

            def __call__(self):
                self.val += 1

        a = A()
        job = self.scheduler.add_interval_job(a, seconds=1)
        self.scheduler._process_jobs(job.next_run_time)
        self.scheduler._process_jobs(job.next_run_time)
        eq_(a.val, 2)

    def test_schedule_method(self):
        # Tests that bound methods can be scheduled (at least with RAMJobStore)
        class A:
            def __init__(self):
                self.val = 0

            def method(self):
                self.val += 1

        a = A()
        job = self.scheduler.add_interval_job(a.method, seconds=1)
        self.scheduler._process_jobs(job.next_run_time)
        self.scheduler._process_jobs(job.next_run_time)
        eq_(a.val, 2)

    def test_unschedule_job(self):
        def increment():
            vals[0] += 1

        vals = [0]
        job = self.scheduler.add_cron_job(increment)
        self.scheduler._process_jobs(job.next_run_time)
        eq_(vals[0], 1)
        self.scheduler.unschedule_job(job)
        self.scheduler._process_jobs(job.next_run_time)
        eq_(vals[0], 1)

    def test_unschedule_func(self):
        def increment():
            vals[0] += 1

        def increment2():
            vals[0] += 1

        vals = [0]
        job1 = self.scheduler.add_cron_job(increment)
        job2 = self.scheduler.add_cron_job(increment2)
        job3 = self.scheduler.add_cron_job(increment)
        eq_(self.scheduler.get_jobs(), [job1, job2, job3])

        self.scheduler.unschedule_func(increment)
        eq_(self.scheduler.get_jobs(), [job2])

    @raises(KeyError)
    def test_unschedule_func_notfound(self):
        self.scheduler.unschedule_func(copy)

    def test_job_finished(self):
        def increment():
            vals[0] += 1

        vals = [0]
        job = self.scheduler.add_interval_job(increment, max_runs=1)
        self.scheduler._process_jobs(job.next_run_time)
        eq_(vals, [1])
        assert job not in self.scheduler.get_jobs()

    def test_job_exception(self):
        def failure():
            raise DummyException

        job = self.scheduler.add_date_job(failure, datetime(9999, 9, 9))
        self.scheduler._process_jobs(job.next_run_time)
        assert "DummyException" in self.logstream.getvalue()

    def test_misfire_grace_time(self):
        self.scheduler.misfire_grace_time = 3
        job = self.scheduler.add_interval_job(lambda: None, seconds=1)
        eq_(job.misfire_grace_time, 3)

        job = self.scheduler.add_interval_job(lambda: None, seconds=1, misfire_grace_time=2)
        eq_(job.misfire_grace_time, 2)

    def test_coalesce_on(self):
        # Makes sure that the job is only executed once when it is scheduled
        # to be executed twice in a row
        def increment():
            vals[0] += 1

        vals = [0]
        events = []
        scheduler.datetime = FakeDateTime
        self.scheduler.add_listener(events.append, EVENT_JOB_EXECUTED | EVENT_JOB_MISSED)
        job = self.scheduler.add_interval_job(
            increment, seconds=1, start_date=FakeDateTime.now(), coalesce=True, misfire_grace_time=2
        )

        # Turn the clock 14 seconds forward
        FakeDateTime._now += timedelta(seconds=2)

        self.scheduler._process_jobs(FakeDateTime.now())
        eq_(job.runs, 1)
        eq_(len(events), 1)
        eq_(events[0].code, EVENT_JOB_EXECUTED)
        eq_(vals, [1])

    def test_coalesce_off(self):
        # Makes sure that every scheduled run for the job is executed even
        # when they are in the past (but still within misfire_grace_time)
        def increment():
            vals[0] += 1

        vals = [0]
        events = []
        scheduler.datetime = FakeDateTime
        self.scheduler.add_listener(events.append, EVENT_JOB_EXECUTED | EVENT_JOB_MISSED)
        job = self.scheduler.add_interval_job(
            increment, seconds=1, start_date=FakeDateTime.now(), coalesce=False, misfire_grace_time=2
        )

        # Turn the clock 2 seconds forward
        FakeDateTime._now += timedelta(seconds=2)

        self.scheduler._process_jobs(FakeDateTime.now())
        eq_(job.runs, 3)
        eq_(len(events), 3)
        eq_(events[0].code, EVENT_JOB_EXECUTED)
        eq_(events[1].code, EVENT_JOB_EXECUTED)
        eq_(events[2].code, EVENT_JOB_EXECUTED)
        eq_(vals, [3])

    def test_interval(self):
        def increment(amount):
            vals[0] += amount
            vals[1] += 1

        vals = [0, 0]
        job = self.scheduler.add_interval_job(increment, seconds=1, args=[2])
        self.scheduler._process_jobs(job.next_run_time)
        self.scheduler._process_jobs(job.next_run_time)
        eq_(vals, [4, 2])

    def test_interval_schedule(self):
        @self.scheduler.interval_schedule(seconds=1)
        def increment():
            vals[0] += 1

        vals = [0]
        start = increment.job.next_run_time
        self.scheduler._process_jobs(start)
        self.scheduler._process_jobs(start + timedelta(seconds=1))
        eq_(vals, [2])

    def test_cron(self):
        def increment(amount):
            vals[0] += amount
            vals[1] += 1

        vals = [0, 0]
        job = self.scheduler.add_cron_job(increment, args=[3])
        start = job.next_run_time
        self.scheduler._process_jobs(start)
        eq_(vals, [3, 1])
        self.scheduler._process_jobs(start + timedelta(seconds=1))
        eq_(vals, [6, 2])
        self.scheduler._process_jobs(start + timedelta(seconds=2))
        eq_(vals, [9, 3])

    def test_cron_schedule_1(self):
        @self.scheduler.cron_schedule()
        def increment():
            vals[0] += 1

        vals = [0]
        start = increment.job.next_run_time
        self.scheduler._process_jobs(start)
        self.scheduler._process_jobs(start + timedelta(seconds=1))
        eq_(vals[0], 2)

    def test_cron_schedule_2(self):
        @self.scheduler.cron_schedule(minute="*")
        def increment():
            vals[0] += 1

        vals = [0]
        start = increment.job.next_run_time
        next_run = start + timedelta(seconds=60)
        eq_(increment.job.get_run_times(next_run), [start, next_run])
        self.scheduler._process_jobs(start)
        self.scheduler._process_jobs(next_run)
        eq_(vals[0], 2)

    def test_date(self):
        def append_val(value):
            vals.append(value)

        vals = []
        date = datetime.now() + timedelta(seconds=1)
        self.scheduler.add_date_job(append_val, date, kwargs={"value": "test"})
        self.scheduler._process_jobs(date)
        eq_(vals, ["test"])

    def test_print_jobs(self):
        out = StringIO()
        self.scheduler.print_jobs(out)
        expected = "Jobstore default:%s" "    No scheduled jobs%s" % (os.linesep, os.linesep)
        eq_(out.getvalue(), expected)

        self.scheduler.add_date_job(copy, datetime(2200, 5, 19))
        out = StringIO()
        self.scheduler.print_jobs(out)
        expected = (
            "Jobstore default:%s    "
            "copy (trigger: date[2200-05-19 00:00:00], "
            "next run at: 2200-05-19 00:00:00)%s" % (os.linesep, os.linesep)
        )
        eq_(out.getvalue(), expected)

    def test_jobstore(self):
        self.scheduler.add_jobstore(RAMJobStore(), "dummy")
        job = self.scheduler.add_date_job(lambda: None, datetime(2200, 7, 24), jobstore="dummy")
        eq_(self.scheduler.get_jobs(), [job])
        self.scheduler.remove_jobstore("dummy")
        eq_(self.scheduler.get_jobs(), [])

    @raises(KeyError)
    def test_remove_nonexistent_jobstore(self):
        self.scheduler.remove_jobstore("dummy2")

    def test_job_next_run_time(self):
        # Tests against bug #5
        def increment():
            vars[0] += 1

        vars = [0]
        scheduler.datetime = FakeDateTime
        job = self.scheduler.add_interval_job(increment, seconds=1, misfire_grace_time=3, start_date=FakeDateTime.now())
        start = job.next_run_time

        self.scheduler._process_jobs(start)
        eq_(vars, [1])

        self.scheduler._process_jobs(start)
        eq_(vars, [1])

        self.scheduler._process_jobs(start + timedelta(seconds=1))
        eq_(vars, [2])
Exemple #22
0
sched = Scheduler()
signal.signal(signal.SIGINT, shutdown_handler)
signal.signal(signal.SIGTERM, shutdown_handler)


def event_handler(event):
    if event.exception:
        logger.error("SCHEDULER FAIL:\n%s\n%s\n%s" %
                     (event.job, event.exception, traceback.format_exc()))
    else:
        logger.info("SUCCESS: %s" % event.job)


sched.add_listener(
    event_handler, events.EVENT_JOB_EXECUTED | events.EVENT_JOB_ERROR
    | events.EVENT_JOB_MISSED)

# ----------------------------------------------------------------------------
# Tasks

#sched.add_cron_job(send_digest, hour=11)

# ----------------------------------------------------------------------------

if __name__ == '__main__':
    sched.start()
    sched.print_jobs()
    while True:
        time.sleep(10)
        db.remove()
# Start the scheduler
sched = Scheduler()
sched.add_jobstore(
    SQLAlchemyJobStore(url=JOBS_DATABASE, tablename='apscheduler_jobs'),
    'default')
sched.start()


def print_reservation_id(reservation_id):
    print "====> Reservation id is " + str(reservation_id)


if __name__ == '__main__':

    print "====> Printing jobs..."
    print sched.print_jobs()

    now = datetime.datetime.now()
    start_time = now + datetime.timedelta(seconds=3)
    later = now + datetime.timedelta(seconds=10)

    print "====> now is " + str(now)
    print "====> start_time is " + str(start_time)
    print "====> later is " + str(later)

    reservation_id = 1

    job_name = "print_reservation_id_" + str(reservation_id)

    print "====> adding start_time job"