def testDFTB(self): try: yaml_file = os.path.join(_TESTDATA_DIR, "Si2-muairss-dftb.yaml") cell_file = os.path.join(_TESTDATA_DIR, "Si2.cell") input_params = load_input_file(yaml_file, MuAirssSchema) with silence_stdio(True, True): input_atoms = io.read(cell_file) # Run Muairss write: sys.argv[1:] = ["-tw", cell_file, yaml_file] os.chdir(_TESTDATA_DIR) run_muairss() # Check all folders contain a dftb_in.hsd and geo_end.gen for rootDir, subDirs, files in os.walk( os.path.abspath("muon-airss-out-dftb/dftb+") ): expected_files = ["geo_end.gen", "dftb_in.hsd"] for s in subDirs: count = 0 for f in expected_files: f = os.path.join("muon-airss-out-dftb/dftb+/" + s, f) self.assertTrue(os.path.exists(f)) if count == 0: with silence_stdio(True, True): atoms = io.read(f) equal = atoms.cell == input_atoms.cell self.assertTrue(equal.all()) count += 1 # Run DFTB if _RUN_DFTB: subprocess.call(os.path.join(_TESTDATA_DIR, "script-dftb")) else: yaml_file = os.path.join(_TESTDATA_DIR, "Si2-muairss-dftb-read.yaml") input_params = load_input_file(yaml_file, MuAirssSchema) sys.argv[1:] = [cell_file, yaml_file] run_muairss() clust_folder = "Si2_clusters/dftb+" self.assertTrue(os.path.exists(clust_folder)) self.assertTrue( len( glob.glob( os.path.join( clust_folder, "*.{0}".format(input_params["clustering_save_format"]), ) ) ) > 0 ) self.assertTrue(os.path.exists("Si2_clusters.txt")) self.assertTrue(os.path.exists("Si2_Si2_dftb+_clusters.dat")) finally: # Remove all created files and folders _clean_testdata_dir()
def save_muairss_batch(args, global_params): structures_path = args.structures all_files = glob.glob(os.path.join(structures_path, "*")) structure_files = [ path for path in all_files if not os.path.splitext(path)[1] == '.yaml' ] global_params['out_folder'] = safe_create_folder( global_params['out_folder']) print("Beginning creation of {} structures".format(len(structure_files))) for path in structure_files: name = parse_structure_name(path) parameter_file = os.path.join(structures_path, "{}.yaml".format(name)) if not os.path.isfile(parameter_file): parameter_file = None struct = io.read(path) params = dict(global_params) # Copy params['name'] = name if parameter_file is not None: params = load_input_file(parameter_file, MuAirssSchema, merge=params) params['out_folder'] = params['name'] print("Making {} ---------------------".format(name)) save_muairss_collection(struct, params, batch_path=global_params['out_folder']) print("Done!")
def main(): parser = ap.ArgumentParser() parser.add_argument('structures', type=str, default=None, help="A structure file or a folder of files in an ASE " "readable format") parser.add_argument('parameter_file', type=str, default=None, help="""YAML formatted file with generation parameters. The arguments can be overridden by structure-specific YAML files if a folder is passed as the first argument.""") args = parser.parse_args() params = load_input_file(args.parameter_file, MuAirssSchema) if os.path.isdir(args.structures): save_muairss_batch(args, params) elif os.path.isfile(args.structures): struct = io.read(args.structures) save_muairss_collection(struct, params) else: raise RuntimeError("{} is neither a file or a directory".format( args.structures))
def nq_entry(): parser = ap.ArgumentParser() parser.add_argument('parameter_file', type=str, help="YAML file containing relevant input parameters") parser.add_argument( '-w', action='store_true', default=False, help="Create and write input files instead of parsing the results") args = parser.parse_args() # Load parameters params = load_input_file(args.parameter_file, MuonHarmonicSchema) # Temperature if params['average_T'] is None: params['average_T'] = params['displace_T'] if args.w: muon_vibrational_average_write(**params) else: try: muon_vibrational_average_read(**params) except IOError as e: print('Read/write error: {0}'.format(e)) print('\nThis could mean it was impossible to find the displaced ' 'structure folder: maybe you wanted to run with the ' '-w option to write it?\n')
def test_write(self): # read in cell file to get atom try: input_folder = _TESTDATA_DIR + "/Si2" os.chdir(input_folder) output_folder = "test_save" os.mkdir(output_folder) with silence_stdio(): atoms = io.read("Si2.cell") # test writing geom_opt output param_file = "Si2-muairss-uep.yaml" params = load_input_file(param_file, MuAirssSchema) reader = ReadWriteUEP(params=params) reader.write(atoms, output_folder) self.assertTrue( os.path.exists(os.path.join(output_folder, "test_save.yaml"))) params["charged"] = False reader = ReadWriteUEP(params=params) reader.write(atoms, output_folder) except Exception as e: print(e) finally: shutil.rmtree("test_save")
def geomopt_entry(): parser = ap.ArgumentParser() parser.add_argument('input', type=str, help="Input YAML file for the calculation") args = parser.parse_args() params = load_input_file(args.input, UEPOptSchema) seedpath = os.path.splitext(args.input)[0] seedname = os.path.split(seedpath)[1] if params['chden_seed'] is None: params['chden_seed'] = seedname # Default is the same with open(seedpath + '.uep', 'w') as outf: try: results = geomopt(params, outf) except Exception as e: print("Error: ", e) return # Now dump results if params['save_pickle']: pickle.dump(results, open(seedpath + '.uep.pkl', 'wb')) muon = Atoms('H', positions=[results['x']]) if params['save_structs']: io.write(seedpath + '.xyz', results['struct'] + muon)
def main(task=None): parser = ap.ArgumentParser() parser.add_argument('structures', type=str, default=None, help="A structure file or a folder of files in an ASE " "readable format") parser.add_argument('parameter_file', type=str, default=None, help="""YAML formatted file with generation parameters. The arguments can be overridden by structure-specific YAML files if a folder is passed as the first argument.""") parser.add_argument('-t', type=str, default='r', choices=['r', 'w'], dest='task', help="""Task to be run by muairss. Can be either 'w' (=generate and WRITE structures) or 'r' (=READ and cluster results). Default is READ.""") args = parser.parse_args() params = load_input_file(args.parameter_file, MuAirssSchema) if task is None: task = args.task if task == 'w': if os.path.isdir(args.structures): muairss_batch_io(args, params, True) elif os.path.isfile(args.structures): with silence_stdio(): struct = io.read(args.structures) save_muairss_collection(struct, params) else: raise RuntimeError("{} is neither a file or a directory".format( args.structures)) elif task == 'r': if os.path.isdir(args.structures): all_coll = muairss_batch_io(args, params) clusters = {} for name, data in all_coll.items(): clusters[name] = muairss_cluster(data['struct'], data['collection'], params) elif os.path.isfile(args.structures): with silence_stdio(): struct = io.read(args.structures) collection = load_muairss_collection(struct, params) clusters = { params['name']: muairss_cluster(struct, collection, params) } else: raise RuntimeError("{} is neither a file or a directory".format( args.structures)) write_cluster_report(args, params, clusters)
def asephonons_entry(): from ase import io from ase.calculators.dftb import Dftb from pymuonsuite.data.dftb_pars import DFTBArgs parser = ap.ArgumentParser(description="Compute phonon modes with ASE and" " DFTB+ for reuse in quantum effects " "calculations.") parser.add_argument('structure_file', type=str, help="Structure for which to compute the phonons") parser.add_argument('parameter_file', type=str, help="YAML file containing relevant input parameters") args = parser.parse_args() # Load parameters params = load_input_file(args.parameter_file, AsePhononsSchema) fname, fext = os.path.splitext(args.structure_file) if params['name'] is None: params['name'] = fname # Load structure a = io.read(args.structure_file) # Create a Dftb calculator dargs = DFTBArgs(params['dftb_set']) # Is it periodic? if params['pbc']: a.set_pbc(True) calc = Dftb(atoms=a, label='asephonons', kpts=params['kpoint_grid'], **dargs.args) ph_kpts = params['phonon_kpoint_grid'] else: a.set_pbc(False) calc = Dftb(atoms=a, label='asephonons', **dargs.args) ph_kpts = None a.set_calculator(calc) phdata = ase_phonon_calc(a, kpoints=ph_kpts, ftol=params['force_tol'], force_clean=params['force_clean'], name=params['name']) # Save optimised structure io.write(params['name'] + '_opt' + fext, phdata.structure) # And write out the phonons outf = params['name'] + '_opt.phonons.pkl' pickle.dump(phdata, open(outf, 'wb')) write_phonon_report(args, params, phdata)
def testUEP(self): try: yaml_file = os.path.join(_TESTDATA_DIR, "Si2-muairss-uep.yaml") cell_file = os.path.join(_TESTDATA_DIR, "Si2.cell") input_params = load_input_file(yaml_file, MuAirssSchema) # Run Muairss write: sys.argv[1:] = ["-tw", cell_file, yaml_file] os.chdir(_TESTDATA_DIR) run_muairss() # Check all folders contain a yaml file for (rootDir, subDirs, files) in os.walk("muon-airss-out-uep/uep/"): for s in subDirs: expected_file = os.path.join( "muon-airss-out-uep/uep/" + s, s + ".yaml" ) self.assertTrue(os.path.exists(expected_file)) params = load_input_file(expected_file, UEPOptSchema) self.assertEqual(params["geom_steps"], input_params["geom_steps"]) self.assertEqual(params["opt_tol"], input_params["geom_force_tol"]) self.assertEqual(params["gw_factor"], input_params["uep_gw_factor"]) # Run UEP subprocess.call(os.path.join(_TESTDATA_DIR, "script-uep")) # Check all folders contain UEP file for (rootDir, subDirs, files) in os.walk("muon-airss-out-uep/uep/"): for s in subDirs: expected_file = os.path.join( "muon-airss-out-uep/uep/" + s, s + ".uep" ) self.assertTrue(os.path.exists(expected_file)) sys.argv[1:] = [cell_file, yaml_file] run_muairss() self.assertTrue(os.path.exists("Si2_clusters.txt")) self.assertTrue(os.path.exists("Si2_Si2_uep_clusters.dat")) finally: # Remove all created files and folders _clean_testdata_dir()
def nq_entry(): parser = ap.ArgumentParser() parser.add_argument( "structure", type=str, default=None, help="A structure file in an ASE readable format", ) parser.add_argument( "parameter_file", type=str, help="YAML file containing relevant input parameters", ) parser.add_argument( "-t", type=str, default="r", choices=["r", "w"], dest="task", help="""Task to be run by pm-nq. Can be either 'w' (=generate and WRITE structures) or 'r' (=READ and analyse results). Default is READ.""", ) args = parser.parse_args() # Load parameters params = load_input_file(args.parameter_file, MuonHarmonicSchema) # Temperature if params["average_T"] is None: params["average_T"] = params["displace_T"] if args.task == "w": try: muon_vibrational_average_write(args.structure, **params) except IOError as e: print(e) else: try: muon_vibrational_average_read(args.structure, **params) except IOError as e: print("Read/write error: {0}".format(e)) print( "\nThis could mean it was impossible to find the displaced " "structure folder: maybe you wanted to run with the " "-t w option to write it?\n" )
def plot_entry(): parser = ap.ArgumentParser() parser.add_argument('input', type=str, help="Input YAML file for the calculation") args = parser.parse_args() params = load_input_file(args.input, UEPPlotSchema) seedpath = os.path.splitext(args.input)[0] seedname = os.path.split(seedpath)[1] if params['chden_seed'] is None: params['chden_seed'] = seedname # Default is the same plot(params, seedname)
def muairss_batch_io(args, global_params, save=False): structures_path = args.structures all_files = glob.glob(os.path.join(structures_path, "*")) structure_files = [ path for path in all_files if not os.path.splitext(path)[1] == ".yaml" ] if save: global_params["out_folder"] = safe_create_folder(global_params["out_folder"]) print( "Beginning {0} of {1} structures".format( "creation" if save else "loading", len(structure_files) ) ) bpath = global_params["out_folder"] loaded = {} for path in structure_files: name = parse_structure_name(path) parameter_file = os.path.join(structures_path, "{}.yaml".format(name)) if not os.path.isfile(parameter_file): parameter_file = None with silence_stdio(): struct = io.read(path) params = dict(global_params) # Copy params["name"] = name if parameter_file is not None: params = load_input_file(parameter_file, MuAirssSchema, merge=params) params["out_folder"] = params["name"] if save: print("Making {} ---------------------".format(name)) save_muairss_collection(struct, params, batch_path=bpath) else: print("Loading {} ---------------------".format(name)) coll = load_muairss_collection(struct, params, batch_path=bpath) loaded[name] = {"struct": struct, "collection": coll} print("Done!") if not save: return loaded
def geomopt_entry(): parser = ap.ArgumentParser() parser.add_argument('input', type=str, help="Input YAML file for the calculation") args = parser.parse_args() params = load_input_file(args.input, UEPSchema) seedpath = os.path.splitext(args.input)[0] seedname = os.path.split(seedpath)[1] if params['chden_seed'] is None: params['chden_seed'] = seedname # Default is the same with open(seedpath + '.uep', 'w') as outf: results = geomopt(params, outf) # Now dump results if params['save_pickle']: pickle.dump(results, open(seedpath + '.uep.pkl', 'wb'))
def nq_entry(): parser = ap.ArgumentParser() parser.add_argument('parameter_file', type=str, help="YAML file containing relevant input parameters") parser.add_argument('-w', action='store_true', default=False, help="Create and write input files instead of parsing the results") args = parser.parse_args() # Load parameters params = load_input_file(args.parameter_file, MuonHarmonicSchema) if args.w: muon_vibrational_average_write(**params) else: try: muon_vibrational_average_read(**params) except IOError: print('\nCould not find displaced structure folder: ' 'maybe you wanted to run with the -w option' ' to write it?\n')
def testCASTEP(self): try: yaml_file = os.path.join(_TESTDATA_DIR, "Si2-muairss-castep.yaml") cell_file = os.path.join(_TESTDATA_DIR, "Si2.cell") param_file = os.path.join(_TESTDATA_DIR, "Si2.param") input_params = load_input_file(yaml_file, MuAirssSchema) with silence_stdio(True, True): castep_param = read_param(param_file).param # Run Muairss write: sys.argv[1:] = ["-tw", cell_file, yaml_file] os.chdir(_TESTDATA_DIR) run_muairss() # Check all folders contain a yaml file for (rootDir, subDirs, files) in os.walk("muon-airss-out-castep/castep/"): for s in subDirs: expected_file = os.path.join( "muon-airss-out-castep/castep/" + s, s + ".cell" ) script_file = input_params["script_file"] if script_file is not None: expected_script = os.path.join( "muon-airss-out-castep/castep/" + s, "script.sh" ) self.assertTrue(os.path.exists(expected_script)) self.assertTrue(os.path.exists(expected_file)) with silence_stdio(): atoms = io.read(expected_file) self.assertEqual( atoms.calc.cell.kpoint_mp_grid.value, list_to_string(input_params["k_points_grid"]), ) expected_param_file = os.path.join( "muon-airss-out-castep/castep/" + s, s + ".param" ) self.assertTrue(os.path.exists(expected_param_file)) with silence_stdio(): output_castep_param = read_param(expected_param_file).param self.assertEqual( output_castep_param.cut_off_energy, castep_param.cut_off_energy, ) self.assertEqual( output_castep_param.elec_energy_tol, castep_param.elec_energy_tol, ) # below test didn't work as cell positions get rounded... # equal = atoms.cell == input_atoms.cell # self.assertTrue(equal.all()) yaml_file = os.path.join(_TESTDATA_DIR, "Si2-muairss-castep-read.yaml") sys.argv[1:] = [cell_file, yaml_file] run_muairss() self.assertTrue(os.path.exists("Si2_clusters.txt")) self.assertTrue(os.path.exists("Si2_Si2_castep_clusters.dat")) # Test clustering_write_input has produced files we expect: self.assertTrue(os.path.exists("Si2_clusters")) calc_folder = "Si2_clusters/castep/" for (rootDir, subDirs, files) in os.walk(calc_folder): for s in subDirs: expected_file = os.path.join(calc_folder + s, s + ".cell") self.assertTrue(os.path.exists(expected_file)) with silence_stdio(): atoms = io.read(expected_file) self.assertEqual( atoms.calc.cell.kpoint_mp_grid.value, list_to_string(input_params["k_points_grid"]), ) expected_param_file = os.path.join(calc_folder + s, s + ".param") self.assertTrue(os.path.exists(expected_param_file)) with silence_stdio(): output_castep_param = read_param(expected_param_file).param self.assertEqual( output_castep_param.cut_off_energy, castep_param.cut_off_energy, ) self.assertEqual( output_castep_param.elec_energy_tol, castep_param.elec_energy_tol, ) finally: # Remove all created files and folders _clean_testdata_dir()
import sys import glob from ase import io, Atoms from ase.build import make_supercell from pymuonsuite.utils import make_3x3 from pymuonsuite.schemas import load_input_file, MuAirssSchema atoms = io.read(sys.argv[1]) if len(sys.argv) > 2: params = load_input_file(sys.argv[2], MuAirssSchema) scell = make_3x3(params["supercell"]) atoms = make_supercell(atoms, scell) for f in glob.glob("muon-airss-out/dftb+/*/geo_end.xyz"): a = io.read(f) atoms += Atoms("H", positions=a.get_positions()[-1, None, :]) io.write("merged.cif", atoms)
def test_write(self): # read in cell file to get atom try: input_folder = _TESTDATA_DIR + "/Si2" output_folder = os.path.join(_TESTDATA_DIR, "test_save") os.mkdir(output_folder) os.chdir(input_folder) yaml_file = os.path.join(input_folder, "Si2-muairss-castep.yaml") cell_file = os.path.join(input_folder, "Si2.cell") param_file = os.path.join(input_folder, "Si2.param") input_params = load_input_file(yaml_file, MuAirssSchema) with silence_stdio(): castep_param = read_param(param_file).param atoms = io.read(cell_file) # test writing geom_opt output reader = ReadWriteCastep(params=input_params) reader.write( atoms, output_folder, sname="Si2_geom_opt", calc_type="GEOM_OPT", ) reader.write(atoms, output_folder, sname="Si2_magres", calc_type="MAGRES") # # read back in and check that atom locations are preserved with silence_stdio(): geom_opt_atoms = io.read( os.path.join(output_folder, "Si2_geom_opt.cell") ) magres_atoms = io.read(os.path.join(output_folder, "Si2_magres.cell")) equal = atoms.positions == geom_opt_atoms.positions # self.assertTrue(equal.all()) # is not true due to to rounding equal = geom_opt_atoms.positions == magres_atoms.positions self.assertTrue(equal.all()) self.assertEqual( geom_opt_atoms.calc.cell.kpoint_mp_grid.value, list_to_string(input_params["k_points_grid"]), ) self.assertEqual( magres_atoms.calc.cell.kpoint_mp_grid.value, list_to_string(input_params["k_points_grid"]), ) # Test if parameters file have correct tasks: with silence_stdio(): geom_params = read_param( os.path.join(output_folder, "Si2_geom_opt.param") ).param magres_params = read_param( os.path.join(output_folder, "Si2_magres.param") ).param self.assertEqual(geom_params.task.value, "GeometryOptimization") self.assertEqual(magres_params.task.value, "Magres") self.assertEqual(magres_params.magres_task.value, "Hyperfine") # These are only set in the param file only so should equal # the value in the param file: self.assertEqual(geom_params.geom_max_iter, castep_param.geom_max_iter) self.assertEqual(geom_params.cut_off_energy, castep_param.cut_off_energy) self.assertEqual(geom_params.elec_energy_tol, castep_param.elec_energy_tol) # This is set in the input yaml and param file so should equal # the value in the yaml file: self.assertEqual( geom_params.geom_force_tol.value, str(input_params["geom_force_tol"]), ) self.assertEqual(magres_params.cut_off_energy, castep_param.cut_off_energy) self.assertEqual( magres_params.elec_energy_tol, castep_param.elec_energy_tol ) finally: shutil.rmtree(output_folder)
def asephonons_entry(): from ase import io from ase.calculators.dftb import Dftb from pymuonsuite.data.dftb_pars import DFTBArgs parser = ap.ArgumentParser( description="Compute phonon modes with ASE and" " DFTB+ for reuse in quantum effects " "calculations." ) parser.add_argument( "structure_file", type=str, help="Structure for which to compute the phonons", ) parser.add_argument( "parameter_file", type=str, help="YAML file containing relevant input parameters", ) args = parser.parse_args() # Load parameters params = load_input_file(args.parameter_file, AsePhononsSchema) fname, fext = os.path.splitext(args.structure_file) if params["name"] is None: params["name"] = fname # Load structure with silence_stdio(): a = io.read(args.structure_file) # Create a Dftb calculator dargs = DFTBArgs(params["dftb_set"]) # Is it periodic? if params["pbc"]: a.set_pbc(True) calc = Dftb( atoms=a, label="asephonons", kpts=params["kpoint_grid"], **dargs.args ) ph_kpts = params["phonon_kpoint_grid"] else: a.set_pbc(False) calc = Dftb(atoms=a, label="asephonons", **dargs.args) ph_kpts = None a.calc = calc try: phdata = ase_phonon_calc( a, kpoints=ph_kpts, ftol=params["force_tol"], force_clean=params["force_clean"], name=params["name"], ) except Exception as e: print(e) print("Error: Could not write phonons file, see asephonons.out for" " details.") sys.exit(1) # Save optimised structure with silence_stdio(): io.write(params["name"] + "_opt" + fext, phdata.structure) # And write out the phonons outf = params["name"] + "_opt.phonons.pkl" pickle.dump(phdata, open(outf, "wb")) write_phonon_report(args, params, phdata)