Source code for eon.state


""" The state module. """

import os
import shutil
import logging
logger = logging.getLogger('state')
from configparser import ConfigParser
import tarfile

from eon import fileio as io

[docs] class State: """ The state super class. """ def __init__(self, statepath, statenumber, statelist, previous_state_num = -1, reactant_path = None): """ Creates a new state, with lazily loaded data. """ # The parent statelist. self.statelist = statelist # The path to and number of this state. self.path = statepath self.number = statenumber # Lazily loaded data. Should use the get/set methods for these. self.procs = None self.proc_repeat_count = None self.procdata_path = os.path.join(self.path, "procdata") self.reactant_path = os.path.join(self.path, "reactant.con") self.proctable_path = os.path.join(self.path, "processtable") self.search_result_path = os.path.join(self.path, "search_results.txt") self.tar_path = os.path.join(self.path, "procdata.tar") self.info = io.ini(os.path.join(self.path, "info")) # If this state does not exist on disk, create it. if not os.path.isdir(self.path): if reactant_path is None: raise IOError("State needs a reactant_path when it is being instantiated to disk") os.mkdir(self.path) os.mkdir(self.procdata_path) shutil.copy(reactant_path, self.reactant_path) self.info.set("MetaData", "previous state", previous_state_num) f = open(self.proctable_path, 'w') f.write(self.processtable_header) f.close() f = open(self.search_result_path, 'w') f.write(self.search_result_header) f.close() def __repr__(self): return "State #%i" % self.number def __eq__(self, other): return isinstance(other, State) and self.number == other.number def __hash__(self): return hash(self.number)
[docs] def add_process(self, result): if 'stdout.dat' in result: id = self.get_num_procs() open(self.proc_stdout_path(id), 'w').writelines(result['stdout.dat'].getvalue())
[docs] def get_energy(self): return self.info.get("MetaData", "reactant energy", None)
[docs] def set_energy(self, e): self.info.set("MetaData", "reactant energy", e)
[docs] def get_reactant(self): """ Loads the reactant.con into a point and returns it. """ return io.loadcon(self.reactant_path)
# Utility functions for loading process .con and mode files.
[docs] def get_process_reactant(self, id): return io.loadcon(self.proc_reactant_path(id))
[docs] def get_process_product(self, id): return io.loadcon(self.proc_product_path(id))
# Utility functions for compiling procdata paths, whether the files exist or not.
[docs] def proc_reactant_path(self, id): return os.path.join(self.procdata_path, "reactant_%d.con" % id)
[docs] def proc_product_path(self, id): return os.path.join(self.procdata_path, "product_%d.con" % id)
[docs] def proc_results_path(self, id): return os.path.join(self.procdata_path, "results_%d.dat" % id)
[docs] def proc_stdout_path(self, id): return os.path.join(self.procdata_path, "stdout_%d.dat" % id)
[docs] def tar_procdata(self): if not self.procdata_tarred: tar = tarfile.TarFile(self.tar_path, 'w') for i in os.listdir(self.procdata_path): tar.add(i) os.unlink(i) tar.close() else: logger.warning("Attempted to tar an already tarred procdata") self.procdata_tarred = True
[docs] def get_process(self, id): self.load_process_table() return self.procs[id]
[docs] def get_process_ids(self): """ Returns the list of ids in the rate table. """ return [b[0] for b in self.get_ratetable()]
[docs] def get_previous_state(self): return self.info.get("MetaData", "previous state", -1)
[docs] def get_num_procs(self): """ Loads the process table if it is not already loaded and returns the length of it """ self.load_process_table() return len(self.procs)
[docs] def get_process_table(self): self.load_process_table() return self.procs