def setup(self): files = os.listdir(".") num_structures = 0 if not set(files).issuperset(VASP_INPUT_FILES): for f in files: try: struct = read_structure(f) num_structures += 1 except: pass if num_structures != 1: raise RuntimeError("{} structures found. Unable to continue." .format(num_structures)) else: self.default_vis.write_input(struct, ".") if self.backup: for f in VASP_INPUT_FILES: shutil.copy(f, "{}.orig".format(f)) if self.auto_npar: try: vi = VaspInput.from_directory(".") incar = vi["INCAR"] #Only optimized NPAR for non-HF and non-RPA calculations. if (not incar.get("LHFCALC")) and (not incar.get("LRPA")): import multiprocessing ncores = multiprocessing.cpu_count() for npar in range(int(round(math.sqrt(ncores))), ncores): if ncores % npar == 0: incar["NPAR"] = npar break incar.write_file("INCAR") except: pass if self.settings_override is not None: vi = VaspInput.from_directory(".") m = Modder([FileActions, DictActions]) modified = [] for a in self.settings_override: if "dict" in a: modified.append(a["dict"]) vi[a["dict"]] = m.modify_object(a["action"], vi[a["dict"]]) elif "filename" in a: m.modify(a["action"], a["filename"]) for f in modified: vi[f].write_file(f)
def test_from_directory(self): vi = VaspInput.from_directory(test_dir, optional_files={"CONTCAR.Li2O": Poscar}) self.assertEqual(vi["INCAR"]["ALGO"], "Damped") self.assertIn("CONTCAR.Li2O", vi) d = vi.to_dict vinput = VaspInput.from_dict(d) self.assertIn("CONTCAR.Li2O", vinput)
def check(self): vi = VaspInput.from_directory(".") nelm = vi["INCAR"].get("NELM", 60) try: oszicar = Oszicar(self.output_filename) esteps = oszicar.ionic_steps if len(esteps) > 10: return all([len(e) == nelm for e in esteps[-11:-1]]) except: pass return False
def correct(self): backup(["INCAR", "KPOINTS", "POSCAR", "OUTCAR", self.output_filename, "vasp.out"]) vi = VaspInput.from_directory(".") ediff = float(vi["INCAR"].get("EDIFF", 1e-4)) actions = [{"file": "CONTCAR", "action": {"_file_copy": {"dest": "POSCAR"}}}, {"dict": "INCAR", "action": {"_set": {"EDIFF": ediff*0.75}}}] VaspModder(vi=vi).apply_actions(actions) return {"errors": ["MaxForce"], "actions": actions}
def correct(self): backup([self.output_filename, "INCAR", "KPOINTS", "POSCAR", "OUTCAR", "vasprun.xml"]) vi = VaspInput.from_directory(".") m = reduce(operator.mul, vi["KPOINTS"].kpts[0]) m = max(int(round(m ** (1 / 3))), 1) if vi["KPOINTS"].style.lower().startswith("m"): m += m % 2 actions = [{"dict": "KPOINTS", "action": {"_set": {"kpoints": [[m] * 3]}}}] VaspModder(vi=vi).apply_actions(actions) return {"errors": ["mesh_symmetry"], "actions": actions}
def correct(self): backup([self.output_filename, "INCAR", "KPOINTS", "POSCAR", "OUTCAR", "vasprun.xml"]) vi = VaspInput.from_directory('.') actions = [] if vi["INCAR"].get("ALGO", "Normal") == "Fast": actions.append({"dict": "INCAR", "action": {"_set": {"ALGO": "Normal"}}}) VaspModder(vi=vi).apply_actions(actions) return {"errors": ["Frozen job"], "actions": actions}
def correct(self): # change ALGO = Fast to Normal if ALGO is !Normal vi = VaspInput.from_directory(".") algo = vi["INCAR"].get("ALGO", "Normal") if algo.lower() not in ['normal', 'n']: backup(["INCAR", "KPOINTS", "POSCAR", "OUTCAR", "vasprun.xml"]) actions = [{"dict": "INCAR", "action": {"_set": {"ALGO": "Normal"}}}] VaspModder(vi=vi).apply_actions(actions) return {"errors": ["Positive energy"], "actions": actions} #Unfixable error. Just return None for actions. else: return {"errors": ["Positive energy"], "actions": None}
def run(self): cmd = list(self.vasp_cmd) if self.auto_gamma: vi = VaspInput.from_directory(".") kpts = vi["KPOINTS"] if kpts.style == "Gamma" and tuple(kpts.kpts[0]) == (1, 1, 1): if self.gamma_vasp_cmd is not None and os.path.exists( self.gamma_vasp_cmd[-1]): cmd = self.gamma_vasp_cmd elif os.path.exists(cmd[-1] + ".gamma"): cmd[-1] += ".gamma" with open(self.output_file, 'w') as f: return subprocess.Popen(cmd, stdout=f)
def correct(self): backup() vi = VaspInput.from_directory(".") potim = float(vi["INCAR"].get("POTIM", 0.5)) * 0.5 actions = [{"dict": "INCAR", "action": {"_set": {"POTIM": potim}}}] m = Modder() modified = [] for a in actions: modified.append(a["dict"]) vi[a["dict"]] = m.modify_object(a["action"], vi[a["dict"]]) for f in modified: vi[f].write_file(f) return {"errors": ["POTIM"], "actions": actions}
def correct(self): backup(["INCAR", "KPOINTS", "POSCAR", "OUTCAR", "vasprun.xml"]) vi = VaspInput.from_directory(".") potim = float(vi["INCAR"].get("POTIM", 0.5)) ibrion = int(vi["INCAR"].get("IBRION", 0)) if potim < 0.2 and ibrion != 3: actions = [{"dict": "INCAR", "action": {"_set": {"IBRION": 3, "SMASS": 0.75}}}] else: actions = [{"dict": "INCAR", "action": {"_set": {"POTIM": potim * 0.5}}}] VaspModder(vi=vi).apply_actions(actions) return {"errors": ["POTIM"], "actions": actions}
def correct(self): backup(self.output_filename) p = Poscar.from_file("POSCAR") s = p.structure trans = PerturbStructureTransformation(0.05) new_s = trans.apply_transformation(s) actions = [{"dict": "POSCAR", "action": {"_set": {"structure": new_s.to_dict}}, "transformation": trans.to_dict}] m = Modder() vi = VaspInput.from_directory(".") for a in actions: vi[a["dict"]] = m.modify_object(a["action"], vi[a["dict"]]) vi["POSCAR"].write_file("POSCAR") return {"errors": ["Frozen job"], "actions": actions}
def correct(self): backup(self.output_filename) vi = VaspInput.from_directory(".") m = reduce(operator.mul, vi["KPOINTS"].kpts[0]) m = max(int(round(m ** (1 / 3))), 1) if vi["KPOINTS"].style.lower().startswith("m"): m += m % 2 actions = [{"dict": "KPOINTS", "action": {"_set": {"kpoints": [[m] * 3]}}}] m = Modder() modified = [] for a in actions: modified.append(a["dict"]) vi[a["dict"]] = m.modify_object(a["action"], vi[a["dict"]]) for f in modified: vi[f].write_file(f) return {"errors": ["mesh_symmetry"], "actions": actions}
def run_task(self, fw_spec): chgcar_start = False vi = VaspInput.from_directory(".") # read the VaspInput from the previous run # figure out what GGA+U values to use and override them mpvis = MPVaspInputSet() incar = mpvis.get_incar(vi['POSCAR'].structure).to_dict incar_updates = {k: incar[k] for k in incar.keys() if 'LDAU' in k} # LDAU values to use vi['INCAR'].update(incar_updates) # override the +U keys # start from the CHGCAR of previous run if os.path.exists('CHGCAR'): vi['INCAR']['ICHARG'] = 1 chgcar_start = True vi['INCAR'].write_file('INCAR') # write back the new INCAR to the current directory return FWAction(stored_data={'chgcar_start': chgcar_start})
def run_task(self, fw_spec): chgcar_start = False # read the VaspInput from the previous run vi = VaspInput.from_directory(".") # figure out what GGA+U values to use and override them # LDAU values to use mpvis = MPVaspInputSet() incar = mpvis.get_incar(vi['POSCAR'].structure).to_dict incar_updates = {k: incar[k] for k in incar.keys() if 'LDAU' in k} vi['INCAR'].update(incar_updates) # override the +U keys # start from the CHGCAR of previous run if os.path.exists('CHGCAR'): vi['INCAR']['ICHARG'] = 1 chgcar_start = True # write back the new INCAR to the current directory vi['INCAR'].write_file('INCAR') return FWAction(stored_data={'chgcar_start': chgcar_start})
def check(self): msg = "Reciprocal lattice and k-lattice belong to different class of" \ " lattices." try: v = Vasprun(self.output_vasprun) vi = VaspInput.from_directory('.') # According to VASP admins, you can disregard this error # if symmetry is off #Also disregard if automatic KPOINT generation is used if v.converged or (not v.incar.get('ISYM', True)) or\ vi["KPOINTS"].style == Kpoints.supported_modes.Automatic: return False except: pass with open(self.output_filename, "r") as f: for line in f: l = line.strip() if l.find(msg) != -1: return True return False
def run(self): """ Perform the actual VASP run. Returns: (subprocess.Popen) Used for monitoring. """ cmd = list(self.vasp_cmd) if self.auto_gamma: vi = VaspInput.from_directory(".") kpts = vi["KPOINTS"] if kpts.style == "Gamma" and tuple(kpts.kpts[0]) == (1, 1, 1): if self.gamma_vasp_cmd is not None and which( self.gamma_vasp_cmd[-1]): cmd = self.gamma_vasp_cmd elif which(cmd[-1] + ".gamma"): cmd[-1] += ".gamma" logging.info("Running {}".format(" ".join(cmd))) with open(self.output_file, 'w') as f: p = subprocess.Popen(cmd, stdout=f) return p
def correct(self): backup() actions = [{"file": "CONTCAR", "action": {"_file_copy": {"dest": "POSCAR"}}}, {"dict": "INCAR", "action": {"_set": {"ISTART": 1, "ALGO": "Normal", "NELMDL": 6, "BMIX": 0.001, "AMIX_MAG": 0.8, "BMIX_MAG": 0.001}}}] vi = VaspInput.from_directory(".") m = Modder(actions=[DictActions, FileActions]) for a in actions: if "dict" in a: vi[a["dict"]] = m.modify_object(a["action"], vi[a["dict"]]) elif "file" in a: m.modify(a["action"], a["file"]) vi["INCAR"].write_file("INCAR") return {"errors": ["Unconverged"], "actions": actions}
def correct(self): # if change_algo is True, change ALGO = Fast to Normal if ALGO is # Fast. If still not converging, following Kresse's # recommendation, we will try two iterations of different mixing # parameters. If this error is caught again, then kil the job vi = VaspInput.from_directory(".") algo = vi["INCAR"].get("ALGO", "Normal") amix = vi["INCAR"].get("AMIX", 0.4) bmix = vi["INCAR"].get("BMIX", 1.0) amin = vi["INCAR"].get("AMIN", 0.1) actions = [] if self.change_algo: if algo == "Fast": backup(["INCAR", "KPOINTS", "POSCAR", "OUTCAR", "vasprun.xml"]) actions.append({"dict": "INCAR", "action": {"_set": {"ALGO": "Normal"}}}) elif amix > 0.1 and bmix > 0.01: #try linear mixing backup(["INCAR", "KPOINTS", "POSCAR", "OUTCAR", "vasprun.xml"]) actions.append({"dict": "INCAR", "action": {"_set": {"AMIX": 0.1, "BMIX": 0.01, "ICHARG": 2}}}) elif bmix < 3.0 and amin > 0.01: #Try increasing bmix backup(["INCAR", "KPOINTS", "POSCAR", "OUTCAR", "vasprun.xml"]) actions.append({"dict": "INCAR", "action": {"_set": {"AMIN": 0.01, "BMIX": 3.0, "ICHARG": 2}}}) if actions: VaspModder(vi=vi).apply_actions(actions) return {"errors": ["Non-converging job"], "actions": actions} #Unfixable error. Just return None for actions. else: return {"errors": ["Non-converging job"], "actions": None}
__author__ = 'Qimin' from pymatgen.io.vaspio.vasp_output import Vasprun from pymatgen.io.vaspio.vasp_input import VaspInput from pymatgen.io.vaspio_set import MPNonSCFVaspInputSet import os vasp_dir = os.path.dirname(os.path.abspath(__file__)) vasp_run = Vasprun(os.path.join(vasp_dir, "vasprun.xml")).to_dict nband = int(vasp_run['input']['parameters']['NBANDS']) prec = str(vasp_run['input']['incar']['PREC']) encut = int(vasp_run['input']['incar']['ENCUT']) user_incar_settings={"PREC":prec,"ENCUT":encut,"EDIFF":1E-4,"NBANDS":nband,"NSW":0} #user_incar_settings={"EDIFF":1E-4,"NBANDS":nband,"NSW":0} mpvis = MPNonSCFVaspInputSet(user_incar_settings=user_incar_settings) vi = VaspInput.from_directory(".") # read the VaspInput from the previous run mpvis.get_kpoints(vi['POSCAR'].structure).write_file('KPOINTS') mpvis.get_incar(vi['POSCAR'].structure).write_file('INCAR')
def correct(self): backup(self.output_filename) actions = [] vi = VaspInput.from_directory(".") if "tet" in self.errors or "dentet" in self.errors: actions.append({"dict": "INCAR", "action": {"_set": {"ISMEAR": 0}}}) if "inv_rot_mat" in self.errors: actions.append({"dict": "INCAR", "action": {"_set": {"SYMPREC": 1e-8}}}) if "brmix" in self.errors or "zpotrf" in self.errors: actions.append({"dict": "INCAR", "action": {"_set": {"ISYM": 0}}}) if "subspacematrix" in self.errors or "rspher" in self.errors or \ "real_optlay" in self.errors: actions.append({"dict": "INCAR", "action": {"_set": {"LREAL": False}}}) if "tetirr" in self.errors or "incorrect_shift" in self.errors: actions.append({"dict": "KPOINTS", "action": {"_set": {"generation_style": "Gamma"}}}) if "amin" in self.errors: actions.append({"dict": "INCAR", "action": {"_set": {"AMIN": "0.01"}}}) if "too_few_bands" in self.errors: if "NBANDS" in vi["INCAR"]: nbands = int(vi["INCAR"]["NBANDS"]) else: with open("OUTCAR") as f: for line in f: if "NBANDS" in line: try: d = line.split("=") nbands = int(d[-1].strip()) break except (IndexError, ValueError): pass actions.append({"dict": "INCAR", "action": {"_set": {"NBANDS": int(1.1 * nbands)}}}) if "triple_product" in self.errors: s = vi["POSCAR"].structure trans = SupercellTransformation(((1, 0, 0), (0, 0, 1), (0, 1, 0))) new_s = trans.apply_transformation(s) actions.append({"dict": "POSCAR", "action": {"_set": {"structure": new_s.to_dict}}, "transformation": trans.to_dict}) if "rot_matrix" in self.errors or "pricel" in self.errors: s = vi["POSCAR"].structure trans = PerturbStructureTransformation(0.05) new_s = trans.apply_transformation(s) actions.append({"dict": "POSCAR", "action": {"_set": {"structure": new_s.to_dict}}, "transformation": trans.to_dict}) actions.append({"dict": "INCAR", "action": {"_set": {"SYMPREC": 1e-8}}}) if "brions" in self.errors: potim = float(vi["INCAR"].get("POTIM", 0.5)) + 0.1 actions.append({"dict": "INCAR", "action": {"_set": {"POTIM": potim}}}) m = Modder() modified = [] for a in actions: modified.append(a["dict"]) vi[a["dict"]] = m.modify_object(a["action"], vi[a["dict"]]) for f in modified: vi[f].write_file(f) return {"errors": list(self.errors), "actions": actions}
def correct(self): #pylint: disable=R0915,R0912,R0914 """ "brmix"にてINCARにADDGRIDを追加する """ backup([self.output_filename, "INCAR", "KPOINTS", "POSCAR", "OUTCAR", "vasprun.xml"]) actions = [] vi = VaspInput.from_directory(".") if "tet" in self.errors or "dentet" in self.errors: actions.append({"dict": "INCAR", "action": {"_set": {"ISMEAR": 0}}}) if "inv_rot_mat" in self.errors: actions.append({"dict": "INCAR", "action": {"_set": {"SYMPREC": 1e-8}}}) if "brmix" in self.errors and "NELECT" in vi["INCAR"]: #brmix error always shows up after DAV steps if NELECT is specified self.errors.remove("brmix") if "brmix" in self.errors or "zpotrf" in self.errors: actions.append({"dict": "INCAR", "action": {"_set": {"ISYM": 0}}}) #140814 add actions.append({"dict": "INCAR", "action": {"_set": {"ADDGRID": True}}}) # Based on VASP forum's recommendation, you should delete the # CHGCAR and WAVECAR when dealing with these errors. actions.append({"file": "CHGCAR", "action": {"_file_delete": {'mode': "actual"}}}) actions.append({"file": "WAVECAR", "action": {"_file_delete": {'mode': "actual"}}}) if "subspacematrix" in self.errors or "rspher" in self.errors or \ "real_optlay" in self.errors: actions.append({"dict": "INCAR", "action": {"_set": {"LREAL": False}}}) if "tetirr" in self.errors or "incorrect_shift" in self.errors or \ "rot_matrix" in self.errors: actions.append({"dict": "KPOINTS", "action": {"_set": {"generation_style": "Gamma"}}}) if "amin" in self.errors: actions.append({"dict": "INCAR", "action": {"_set": {"AMIN": "0.01"}}}) if "triple_product" in self.errors: s = vi["POSCAR"].structure trans = SupercellTransformation(((1, 0, 0), (0, 0, 1), (0, 1, 0))) new_s = trans.apply_transformation(s) actions.append({"dict": "POSCAR", "action": {"_set": {"structure": new_s.to_dict}}, "transformation": trans.to_dict}) if "pricel" in self.errors: actions.append({"dict": "INCAR", "action": {"_set": {"SYMPREC": 1e-8, "ISYM": 0}}}) if "brions" in self.errors: potim = float(vi["INCAR"].get("POTIM", 0.5)) + 0.1 actions.append({"dict": "INCAR", "action": {"_set": {"POTIM": potim}}}) if "zbrent" in self.errors: actions.append({"dict": "INCAR", "action": {"_set": {"IBRION": 1}}}) if "too_few_bands" in self.errors: if "NBANDS" in vi["INCAR"]: nbands = int(vi["INCAR"]["NBANDS"]) else: with open("OUTCAR") as f: for line in f: if "NBANDS" in line: try: d = line.split("=") nbands = int(d[-1].strip()) break except (IndexError, ValueError): pass actions.append({"dict": "INCAR", "action": {"_set": {"NBANDS": int(1.1 * nbands)}}}) if "aliasing" in self.errors: with open("OUTCAR") as f: grid_adjusted = False changes_dict = {} for line in f: if "aliasing errors" in line: try: grid_vector = line.split(" NG", 1)[1] value = [int(s) for s in grid_vector.split(" ") if s.isdigit()][0] changes_dict["NG" + grid_vector[0]] = value grid_adjusted = True except (IndexError, ValueError): pass #Ensure that all NGX, NGY, NGZ have been checked if grid_adjusted and 'NGZ' in line: actions.append({"dict": "INCAR", "action": {"_set": changes_dict}}) break m = Modder(actions=[DictActions, FileActions]) modified = [] for a in actions: if "dict" in a: modified.append(a["dict"]) vi[a["dict"]] = m.modify_object(a["action"], vi[a["dict"]]) elif "file" in a: m.modify(a["action"], a["file"]) for f in modified: vi[f].write_file(f) return {"errors": list(self.errors), "actions": actions}
def correct(self): backup([self.output_filename, "INCAR", "KPOINTS", "POSCAR", "OUTCAR", "OSZICAR", "vasprun.xml"]) actions = [] vi = VaspInput.from_directory(".") if self.errors.intersection(["tet", "dentet"]): actions.append({"dict": "INCAR", "action": {"_set": {"ISMEAR": 0}}}) if "inv_rot_mat" in self.errors: actions.append({"dict": "INCAR", "action": {"_set": {"SYMPREC": 1e-8}}}) if "brmix" in self.errors: actions.append({"dict": "INCAR", "action": {"_set": {"ISYM": 0}}}) if vi["KPOINTS"].style == Kpoints.supported_modes.Monkhorst: actions.append({"dict": "KPOINTS", "action": {"_set": {"generation_style": "Gamma"}}}) # Based on VASP forum's recommendation, you should delete the # CHGCAR and WAVECAR when dealing with this error. actions.append({"file": "CHGCAR", "action": {"_file_delete": {'mode': "actual"}}}) actions.append({"file": "WAVECAR", "action": {"_file_delete": {'mode': "actual"}}}) if "zpotrf" in self.errors: # Usually caused by short bond distances. If on the first step, # volume needs to be increased. Otherwise, it was due to a step # being too big and POTIM should be decreased. try: oszicar = Oszicar("OSZICAR") nsteps = len(oszicar.ionic_steps) except: nsteps = 0 if nsteps >= 1: potim = float(vi["INCAR"].get("POTIM", 0.5)) / 2.0 actions.append( {"dict": "INCAR", "action": {"_set": {"ISYM": 0, "POTIM": potim}}}) else: s = vi["POSCAR"].structure s.apply_strain(0.2) actions.append({"dict": "POSCAR", "action": {"_set": {"structure": s.as_dict()}}}) # Based on VASP forum's recommendation, you should delete the # CHGCAR and WAVECAR when dealing with this error. actions.append({"file": "CHGCAR", "action": {"_file_delete": {'mode': "actual"}}}) actions.append({"file": "WAVECAR", "action": {"_file_delete": {'mode': "actual"}}}) if self.errors.intersection(["subspacematrix", "rspher", "real_optlay"]): actions.append({"dict": "INCAR", "action": {"_set": {"LREAL": False}}}) if self.errors.intersection(["tetirr", "incorrect_shift"]): if vi["KPOINTS"].style == Kpoints.supported_modes.Monkhorst: actions.append({"dict": "KPOINTS", "action": {"_set": {"generation_style": "Gamma"}}}) if "rot_matrix" in self.errors: if vi["KPOINTS"].style == Kpoints.supported_modes.Monkhorst: actions.append({"dict": "KPOINTS", "action": {"_set": {"generation_style": "Gamma"}}}) else: actions.append({"dict": "INCAR", "action": {"_set": {"ISYM": 0}}}) if "amin" in self.errors: actions.append({"dict": "INCAR", "action": {"_set": {"AMIN": "0.01"}}}) if "triple_product" in self.errors: s = vi["POSCAR"].structure trans = SupercellTransformation(((1, 0, 0), (0, 0, 1), (0, 1, 0))) new_s = trans.apply_transformation(s) actions.append({"dict": "POSCAR", "action": {"_set": {"structure": new_s.as_dict()}}, "transformation": trans.as_dict()}) if "pricel" in self.errors: actions.append({"dict": "INCAR", "action": {"_set": {"SYMPREC": 1e-8, "ISYM": 0}}}) if "brions" in self.errors: potim = float(vi["INCAR"].get("POTIM", 0.5)) + 0.1 actions.append({"dict": "INCAR", "action": {"_set": {"POTIM": potim}}}) if "zbrent" in self.errors: actions.append({"dict": "INCAR", "action": {"_set": {"IBRION": 1}}}) if "too_few_bands" in self.errors: if "NBANDS" in vi["INCAR"]: nbands = int(vi["INCAR"]["NBANDS"]) else: with open("OUTCAR") as f: for line in f: if "NBANDS" in line: try: d = line.split("=") nbands = int(d[-1].strip()) break except (IndexError, ValueError): pass actions.append({"dict": "INCAR", "action": {"_set": {"NBANDS": int(1.1 * nbands)}}}) if "aliasing" in self.errors: with open("OUTCAR") as f: grid_adjusted = False changes_dict = {} r = re.compile(".+aliasing errors.*(NG.)\s*to\s*(\d+)") for line in f: m = r.match(line) if m: changes_dict[m.group(1)] = int(m.group(2)) grid_adjusted = True #Ensure that all NGX, NGY, NGZ have been checked if grid_adjusted and 'NGZ' in line: actions.extend( [{"dict": "INCAR", "action": {"_set": changes_dict}}, {"file": "CHGCAR", "action": {"_file_delete": {'mode': "actual"}}}, {"file": "WAVECAR", "action": {"_file_delete": {'mode': "actual"}}}]) break if "aliasing_incar" in self.errors: #vasp seems to give different warnings depending on whether the #aliasing error was caused by user supplied inputs d = {k: 1 for k in ['NGX', 'NGY', 'NGZ'] if k in vi['INCAR'].keys()} actions.extend([{"dict": "INCAR", "action": {"_unset": d}}, {"file": "CHGCAR", "action": {"_file_delete": {'mode': "actual"}}}, {"file": "WAVECAR", "action": {"_file_delete": {'mode': "actual"}}}]) if "pssyevx" in self.errors: actions.append({"dict": "INCAR", "action": {"_set": {"ALGO": "Normal"}}}) if "eddrmm" in self.errors: #RMM algorithm is not stable for this calculation if vi["INCAR"].get("ALGO", "Normal") in ["Fast", "VeryFast"]: actions.append({"dict": "INCAR", "action": {"_set": {"ALGO": "Normal"}}}) else: potim = float(vi["INCAR"].get("POTIM", 0.5)) / 2.0 actions.append({"dict": "INCAR", "action": {"_set": {"POTIM": potim}}}) actions.append({"file": "CHGCAR", "action": {"_file_delete": {'mode': "actual"}}}) actions.append({"file": "WAVECAR", "action": {"_file_delete": {'mode': "actual"}}}) VaspModder(vi=vi).apply_actions(actions) return {"errors": list(self.errors), "actions": actions}