def hold_message(self, destination, data, headers): """ Calls the reduction script. """ logger.debug("holding thread") message = Message() message.populate(data) self.update_child_process_list() if not self.should_proceed(message): # wait while the run shouldn't proceed # pylint: disable=maybe-no-member reactor.callLater(10, self.hold_message, # pragma: no cover destination, data, headers) return if self.should_cancel(message): self.cancel_run(message) # pylint: disable=maybe-no-member return if not os.path.isfile(MISC['post_process_directory']): logger.warning("Could not find autoreduction post processing file " "- please contact a system administrator") python_path = sys.executable logger.info("Calling: %s %s %s %s", python_path, MISC['post_process_directory'], destination, message.serialize(limit_reduction_script=True)) proc = subprocess.Popen([python_path, MISC['post_process_directory'], destination, message.serialize()]) # PPA expects json data self.add_process(proc, message)
def _remove_with_wait(self, remove_folder, full_path): """ Removes a folder or file and waits for it to be removed. """ file_deleted = False for sleep in [0, 0.1, 0.2, 0.5, 1, 2, 5, 10, 20]: try: if remove_folder: os.removedirs(full_path) else: if os.path.isfile(full_path): os.remove(full_path) file_deleted = True elif sleep == 20: logger.warning( "Unable to delete file %s, file could not be found", full_path) elif file_deleted is True: logger.debug("file %s has been successfully deleted", full_path) break except OSError as exp: if exp.errno == errno.ENOENT: # File has been deleted break time.sleep(sleep) else: self.log_and_message("Failed to delete %s" % full_path)
def __init__(self, message, client): logger.debug("Message data: %s", message.serialize(limit_reduction_script=True)) self.read_write_map = {"R": "read", "W": "write"} self.message = message self.client = client self.reduction_log_stream = io.StringIO() self.admin_log_stream = io.StringIO() try: self.data_file = windows_to_linux_path(self.validate_input('data'), MISC["temp_root_directory"]) self.facility = self.validate_input('facility') self.instrument = self.validate_input('instrument').upper() self.proposal = str(int( self.validate_input('rb_number'))) # Integer-string validation self.run_number = str(int(self.validate_input('run_number'))) self.reduction_script = self.validate_input('reduction_script') self.reduction_arguments = self.validate_input( 'reduction_arguments') except ValueError: logger.info('JSON data error', exc_info=True) raise
def validate_input(self, attribute): """ Validates the input message :param attribute: attribute to validate :return: The value of the key or raise an exception if none """ attribute_dict = self.message.__dict__ if attribute in attribute_dict and attribute_dict[ attribute] is not None: value = attribute_dict[attribute] logger.debug("%s: %s", attribute, str(value)[:50]) return value raise ValueError('%s is missing' % attribute)
def send_reduction_message(self, message, amq_message): """Send/Update AMQ reduction message :param message: (str) amq reduction status :param amq_message: (str) reduction status path """ try: logger.debug("Calling: %s\n%s", amq_message, self.message.serialize(limit_reduction_script=True)) self.client.send(amq_message, self.message) logger.info("Reduction: %s", message) except AttributeError: logger.debug("Failed to find send reduction message: %s", amq_message)
def on_message(self, headers, data): """ handles message consuming. It will consume a message. """ destination = headers['destination'] logger.debug("Received frame destination: %s", destination) logger.debug("Received frame priority: %s", headers["priority"]) self.update_child_process_list() message = Message() message.populate(data) if message.cancel: self.add_cancel(message) return self.hold_message(destination, data, headers)