def run_mopac(s, exe='mopac', template='mopac_template.txt', mult=None, overwrite=False): """ Runs mopac, returns a string specifying the status of the calculation. mopac inp inp.out Mopac always writes the log file into a file with .out extension """ mol = ob.get_mol(s, make3D=True) if mult is None: mult = ob.get_multiplicity(mol) tmp = io.read_file(template) inptext = get_input(mol, tmp, mult) prefix = ob.get_smiles_filename(s) inpfile = prefix + '.mop' outfile = prefix + '.out' command = [exe, inpfile] if io.check_file(outfile, timeout=1): if overwrite: msg = 'Overwriting previous calculation "{0}"\n'.format(io.get_path(outfile)) run = True else: msg = 'Skipping calculation, found "{0}"\n'.format(io.get_path(outfile)) run = False else: run = True if run: if not io.check_file(inpfile, timeout=1) or overwrite: io.write_file(inptext, inpfile) if io.check_file(inpfile, timeout=1): msg = io.execute(command) if io.check_file(outfile, timeout=1): msg += 'Output file: "{0}"\n'.format(io.get_path(outfile)) else: msg = 'Failed, cannot find input file "{0}"\n'.format(io.get_path(inpfile)) return msg
def run_molpro(s, exe='molpro', template='molpro_template.txt', mult=None, overwrite=False): """ Runs molpro, returns a string specifying the status of the calculation. TODO """ mol = ob.get_mol(s, make3D=True) if mult is None: mult = ob.get_multiplicity(mol) tmp = io.read_file(template) inptext = get_input(mol, tmp, mult) prefix = ob.get_smiles_filename(s) inpfile = prefix + '.nw' outfile = prefix + '_nwchem.log' command = [exe, inpfile] if io.check_file(outfile, timeout=1): if overwrite: msg = 'Overwriting previous calculation "{0}"\n'.format(io.get_path(outfile)) run = True else: msg = 'Skipping calculation, found "{0}"\n'.format(io.get_path(outfile)) run = False else: run = True if run: if not io.check_file(inpfile, timeout=1) or overwrite: io.write_file(inptext, inpfile) if io.check_file(inpfile, timeout=1): msg = io.execute(command,stdoutfile=outfile,merge=True) if io.check_file(outfile, timeout=1): msg += ' Output file: "{0}"\n'.format(io.get_path(outfile)) else: msg = 'Failed, cannot find input file "{0}"\n'.format(io.get_path(inpfile)) return msg
def run_gaussian(s, exe='g09', template='gaussian_template.txt', mult=None, overwrite=False): """ Runs gaussian calculation """ mol = ob.get_mol(s, make3D=True) if mult is None: mult = ob.get_multiplicity(mol) tmp = io.read_file(template) inptext = get_gaussian_input(mol, tmp, mult) prefix = ob.get_smiles_filename(s) inpfile = prefix + '.g09' outfile = prefix + '_gaussian.log' command = [exe, inpfile, outfile] if io.check_file(outfile, timeout=1): if overwrite: msg = 'Overwriting previous calculation "{0}"\n'.format(io.get_path(outfile)) run = True else: msg = 'Skipping calculation, found "{0}"\n'.format(io.get_path(outfile)) run = False else: run = True if run: if not io.check_file(inpfile, timeout=1) or overwrite: io.write_file(inptext, inpfile) if io.check_file(inpfile, timeout=1): msg = io.execute(command) if io.check_file(outfile, timeout=1): msg += ' Output file: "{0}"\n'.format(io.get_path(outfile)) else: msg = 'Failed, cannot find input file "{0}"\n'.format(io.get_path(inpfile)) return msg
def parse_qclog_cclib(qclog,anharmonic=False): xyz = None freqs = None zpe = None deltaH = None xmat = None afreqs = None msg ='' if io.check_file(qclog, 1): s = io.read_file(qclog, aslines=False) else: msg = 'File not found: "{0}"\n'.format(io.get_path(qclog)) return msg,xyz,freqs,zpe,deltaH,afreqs,xmat if check_output(s): if cclib: ccdata = parse_cclib(qclog) xyz = ccdata.writexyz() try: freqs = ccdata.vibfreqs freqs = get_listofstrings(freqs) nfreq = len(freqs) except AttributeError: pass try: deltaH = ccdata.enthalpy except AttributeError: pass if anharmonic: xmat = ccdata.vibanharms afreqs = get_gaussian_fundamentals(s, nfreq)[:,1] afreqs = get_listofstrings(afreqs) else: msg = 'Failed job: "{0}"\n'.format(io.get_path(qclog)) return msg,xyz,freqs,zpe,deltaH,afreqs,xmat
def run(s, template, parameters, mult=None): """ Runs nwchem, returns a string specifying the status of the calculation. nwchem inp.nw > nw.log NWChem writes output and error to stdout. Generates .db (a binary file to restart a job) and .movecs (scf wavefunction) files in the run directory. Generates many junk files in a scratch directory. If scratch is not specified, these junk files are placed in the run directory. """ package = parameters['qcpackage'] overwrite = parameters['overwrite'] mol = ob.get_mol(s, make3D=True) msg = '' if mult is None: mult = ob.get_multiplicity(mol) else: ob.set_mult(mol, mult) tmp = io.read_file(template) inptext = get_input(mol, tmp) prefix = ob.get_smiles_filename(s) + '_' + package inpfile = prefix + '.inp' outfile = prefix + '.out' if io.check_file(outfile, timeout=1): if overwrite: msg = 'Overwriting previous calculation "{0}"\n'.format(io.get_path(outfile)) run = True else: msg = 'Skipping calculation, found "{0}"\n'.format(io.get_path(outfile)) run = False else: run = True if run: if not io.check_file(inpfile, timeout=1) or overwrite: io.write_file(inptext, inpfile) if io.check_file(inpfile, timeout=1): if package == 'extrapolation': run_extrapolation(s, parameters) elif package == 'nwchem': command = [parameters['qcexe'], inpfile] msg += io.execute(command,stdoutfile=outfile,merge=True) else: command = [parameters['qcexe'], inpfile, outfile] msg = io.execute(command) if io.check_file(outfile, timeout=1): msg += ' Output file: "{0}"\n'.format(io.get_path(outfile)) else: msg += 'Failed, cannot find input file "{0}"\n'.format(io.get_path(inpfile)) return msg
def parse_qclog_as_dict(qclog,qccode='gaussian',anharmonic=False): xyz = None freqs = None zpe = None deltaH = None xmat = None afreqs = None basis = None method = None msg ='' if io.check_file(qclog, 1): s = io.read_file(qclog, aslines=False) else: msg = 'File not found: "{0}"\n'.format(io.get_path(qclog)) return msg,xyz,freqs,zpe,deltaH,afreqs,xmat lines = s.splitlines() if check_output(s): try: if qccode == 'gaussian': mol = ob.get_gaussian_mol(qclog) zpe = mol.energy if cclib: ccdata = parse_cclib(qclog) xyz = ccdata.writexyz() freqs = ccdata.vibfreqs freqs = get_listofstrings(freqs) nfreq = len(freqs) deltaH = ccdata.enthalpy if anharmonic: xmat = ccdata.vibanharms afreqs = get_gaussian_fundamentals(s, nfreq)[:,1] afreqs = get_listofstrings(afreqs) elif qccode == 'mopac': xyz = get_mopac_xyz(lines) freqs = get_mopac_freq(lines) freqs = get_listofstrings(freqs) zpe = get_mopac_zpe(lines) deltaH = get_mopac_deltaH(lines) except: msg = 'Parsing failed for "{0}"\n'.format(io.get_path(qclog)) return msg,xyz,freqs,zpe,deltaH,afreqs,xmat else: msg = 'Failed job: "{0}"\n'.format(io.get_path(qclog)) return msg,xyz,freqs,zpe,deltaH,afreqs,xmat
def run_nwchem(s, exe='nwchem', template='nwchem_template.txt', mult=None, overwrite=False): """ Runs nwchem, returns a string specifying the status of the calculation. nwchem inp.nw > nw.log NWChem writes output and error to stdout. Generates .db (a binary file to restart a job) and .movecs (scf wavefunction) files in the run directory. Generates many junk files in a scratch directory. If scratch is not specified, these junk files are placed in the run directory. """ mol = ob.get_mol(s, make3D=True) if mult is None: mult = ob.get_multiplicity(mol) tmp = io.read_file(template) inptext = get_input(mol, tmp) prefix = ob.get_smiles_filename(s) inpfile = prefix + '.nw' outfile = prefix + '_nwchem.log' command = [exe, inpfile] if io.check_file(outfile, timeout=1): if overwrite: msg = 'Overwriting previous calculation "{0}"\n'.format(io.get_path(outfile)) run = True else: msg = 'Skipping calculation, found "{0}"\n'.format(io.get_path(outfile)) run = False else: run = True if run: if not io.check_file(inpfile, timeout=1) or overwrite: io.write_file(inptext, inpfile) if io.check_file(inpfile, timeout=1): msg = io.execute(command,stdoutfile=outfile,merge=True) if io.check_file(outfile, timeout=1): msg += ' Output file: "{0}"\n'.format(io.get_path(outfile)) else: msg = 'Failed, cannot find input file "{0}"\n'.format(io.get_path(inpfile)) return msg
def execute_gaussian(inp, exe='g09'): """ Runs gaussian calculation. """ from subprocess import Popen, PIPE process = Popen([exe, inp], stdout=PIPE, stderr=PIPE) out, err = process.communicate() if err is None or err == '': msg = 'Run {0} {1}: Success.'.format(exe, inp) else: errstr = """ERROR in "{0}"\n STDOUT:\n{1}\n STDERR:\n{2}""".format(inp, out, err) errfile = inp + '.err' io.write_file(errstr, errfile) msg = 'Run {0} {1}: Failed, see "{2}"'.format(exe, inp, io.get_path(errfile)) return msg
def execute(inp, exe,outputfile=None): """ Executes a calculation for a given input file inp and executable exe. """ from subprocess import Popen, PIPE process = Popen([exe, inp], stdout=PIPE, stderr=PIPE) out, err = process.communicate() if outputfile: io.write_file(out,outputfile) if err is None or err == '': msg = 'Run {0} {1}: Success.\n'.format(exe, inp) else: errstr = """ERROR in "{0}"\n STDOUT:\n{1}\n STDERR:\n{2}""".format(inp, out, err) errfile = inp + '.err' io.write_file(errstr, errfile) msg = 'Run {0} {1}: Failed, see "{2}"\n'.format(exe, inp, io.get_path(errfile)) return msg
def run(s): """ A driver function to run quantum chemistry and thermochemistry calculations based on command line options: --qcmethod --qcpackage """ global parameters runqc = parameters['runqc'] parseqc = parameters['parseqc'] runthermo = parameters['runthermo'] runanharmonic = parameters['anharmonic'] msg = "***************************************\n" msg += "{0}\n".format(s) mult = ob.get_mult(s) mol = ob.get_mol(s) smilesname = ob.get_smiles_filename(s) smilesdir = ob.get_smiles_path(mol, mult, method='', basis='', geopath='') qcdirectory = io.join_path(*[smilesdir, parameters['qcdirectory']]) qctemplate = io.get_path(parameters['qctemplate']) qcpackage = parameters['qcpackage'] qcscript = io.get_path(parameters['qcscript']) qclog = smilesname + '_' + qcpackage + '.out' xyzpath = parameters['xyzpath'] xyzfile = None if xyzpath: if io.check_file(xyzpath): xyzfile = xyzpath elif io.check_file(io.join_path(*(smilesdir, xyzpath))): xyzfile = io.join_path(*(smilesdir, xyzpath)) elif io.check_dir(xyzpath): try: xyzfile = next(io.find_files(xyzpath, '*.xyz')) except StopIteration: msg += "xyz file not found in {0}".format(xyzpath) elif io.check_dir(io.join_path(*(smilesdir, xyzpath))): xyzpath = io.join_path(*(smilesdir, xyzpath)) try: xyzfile = next(io.find_files(xyzpath, '*.xyz')) except StopIteration: msg += "xyz file not found in {0}".format(xyzpath) else: msg += "xyz path not found {0}".format(xyzpath) return msg if xyzfile: msg += "Using xyz file in '{0}'\n".format(xyzfile) xyz = io.read_file(xyzfile) coords = ob.get_coordinates_array(xyz) mol = ob.set_xyz(mol, coords) print(msg) msg = '' io.mkdir(qcdirectory) cwd = io.pwd() if io.check_dir(qcdirectory, 1): io.cd(qcdirectory) msg += "cd '{0}'\n".format(qcdirectory) else: msg += ('I/O error, {0} directory not found.\n'.format(qcdirectory)) return -1 print(msg) msg = '' available_packages = [ 'nwchem', 'molpro', 'mopac', 'gaussian', 'extrapolation' ] if runqc: if qcpackage in available_packages: print('Running {0}'.format(qcpackage)) msg += qc.run(s, qctemplate, parameters, mult) elif qcpackage == 'qcscript': msg += "Running qcscript...\n" geofile = smilesname + '.geo' geo = ob.get_geo(mol) io.write_file(geo, geofile) if io.check_file(geofile, 1): msg += qc.run_qcscript(qcscript, qctemplate, geofile, mult) else: msg = '{0} package not implemented\n'.format(qcpackage) msg += 'Available packages are {0}'.format(available_packages) exit(msg) print(msg) msg = '' if parseqc: if io.check_file(qclog, timeout=1, verbose=False): out = io.read_file(qclog, aslines=False) d = qc.parse_output(out, smilesname, parameters['writefiles']) pprint(d) if runthermo: groupstext = tc.get_new_groups() io.write_file(groupstext, 'new.groups') msg += "Parsing qc logfile '{0}'\n".format(io.get_path(qclog)) newmsg, xyz, freqs, zpe, deltaH, afreqs, xmat = qc.parse_qclog( qclog, qcpackage, anharmonic=runanharmonic) msg += newmsg if xyz is not None: msg += "Optimized xyz in Angstroms:\n{0} \n".format(xyz) else: runthermo = False if freqs is not None: msg += "Harmonic frequencies in cm-1:\n {0} \n".format(freqs) else: runthermo = False if afreqs: msg += "Anharmonic frequencies in cm-1:\n {0}\n".format(afreqs) else: runanharmonic = False if zpe: msg += 'ZPE = {0} kcal/mol\n'.format(zpe) else: runthermo = False if deltaH is not None: msg += 'deltaH = {0} kcal/mol\n'.format(deltaH) else: runthermo = False if xmat is not None: msg += 'Xmat = {0} kcal/mol\n'.format(xmat) else: runanharmonic = False if runthermo: msg += tc.write_chemkin_polynomial(mol, zpe, xyz, freqs, deltaH, parameters) io.cd(cwd) print(msg) return
available_packages = ['nwchem', 'molpro', 'mopac', 'gaussian'] start = timer() args = get_args() parameters = vars(args) if not parameters['qcpackage']: if not parameters['qctemplate']: if parameters['runqc']: exit('Please specify template file with -t') else: parameters['qcpackage'] = qc.get_package(parameters['qctemplate']) if not parameters['qcexe']: if parameters['qcpackage'] in available_packages: parameters['qcexe'] = parameters[parameters['qcpackage']] if parameters['writefiles']: parameters['parseqc'] = True parameters['qctemplate'] = io.get_path(args.qctemplate) parameters['qcexe'] = io.get_path(args.qcexe, executable=True) parameters['qcscript'] = io.get_path(args.qcscript) parameters['mopac'] = io.get_path(args.mopac, executable=True) parameters['nwchem'] = io.get_path(args.nwchem, executable=True) parameters['gaussian'] = io.get_path(args.gaussian, executable=True) parameters['molpro'] = io.get_path(args.molpro, executable=True) parameters['messpf'] = io.get_path(args.messpf, executable=True) parameters['thermp'] = io.get_path(args.thermp, executable=True) parameters['pac99'] = io.get_path(args.pac99, executable=True) beginindex = args.first endindex = args.last inp = args.input nproc = args.nproc if io.check_file(inp): mylist = io.read_list(inp)