def stage_wrapper(self, start_key, begin_log_msg='', fin_log_msg='', torsion_options=None): """ Firstly, check if the stage start_key is in self.order; this tells you if the stage should be called or not. If it isn't in self.order: - Do nothing If it is: - Unpickle the ligand object at the start_key stage - Write to the log that something's about to be done (if specified) - Make (if not restarting) and / or move into the working directory for that stage - Do the thing - Move back out of the working directory for that stage - Write to the log that something's been done (if specified) - Pickle the ligand object again with the next_key marker as its stage """ mol = unpickle()[start_key] # Set the state for logging any exceptions should they arise mol.state = start_key # if we have a torsion options dictionary pass it to the molecule if torsion_options is not None: mol = self.store_torsions(mol, torsion_options) skipping = False if self.order[start_key] == self.skip: printf(f'Skipping stage: {start_key}') append_to_log(f'skipping stage: {start_key}') skipping = True else: if begin_log_msg: printf(f'{begin_log_msg}...', end=' ') home = os.getcwd() folder_name = f'{self.immutable_order.index(start_key) + 1}_{start_key}' # Make sure you don't get an error if restarting try: os.mkdir(folder_name) except FileExistsError: pass finally: os.chdir(folder_name) self.order[start_key](mol) self.order.pop(start_key, None) os.chdir(home) # Begin looping through self.order, but return after the first iteration. for key in self.order: next_key = key if fin_log_msg and not skipping: printf(fin_log_msg) mol.pickle(state=next_key) return next_key
def __init__(self): # First make sure the config folder has been made missing for conda and pip home = str(Path.home()) config_folder = f'{home}/QUBEKit_configs/' if not os.path.exists(config_folder): os.makedirs(config_folder) print(f'Making config folder at: {home}') self.args = self.parse_commands() # If it's a bulk run, handle it separately # TODO Add .sdf as possible bulk_run, not just .csv if self.args.bulk_run: self.handle_bulk() if self.args.restart is not None: # Find the pickled checkpoint file and load it as the molecule try: self.molecule = unpickle()[self.args.restart] except FileNotFoundError: raise FileNotFoundError('No checkpoint file found!') else: if self.args.smiles: self.file = RDKit().smiles_to_pdb(*self.args.smiles) else: self.file = self.args.input # Initialise molecule self.molecule = Ligand(self.file) # Find which config file is being used self.molecule.config = self.args.config_file # Handle configs which are in a file file_configs = Configure.load_config(self.molecule.config) for name, val in file_configs.items(): setattr(self.molecule, name, val) # Although these may be None always, they need to be explicitly set anyway. setattr(self.molecule, 'restart', None) setattr(self.molecule, 'end', None) setattr(self.molecule, 'skip', None) # Handle configs which are changed by terminal commands for name, val in vars(self.args).items(): if val is not None: setattr(self.molecule, name, val) # If restarting put the molecule back into the checkpoint file with the new configs if self.args.restart is not None: self.molecule.pickle(state=self.args.restart) # Now that all configs are stored correctly: execute. Execute(self.molecule)
def setUp(self): """ Set up the seminario test case by loading a pickled ligand that contains the hessian already :return: None """ self.home = os.getcwd() self.test_folder = os.path.join(os.path.dirname(__file__), 'files') # Make temp folder and move the pickle file in with tempfile.TemporaryDirectory() as temp: os.chdir(temp) copy(os.path.join(self.test_folder, '.QUBEKit_states'), '.QUBEKit_states') self.molecules = unpickle() self.benzene_hessian, self.benzene_mod_sem = self.molecules['hessian'], self.molecules['mod_sem'] self.benzene_mod_sem_vib_1 = self.molecules['mod_sem_vib_1'] self.benzonitrile_hessian, self.benzonitrile_mod_sem = self.molecules['benzonitrile_hessian'], self.molecules['benzonitrile_mod_sem']
def wrapper(*args, **kwargs): logger = logger_format() # Run as normal try: return func(*args, **kwargs) except KeyboardInterrupt: raise # Any other exception that occurs is logged except: logger.exception(f'An exception occurred with: {func.__qualname__}') print(f'An exception occurred with: {func.__qualname__}. View the log file for details.') log_file = f'{"" if "QUBEKit_log.txt" in os.listdir(".") else "../"}QUBEKit_log.txt' with open(log_file, 'r') as log: # Run through log file backwards to find proper pickle point lines = list(reversed(log.readlines())) mol_name, pickle_point = False, False for pos, line in enumerate(lines): if 'Analysing:' in line: mol_name = line.split()[1] elif ' stage_wrapper' in line: # The stage_wrapper always wraps the method which is the name of the pickle point. pickle_point = lines[pos - 2].split()[-1] if not (mol_name and pickle_point): raise EOFError('Cannot locate molecule name or completion stage in log file.') mol = unpickle()[pickle_point] pretty_print(mol, to_file=True, finished=False) # Re-raises the exception raise