Ejemplo n.º 1
0
def main():
    parser = argparse.ArgumentParser()
    parser.add_argument('-s',
                        '--structure',
                        dest='structure',
                        help='POSCAR file of the structure.')
    args = parser.parse_args()

    struc = Structure.from_file(args.structure)
    # Prepare the vasp working directory
    working_path = os.getcwd()

    vasp_path = os.path.join(working_path, 'vasp_tmp')
    if not os.path.exists(vasp_path):
        os.makedirs(vasp_path)
    else:
        shutil.rmtree(vasp_path)
        os.makedirs(vasp_path)

    staticset = MPStaticSet(struc,
                            force_gamma=True,
                            user_incar_settings={"ICHARG": 2})
    staticset.write_input(vasp_path)
    # chdir to vasp running directory
    os.chdir(vasp_path)
    subprocess.call("mpirun -np 10 vasp5.2-openmpi", shell=True)
Ejemplo n.º 2
0
def generate_old_polarization_folders(structures):
    """
    Generate the polarization calculations (old format) from the completed scf calculation
    """
    for name in structures:
        for i in range(3):
            # compute the Berry phase along the x-i, y- and z-directions (IGPAR = 1,2,3)
            # Note: calculations usualy are very sensetive to the choice of "NPPSTR" parameter. You might consider to reduce it.
            MPStaticSet.from_prev_calc(
                name,
                user_incar_settings={
                    "LBERRY": True,
                    "IGPAR": i + 1,
                    "ICHARG": 2,
                    "NPAR": 2,
                    "ALGO": "Fast",
                    "NPPSTR": 6,
                    "LAECHG": False,
                    "LVHAR": False,
                    "ISIF": 2
                },
                user_kpoints_settings={
                    "reciprocal_density": 500
                }).write_input(os.path.join(name, 'Berry_' + str(i + 1)))
            shutil.copy(os.path.join(name, 'CHGCAR'),
                        os.path.join(name, 'Berry_' + str(i + 1)))
Ejemplo n.º 3
0
 def write_vasp_files_static(self):
     """
     Writes:
         a folder that includes vasp input file for a single structure
     """
     mpset = MPStaticSet(self.out_struc, reciprocal_density=1, user_incar_settings={'EDIFF': 1e-5, 'ALGO': 'F', 'ISMEAR': 0})
     mpset.write_input(self.wd)
Ejemplo n.º 4
0
    def run_task(self, fw_spec):
        unitcell = Structure.from_file("POSCAR")
        supercell = self.get("supercell", None)
        if supercell is not None:
            os.system('cp POSCAR POSCAR-unitcell')
            unitcell.make_supercell(supercell)

        lepsilon = self.get("lepsilon", False)
        standardize = self.get("standardize", False)
        other_params = self.get("other_params", {})
        user_incar_settings = self.get("user_incar_settings", {})
        finder = SpacegroupAnalyzer(unitcell)
        prims = finder.get_primitive_standard_structure()
        # for lepsilon runs, the kpoints should be denser
        if lepsilon:
            kpoint_set = Generate_kpoints(prims, 0.02)
            struct = prims
        elif standardize:
            kpoint_set = Generate_kpoints(prims, 0.03)
            struct = prims
        else:
            kpoint_set = Generate_kpoints(unitcell, 0.03)
            struct = unitcell

        vis = MPStaticSet(struct,
                          user_incar_settings=user_incar_settings,
                          user_kpoints_settings=kpoint_set,
                          sym_prec=self.get("sym_prec", 0.1),
                          lepsilon=lepsilon,
                          **other_params)
        vis.write_input(".")
Ejemplo n.º 5
0
    def run_task(self, fw_spec):
        lepsilon = self.get("lepsilon")

        default_reciprocal_density = 200 if lepsilon else 100  # more k-points for dielectric calc.
        other_params = self.get("other_params", {})
        user_incar_settings = other_params.get("user_incar_settings", {})

        # for lepsilon runs, set EDIFF to 1E-5 unless user says otherwise
        if lepsilon and "EDIFF" not in user_incar_settings and \
                        "EDIFF_PER_ATOM" not in user_incar_settings:
            if "user_incar_settings" not in other_params:
                other_params["user_incar_settings"] = {}
            other_params["user_incar_settings"]["EDIFF"] = 1E-5

        vis = MPStaticSet.from_prev_calc(
            prev_calc_dir=self.get("prev_calc_dir", "."),
            reciprocal_density=self.get("reciprocal_density",
                                        default_reciprocal_density),
            small_gap_multiply=self.get("small_gap_multiply", None),
            standardize=self.get("standardize", False),
            sym_prec=self.get("sym_prec", 0.1),
            international_monoclinic=self.get("international_monoclinic",
                                              True),
            lepsilon=lepsilon,
            **other_params)
        vis.write_input(".")
Ejemplo n.º 6
0
    def Static (self):
        from pymatgen.io.vasp.sets import MPStaticSet
        import shutil
        import os
        filePath=self.dire
        for dirpath, dirnames, filenames in os.walk(filePath):
            # print(dirpath)
            for name in dirnames:
                if 'static' not in str(name):
                    path = os.path.join(filePath, name)
                    custom_settings = {"NELM": 60,'NPAR':4} # user custom incar settings
                    static = MPStaticSet.from_prev_calc(path, standardize=True,
                                                        user_incar_settings=custom_settings)
                    
                    diree = os.chdir(self.dire)

                    static.write_input("static_"+str(name))


                    pat = os.path.join(self.dire, "static_"+str(name))
                    os.chdir(pat)
                    #定义一个更改当前目录的变量
                    dire2 = './vaspstd_sub' 
                    #确立脚本名称
                    shutil.copy(r"C:\Users\41958\.spyder-py3\vaspstd_sub", dire2 )
Ejemplo n.º 7
0
    def __init__(self, structure=None, prev_calc_dir=None, name="static dielectric", vasp_cmd=VASP_CMD,
                 copy_vasp_outputs=True, lepsilon=True,
                 db_file=DB_FILE, parents=None, user_incar_settings=None,
                 pass_nm_results=False, **kwargs):
        """
         Static DFPT calculation Firework

        Args:
            structure (Structure): Input structure. If copy_vasp_outputs, used only to set the
                name of the FW.
            name (str): Name for the Firework.
            lepsilon (bool): Turn on LEPSILON to calculate polar properties
            vasp_cmd (str): Command to run vasp.
            copy_vasp_outputs (str or bool): Whether to copy outputs from previous
                run. Defaults to True.
            prev_calc_dir (str): Path to a previous calculation to copy from
            db_file (str): Path to file specifying db credentials.
            parents (Firework): Parents of this particular Firework.
                FW or list of FWS.
            user_incar_settings (dict): Parameters in INCAR to override
            pass_nm_results (bool): if true the normal mode eigen vals and vecs are passed so that
                next firework can use it.
            \*\*kwargs: Other kwargs that are passed to Firework.__init__.
        """
        name = "static dielectric" if lepsilon else "phonon"

        fw_name = "{}-{}".format(structure.composition.reduced_formula if structure else "unknown", name)

        user_incar_settings = user_incar_settings or {}
        t = []

        if prev_calc_dir:
            t.append(CopyVaspOutputs(calc_dir=prev_calc_dir, contcar_to_poscar=True))
            t.append(WriteVaspStaticFromPrev(lepsilon=lepsilon, other_params={
                'user_incar_settings': user_incar_settings, 'force_gamma': True}))
        elif parents and copy_vasp_outputs:
            t.append(CopyVaspOutputs(calc_loc=True, contcar_to_poscar=True))
            t.append(WriteVaspStaticFromPrev(lepsilon=lepsilon, other_params={
                'user_incar_settings': user_incar_settings, 'force_gamma': True}))
        elif structure:
            vasp_input_set = MPStaticSet(structure, lepsilon=lepsilon, force_gamma=True,
                                         user_incar_settings=user_incar_settings)
            t.append(WriteVaspFromIOSet(structure=structure,
                                        vasp_input_set=vasp_input_set))
        else:
            raise ValueError("Must specify structure or previous calculation")

        t.append(RunVaspCustodian(vasp_cmd=vasp_cmd))

        if pass_nm_results:
            t.append(pass_vasp_result({"structure": "a>>final_structure",
                                       "eigenvals": "a>>normalmode_eigenvals",
                                       "eigenvecs": "a>>normalmode_eigenvecs"},
                                      parse_eigen=True,
                                      mod_spec_key="normalmodes"))

        t.append(PassCalcLocs(name=name))
        t.append(VaspToDb(db_file=db_file, additional_fields={"task_label": name}))

        super(DFPTFW, self).__init__(t, parents=parents, name=fw_name, **kwargs)
Ejemplo n.º 8
0
    def run_task(self, fw_spec):
        lepsilon = self.get("lepsilon")

        default_reciprocal_density = 100 if not lepsilon else 200
        other_params = self.get("other_params", {})

        # for lepsilon runs, set EDIFF to 1E-5 unless user says otherwise
        user_incar_settings = self.get("other_params", {}).get("user_incar_settings", {})

        if lepsilon and "EDIFF" not in user_incar_settings and "EDIFF_PER_ATOM" not in user_incar_settings:
            if "user_incar_settings" not in other_params:
                other_params["user_incar_settings"] = {}
            other_params["user_incar_settings"]["EDIFF"] = 1e-5

        vis = MPStaticSet.from_prev_calc(
            prev_calc_dir=self["prev_calc_dir"],
            reciprocal_density=self.get("reciprocal_density", default_reciprocal_density),
            small_gap_multiply=self.get("small_gap_multiply", None),
            standardize=self.get("standardize", False),
            sym_prec=self.get("sym_prec", 0.1),
            international_monoclinic=self.get("international_monoclinic", True),
            lepsilon=lepsilon,
            **other_params
        )
        vis.write_input(".")
Ejemplo n.º 9
0
def wf_bandstructure_no_opt(structure, c=None):

    c = c or {}
    vasp_cmd = c.get("VASP_CMD", VASP_CMD)
    db_file = c.get("DB_FILE", DB_FILE)

    wf = get_wf(
        structure,
        "bandstructure_no_opt.yaml",
        vis=MPStaticSet(structure, force_gamma=True),
        common_params={
            "vasp_cmd": vasp_cmd,
            "db_file": db_file
        },
    )

    wf = add_common_powerups(wf, c)

    if c.get("SMALLGAP_KPOINT_MULTIPLY", SMALLGAP_KPOINT_MULTIPLY):
        wf = add_small_gap_multiply(wf, 0.5, 5, "static")
        wf = add_small_gap_multiply(wf, 0.5, 5, "nscf")

    if c.get("ADD_WF_METADATA", ADD_WF_METADATA):
        wf = add_wf_metadata(wf, structure)

    return wf
Ejemplo n.º 10
0
 def dielectric(self,uc_type='prim',output_dir='./'):
     if uc_type == 'prim':
         uc_type = 'primitive'
         stru = self.stru_prim.copy()
     elif uc_type == 'conv':
         uc_type = 'conventional'
         stru = self.stru_conv.copy()
     path = os.path.join(output_dir,self.name)
     inputs = MPStaticSet(stru).all_input
     transf = {'history':[{'source':self.mpid,'unit_cell':uc_type}],'defect_type':'dielectric'}
     incar = inputs['INCAR']
     kpoints = Kpoints.automatic_gamma_density(stru,2000)
     if self.is_spin_polarized:
         incar['ISPIN']=2
     else:
         incar['ISPIN']=1
     incar['IBRION']=8
     incar['LEPSILON']=True
     incar['LPEAD']=True
     incar['EDIFF']=0.000001
     incar['LWAVE']=False
     incar['LCHARG']=False
     incar['ISMEAR']=0
     incar['ALGO']="Normal"
     incar['SIGMA']=0.01
     del incar['NSW'], incar['LVHAR'], incar['LAECHG']
     os.mkdir(path)
     f=open(path+"/transformations.json",'w')
     f.write(json.dumps(jsanitize(transf)))
     inputs['POTCAR'].write_file(path+"/POTCAR")
     incar.write_file(path+"/INCAR")
     kpoints.write_file(path+"/KPOINTS")
     inputs['POSCAR'].write_file(path+"/POSCAR")
Ejemplo n.º 11
0
    def test_chgcar_db_read(self):
        # add the workflow
        structure = self.struct_si
        # instructs to use db_file set by FWorker, see env_chk
        my_wf = get_wf(structure, "static_only.yaml", vis=MPStaticSet(structure, force_gamma=True),
                       common_params={"vasp_cmd": VASP_CMD,
                                      "db_file": ">>db_file<<"})
        if not VASP_CMD:
            my_wf = use_fake_vasp(my_wf, ref_dirs_si)
        else:
            my_wf = use_custodian(my_wf)

        # set the flags for storing charge densties
        my_wf.fws[0].tasks[-1]["parse_chgcar"] = True
        my_wf.fws[0].tasks[-1]["parse_aeccar"] = True
        self.lp.add_wf(my_wf)

        # run the workflow
        # set the db_file variable
        rapidfire(self.lp, fworker=FWorker(env={"db_file": os.path.join(db_dir, "db.json")}))

        d = self.get_task_collection().find_one()
        self._check_run(d, mode="static")

        wf = self.lp.get_wf_by_fw_id(1)
        self.assertTrue(all([s == 'COMPLETED' for s in wf.fw_states.values()]))

        chgcar_fs_id = d["calcs_reversed"][0]["chgcar_fs_id"]
        accar0_fs_id = d["calcs_reversed"][0]["aeccar0_fs_id"]
        accar2_fs_id = d["calcs_reversed"][0]["aeccar2_fs_id"]

        self.assertTrue(bool(chgcar_fs_id))
        self.assertTrue(bool(accar0_fs_id))
        self.assertTrue(bool(accar2_fs_id))
Ejemplo n.º 12
0
 def elastic_moduli(self,output_dir='./'):
     stru = self.stru_prim.copy()
     inputs = MPStaticSet(stru).all_input
     path = os.path.join(output_dir,self.name)
     transf = {'history':[{'source':self.mpid}],'defect_type':'elastic_moduli'}
     incar = inputs['INCAR']
     if self.is_spin_polarized:
         incar['ISPIN']=2
     else:
         incar['ISPIN']=1
     incar['IBRION']=6
     incar['ISIF'] = 3
     incar['EDIFF'] = 1e-6
     incar['ISMEAR']=0
     incar['POTIM']=0.015
     del incar['NSW'], incar['LVHAR'], incar['LAECHG']
     os.mkdir(path)
     f=open(path+"/transformations.json",'w')
     f.write(json.dumps(jsanitize(transf)))
     enmax = round(max([i.PSCTR['ENMAX'] for i in inputs['POTCAR']])*1.3)
     incar['ENCUT'] = int(enmax)
     inputs['POTCAR'].write_file(path+"/POTCAR")
     incar.write_file(path+"/INCAR")
     inputs['KPOINTS'].write_file(path+"/KPOINTS")
     inputs['POSCAR'].write_file(path+"/POSCAR")
Ejemplo n.º 13
0
def get_wf_bulk_modulus(structure,
                        deformations,
                        vasp_input_set=None,
                        vasp_cmd="vasp",
                        db_file=None,
                        user_kpoints_settings=None,
                        eos="vinet",
                        tag=None,
                        user_incar_settings=None):
    """
    Returns the workflow that computes the bulk modulus by fitting to the given equation of state.

    Args:
        structure (Structure): input structure.
        deformations (list): list of deformation matrices(list of lists).
        vasp_input_set (VaspInputSet): for the static deformation calculations
        vasp_cmd (str): vasp command to run.
        db_file (str): path to the db file.
        user_kpoints_settings (dict): example: {"grid_density": 7000}
        eos (str): equation of state used for fitting the energies and the volumes.
            supported equation of states: "quadratic", "murnaghan", "birch", "birch_murnaghan",
            "pourier_tarantola", "vinet", "deltafactor". See pymatgen.analysis.eos.py
        tag (str): something unique to identify the tasks in this workflow. If None a random uuid
            will be assigned.
        user_incar_settings (dict):

    Returns:
        Workflow
    """

    tag = tag or "bulk_modulus group: >>{}<<".format(str(uuid4()))

    deformations = [Deformation(defo_mat) for defo_mat in deformations]

    vis_static = vasp_input_set or MPStaticSet(
        structure=structure,
        force_gamma=True,
        lepsilon=False,
        user_kpoints_settings=user_kpoints_settings,
        user_incar_settings=user_incar_settings)

    wf_bulk_modulus = get_wf_deformations(structure,
                                          deformations,
                                          name="bulk_modulus deformation",
                                          vasp_input_set=vis_static,
                                          vasp_cmd=vasp_cmd,
                                          db_file=db_file,
                                          tag=tag)

    fw_analysis = Firework(FitEOSToDb(tag=tag, db_file=db_file, eos=eos),
                           name="fit equation of state")

    wf_bulk_modulus.append_wf(Workflow.from_Firework(fw_analysis),
                              wf_bulk_modulus.leaf_fw_ids)

    wf_bulk_modulus.name = "{}:{}".format(
        structure.composition.reduced_formula, "Bulk modulus")

    return wf_bulk_modulus
Ejemplo n.º 14
0
def get_VASP_inputs(input_path, mag_prec=0.1, enum_prec=0.00001):
    init_structure = Structure.from_file(os.path.join(input_path, 'POSCAR'))
    enum_struct_list = MagneticStructureEnumerator(
        init_structure,
        transformation_kwargs={
            'symm_prec': mag_prec,
            'enum_precision_parameter': enum_prec
        })

    for i, magnetic_structure in enumerate(
            enum_struct_list.ordered_structures):
        magnetic_type = enum_struct_list.ordered_structure_origins[i]
        str_id = magnetic_type + str(i)
        vasp_out_path = os.path.join(input_path, 'vasp_inputs', str_id)
        relax_set = MPStaticSet(structure=magnetic_structure)
        relax_set.get_vasp_input().write_input(vasp_out_path)
        create_job_script(vasp_out_path, job_id=str_id)
Ejemplo n.º 15
0
def get_wf_thermal_expansion(structure, deformations, vasp_input_set=None, vasp_cmd="vasp",
                             db_file=None, user_kpoints_settings=None, t_step=10, t_min=0,
                             t_max=1000, mesh=(20, 20, 20), eos="vinet", pressure=0.0,
                             copy_vasp_outputs=False,
                             tag=None):
    """
    Returns quasi-harmonic thermal expansion workflow.
    Note: phonopy package is required for the final analysis step.

    Args:
        structure (Structure): input structure.
        deformations (list): list of deformation matrices(list of lists).
        vasp_input_set (VaspInputSet)
        vasp_cmd (str): vasp command to run.
        db_file (str): path to the db file.
        user_kpoints_settings (dict): example: {"grid_density": 7000}
        t_step (float): temperature step (in K)
        t_min (float): min temperature (in K)
        t_max (float): max temperature (in K)
        mesh (list/tuple): reciprocal space density
        eos (str): equation of state used for fitting the energies and the volumes.
            options supported by phonopy: "vinet", "murnaghan", "birch_murnaghan".
            Note: pymatgen supports more options than phonopy. see pymatgen.analysis.eos.py
        copy_vasp_outputs (bool): whether or not copy the outputs from the previous calc
            (usually structure optimization) before the deformations are performed.
        pressure (float): in GPa
        tag (str): something unique to identify the tasks in this workflow. If None a random uuid
            will be assigned.

    Returns:
        Workflow
    """
    try:
        from phonopy import Phonopy
    except ImportError:
        logger.warning("'phonopy' package NOT installed. Required for the final analysis step.")

    tag = tag or "thermal_expansion group: >>{}<<".format(str(uuid4()))

    deformations = [Deformation(defo_mat) for defo_mat in deformations]

    vis_static = vasp_input_set or MPStaticSet(structure, force_gamma=True, lepsilon=True,
                                               user_kpoints_settings=user_kpoints_settings)
    wf_alpha = get_wf_deformations(structure, deformations, name="thermal_expansion deformation",
                                   vasp_cmd=vasp_cmd, db_file=db_file, tag=tag,
                                   copy_vasp_outputs=copy_vasp_outputs,
                                   vasp_input_set=vis_static)

    fw_analysis = Firework(ThermalExpansionCoeffToDb(tag=tag, db_file=db_file, t_step=t_step,
                                                     t_min=t_min, t_max=t_max, mesh=mesh, eos=eos,
                                                     pressure=pressure),
                           name="Thermal expansion")

    wf_alpha.append_wf(Workflow.from_Firework(fw_analysis), wf_alpha.leaf_fw_ids)

    wf_alpha.name = "{}:{}".format(structure.composition.reduced_formula, "thermal expansion")

    return wf_alpha
Ejemplo n.º 16
0
def generate_new_polarization_folders(structures):
    """
    Generate the polarization calculations (new format) from the completed scf calculation
    """
    for name in structures:
        MPStaticSet.from_prev_calc(name,
                                   user_incar_settings={
                                       "LCALCPOL": True,
                                       "LAECHG": False,
                                       "LVHAR": False,
                                       "ISIF": 2
                                   },
                                   user_kpoints_settings={
                                       "reciprocal_density": 500
                                   }).write_input(
                                       os.path.join(name, 'Berry_new'))
        shutil.copy(os.path.join(name, 'CHGCAR'),
                    os.path.join(name, 'Berry_new'))
Ejemplo n.º 17
0
    def __init__(self,
                 structure,
                 name="static",
                 vasp_input_set=None,
                 vasp_cmd="vasp",
                 prev_calc_loc=True,
                 db_file=None,
                 parents=None,
                 **kwargs):
        """
        Standard static calculation Firework - either from a previous location or from a structure.

        Args:
            structure (Structure): Input structure. Note that for prev_calc_loc jobs, the structure 
                is only used to set the name of the FW and any structure with the same composition 
                can be used.
            name (str): Name for the Firework.
            vasp_input_set (VaspInputSet): input set to use (for jobs w/no parents)
                Defaults to MPStaticSet() if None.
            vasp_cmd (str): Command to run vasp.
            prev_calc_loc (bool or str): If true (default), copies outputs from previous calc. If 
                a str value, grabs a previous calculation output by name. If False/None, will create
                new static calculation using the provided structure.
            db_file (str): Path to file specifying db credentials.
            parents (Firework): Parents of this particular Firework. FW or list of FWS.
            \*\*kwargs: Other kwargs that are passed to Firework.__init__.
        """

        # TODO: @computron - I really don't like how you need to set the structure even for
        # prev_calc_loc jobs. Sometimes it makes appending new FWs to an existing workflow
        # difficult. Maybe think about how to remove this need? -computron

        t = []

        if parents:
            if prev_calc_loc:
                t.append(
                    CopyVaspOutputs(calc_loc=prev_calc_loc,
                                    contcar_to_poscar=True))
            t.append(WriteVaspStaticFromPrev())
        else:
            vasp_input_set = vasp_input_set or MPStaticSet(structure)
            t.append(
                WriteVaspFromIOSet(structure=structure,
                                   vasp_input_set=vasp_input_set))

        t.append(RunVaspCustodian(vasp_cmd=vasp_cmd,
                                  auto_npar=">>auto_npar<<"))
        t.append(PassCalcLocs(name=name))
        t.append(
            VaspToDb(db_file=db_file, additional_fields={"task_label": name}))
        super(StaticFW,
              self).__init__(t,
                             parents=parents,
                             name="{}-{}".format(
                                 structure.composition.reduced_formula, name),
                             **kwargs)
Ejemplo n.º 18
0
    def write_vasp_files_disp(self, incar_path):
        try:
            poscar_list = glob(self.wd + '/POSCAR-[0-9][0-9][0-9]')
            print('{} displacement poscar in total'.format(len(poscar_list)))

            for poscar in poscar_list:
                folder = 'disp-' + poscar.split('-')[-1]
                structure = Poscar.from_file(poscar).structure
                mpset = MPStaticSet(
                    structure,
                    user_kpoints_settings={'reciprocal_density': 250},
                    force_gamma=True)
                mpset.write_input(os.path.join(self.wd, folder))
                p = subprocess.Popen(['cp', incar_path, 'INCAR'],
                                     cwd=os.path.join(self.wd, folder))
                p.wait()
        except:
            print('No displacement poscars')
Ejemplo n.º 19
0
def get_wf_deformations(
    structure,
    deformations,
    name="deformation",
    vasp_input_set=None,
    vasp_cmd="vasp",
    db_file=None,
    tag="",
    copy_vasp_outputs=True,
    metadata=None,
):
    """
    Returns a structure deformation workflow.

    Worfklow consists of: len(deformations) in which the structure is deformed followed
    by a static calculation.

    Args:
        structure (Structure): input structure to be optimized and run
        deformations (list of 3x3 array-likes): list of deformations
        name (str): some appropriate name for the transmuter fireworks.
        vasp_input_set (DictVaspInputSet): vasp input set for static deformed structure
            calculation.
        vasp_cmd (str): command to run
        db_file (str): path to file containing the database credentials.
        tag (str): some unique string that will be appended to the names of the
            fireworks so that the data from those tagged fireworks can be queried later
            during the analysis.
        copy_vasp_outputs (bool): whether or not copy the outputs from the previous calc
            (usually structure optimization) before the transmuter fireworks.
        metadata (dict): meta data

    Returns:
        Workflow
    """
    vasp_input_set = vasp_input_set or MPStaticSet(structure, force_gamma=True)

    fws = []
    for n, deformation in enumerate(deformations):
        fw = TransmuterFW(
            name=f"{tag} {name} {n}",
            structure=structure,
            transformations=["DeformStructureTransformation"],
            transformation_params=[{
                "deformation": deformation.tolist()
            }],
            vasp_input_set=vasp_input_set,
            copy_vasp_outputs=copy_vasp_outputs,
            vasp_cmd=vasp_cmd,
            db_file=db_file,
        )
        fws.append(fw)

    wfname = f"{structure.composition.reduced_formula}:{name}"

    return Workflow(fws, name=wfname, metadata=metadata)
Ejemplo n.º 20
0
def get_wf_deformations(structure,
                        deformations,
                        name="deformation",
                        vasp_input_set=None,
                        vasp_cmd="vasp",
                        db_file=None,
                        tag="",
                        copy_vasp_outputs=True,
                        metadata=None):
    """
    Returns a structure deformation workflow.

    Firework 1 : structural relaxation
    Firework 2 - len(deformations): Deform the optimized structure and run static calculations.


    Args:
        structure (Structure): input structure to be optimized and run
        deformations (list of 3x3 array-likes): list of deformations
        name (str): some appropriate name for the transmuter fireworks.
        vasp_input_set (DictVaspInputSet): vasp input set for static deformed structure calculation.
        vasp_cmd (str): command to run
        db_file (str): path to file containing the database credentials.
        tag (str): some unique string that will be appended to the names of the fireworks so that
            the data from those tagged fireworks can be queried later during the analysis.
        copy_vasp_outputs (bool): whether or not copy the outputs from the previous calc(usually
            structure optimization) before the transmuter fireworks.
        metadata (dict): meta data

    Returns:
        Workflow
    """

    fws, parents = [], []

    vasp_input_set = vasp_input_set or MPStaticSet(structure, force_gamma=True)

    # Deformation fireworks with the task to extract and pass stress-strain appended to it.
    for n, deformation in enumerate(deformations):
        fw = TransmuterFW(name="{} {} {}".format(tag, name, n),
                          structure=structure,
                          transformations=['DeformStructureTransformation'],
                          transformation_params=[{
                              "deformation":
                              deformation.tolist()
                          }],
                          vasp_input_set=vasp_input_set,
                          copy_vasp_outputs=copy_vasp_outputs,
                          parents=parents,
                          vasp_cmd=vasp_cmd,
                          db_file=db_file)
        fws.append(fw)

    wfname = "{}:{}".format(structure.composition.reduced_formula, name)

    return Workflow(fws, name=wfname, metadata=metadata)
Ejemplo n.º 21
0
    def write_vasp_files_dfpt(self, incar_path):
        """
        should run only after tight, proper relaxation

        Write vasp files to a folder named dfpt

        pymatgen inputset may not work very well, so just copy incar from a source
        """
        try:
            relaxed_structure = Poscar.from_file(os.path.join(self.wd, 'relax/CONTCAR')).structure
            supercell = self.generate_structure(relaxed_structure)
            mpset = MPStaticSet(supercell, user_kpoints_settings={'reciprocal_density': 250}, force_gamma=True)
            mpset.write_input(os.path.join(self.wd, self.dfpt_folder))

            p = subprocess.Popen(['cp', incar_path, 'INCAR'], cwd=os.path.join(self.wd, self.dfpt_folder))
            p.wait()

        except:
            print('make sure you have relaxed the structure in tight criteria(ediff 1e-8, ediffg 1e-3')
def Write_MPStatic_KPOINTS(structure_filename="./POSCAR", **kwargs):
    """
    generate KPOINTS for scf cal by pymatgen.io.vasp.set.MPStaticSet.
    input argument:
        -structure_filename: a file that can be understood by pymatgen.Structure.from_file.
    """
    struct = Structure.from_file(structure_filename)
    vis = MPStaticSet(structure=struct, **kwargs)
    folder = os.path.split(structure_filename)[0]
    vis.kpoints.write_file(os.path.join(folder, "KPOINTS"))
Ejemplo n.º 23
0
    def __init__(self, structure=None, name="static", vasp_input_set=None, vasp_input_set_params=None,
                 vasp_cmd=VASP_CMD, prev_calc_loc=True, prev_calc_dir=None, db_file=DB_FILE, vasptodb_kwargs=None,
                 parents=None, **kwargs):
        """
        Standard static calculation Firework - either from a previous location or from a structure.

        Args:
            structure (Structure): Input structure. Note that for prev_calc_loc jobs, the structure
                is only used to set the name of the FW and any structure with the same composition
                can be used.
            name (str): Name for the Firework.
            vasp_input_set (VaspInputSet): input set to use (for jobs w/no parents)
                Defaults to MPStaticSet() if None.
            vasp_input_set_params (dict): Dict of vasp_input_set kwargs.
            vasp_cmd (str): Command to run vasp.
            prev_calc_loc (bool or str): If true (default), copies outputs from previous calc. If
                a str value, retrieves a previous calculation output by name. If False/None, will create
                new static calculation using the provided structure.
            prev_calc_dir (str): Path to a previous calculation to copy from
            db_file (str): Path to file specifying db credentials.
            parents (Firework): Parents of this particular Firework. FW or list of FWS.
            vasptodb_kwargs (dict): kwargs to pass to VaspToDb
            \*\*kwargs: Other kwargs that are passed to Firework.__init__.
        """
        t = []

        vasp_input_set_params = vasp_input_set_params or {}
        vasptodb_kwargs = vasptodb_kwargs or {}
        if "additional_fields" not in vasptodb_kwargs:
            vasptodb_kwargs["additional_fields"] = {}
        vasptodb_kwargs["additional_fields"]["task_label"] = name

        fw_name = "{}-{}".format(structure.composition.reduced_formula if structure else "unknown", name)

        if prev_calc_dir:
            t.append(CopyVaspOutputs(calc_dir=prev_calc_dir, contcar_to_poscar=True))
            t.append(WriteVaspStaticFromPrev(other_params=vasp_input_set_params))
        elif parents:
            if prev_calc_loc:
                t.append(CopyVaspOutputs(calc_loc=prev_calc_loc,
                                         contcar_to_poscar=True))
            t.append(WriteVaspStaticFromPrev(other_params=vasp_input_set_params))
        elif structure:
            vasp_input_set = vasp_input_set or MPStaticSet(structure, **vasp_input_set_params)
            t.append(WriteVaspFromIOSet(structure=structure,
                                        vasp_input_set=vasp_input_set))
        else:
            raise ValueError("Must specify structure or previous calculation")

        t.append(RunVaspCustodian(vasp_cmd=vasp_cmd, auto_npar=">>auto_npar<<"))
        t.append(PassCalcLocs(name=name))
        t.append(
            VaspToDb(db_file=db_file, **vasptodb_kwargs))
        super(StaticFW, self).__init__(t, parents=parents, name=fw_name, **kwargs)
Ejemplo n.º 24
0
    def __init__(self,
                 structure,
                 name="static",
                 previous_structure=False,
                 vasp_input_set=None,
                 vasp_cmd="vasp",
                 db_file=None,
                 parents=None,
                 override_default_vasp_params=None,
                 pass_structure=True,
                 prev_calc_loc=False,
                 **kwargs):
        """
        This Firework is modified from atomate.vasp.fireworks.core.StaticFW to fit the needs of mpmorph
        Standard static calculation Firework - either from a previous location or from a structure.
        Args:
            structure (Structure): Input structure. Note that for prev_calc_loc jobs, the structure
                is only used to set the name of the FW and any structure with the same composition
                can be used.
            name (str): Name for the Firework.
            vasp_input_set (VaspInputSet): input set to use (for jobs w/no parents)
                Defaults to MPStaticSet() if None.
            vasp_cmd (str): Command to run vasp.
            prev_calc_loc (bool or str): If true (default), copies outputs from previous calc. If
                a str value, grabs a previous calculation output by name. If False/None, will create
                new static calculation using the provided structure.
            db_file (str): Path to file specifying db credentials.
            parents (Firework): Parents of this particular Firework. FW or list of FWS.
            \*\*kwargs: Other kwargs that are passed to Firework.__init__.
        """

        t = []
        override_default_vasp_params = override_default_vasp_params or {}
        vasp_input_set = vasp_input_set or MPStaticSet(
            structure, **override_default_vasp_params)
        if prev_calc_loc:
            t.append(
                CopyVaspOutputs(calc_loc=prev_calc_loc,
                                contcar_to_poscar=True))
        t.append(
            WriteVaspFromIOSet(structure=structure,
                               vasp_input_set=vasp_input_set))
        if previous_structure:
            t.append(PreviousStructureTask())
        t.append(RunVaspCustodian(vasp_cmd=vasp_cmd,
                                  auto_npar=">>auto_npar<<"))
        t.append(SaveStructureTask())
        t.append(PassCalcLocs(name=name))
        t.append(
            VaspToDb(db_file=db_file, additional_fields={"task_label": name}))
        name = f'{structure.composition.reduced_formula}-{name}'
        super(StaticFW, self).__init__(t, parents=parents, name=name, **kwargs)
Ejemplo n.º 25
0
 def run_task(self, fw_spec):
     material_id = self["material_id"]
     dest_root = fw_spec["_fw_en"]["run_dest_root"]
     dest = "{}/{}/bs/{}/relax".format(dest_root, os.environ["USER"],
                                       material_id)
     user_incar_settings = fw_spec.get("user_incar_settings", {})
     vasp_input_set = MPStaticSet.from_prev_calc(
         prev_calc_dir=dest,
         standardize=1e-3,
         user_incar_settings=user_incar_settings)
     dec = MontyDecoder()
     vis = dec.process_decoded(vasp_input_set.as_dict())
     vis.write_input(".")
Ejemplo n.º 26
0
def generate_scf_folders(structures, user_incar):
    """
    Generate calculations from the structures dictionary 
    """
    for name in structures:
        if os.path.exists(name) == False:
            os.mkdir(name)
        structures[name].to(fmt='POSCAR', filename='/'.join([name, 'POSCAR']))
        MPStaticSet(structures[name],
                    user_incar_settings=user_incar,
                    user_kpoints_settings={
                        "reciprocal_density": 500
                    }).write_input(name)
        print(name + '\n')
Ejemplo n.º 27
0
def wf_static(structure, c=None):

    c = c or {}
    vasp_cmd = c.get("VASP_CMD", VASP_CMD)
    db_file = c.get("DB_FILE", DB_FILE)

    wf = get_wf(structure, "static_only.yaml", vis=MPStaticSet(structure),
                common_params={"vasp_cmd": vasp_cmd, "db_file": db_file})

    wf = add_common_powerups(wf, c)

    if c.get("ADD_WF_METADATA", ADD_WF_METADATA):
        wf = add_wf_metadata(wf, structure)

    return wf
Ejemplo n.º 28
0
 def run_task(self, fw_spec):
     self.user_incar_settings.update({"NPAR": 2})
     # Get kpoint density per vol
     vol = Poscar.from_file("POSCAR").structure.volume
     kppra_vol = self.kpoints_density / vol
     new_set = MPStaticSet.from_prev_calc(
         os.getcwd(),
         user_incar_settings=self.user_incar_settings, 
         reciprocal_density=kppra_vol)
     new_set.write_input('.')
     structure = new_set.structure
     sga = SpacegroupAnalyzer(structure, 0.1)
     return FWAction(stored_data={
         'refined_structure': sga.get_refined_structure().as_dict(),
         'conventional_standard_structure': sga.get_conventional_standard_structure().as_dict(),
         'symmetry_dataset': sga.get_symmetry_dataset(),
         'symmetry_operations': [x.as_dict() for x in sga.get_symmetry_operations()]})
Ejemplo n.º 29
0
def wf_elastic_constant(structure, c=None, order=2, sym_reduce=False):

    c = c or {}
    vasp_cmd = c.get("VASP_CMD", VASP_CMD)
    db_file = c.get("DB_FILE", DB_FILE)

    uis_optimize = {"ENCUT": 700, "EDIFF": 1e-6, "LAECHG": False}
    if order > 2:
        uis_optimize.update({"EDIFF": 1e-10, "EDIFFG": -0.001,
                             "ADDGRID": True, "LREAL": False, "ISYM": 0})
        # This ensures a consistent k-point mesh across all calculations
        # We also turn off symmetry to prevent VASP from changing the
        # mesh internally
        kpts_settings = Kpoints.automatic_density(structure, 40000, force_gamma=True)
        stencils = np.linspace(-0.075, 0.075, 7)
    else:
        kpts_settings = {'grid_density': 7000}
        stencils = None

    uis_static = uis_optimize.copy()
    uis_static.update({'ISIF': 2, 'IBRION': 2, 'NSW': 99, 'ISTART': 1, "PREC": "High"})

    # input set for structure optimization
    vis_relax = MPRelaxSet(structure, force_gamma=True, user_incar_settings=uis_optimize,
                           user_kpoints_settings=kpts_settings)

    # optimization only workflow
    wf = get_wf(structure, "optimize_only.yaml", vis=vis_relax,
                params=[{"vasp_cmd": vasp_cmd,  "db_file": db_file,
                         "name": "elastic structure optimization"}])

    vis_static = MPStaticSet(structure, force_gamma=True, lepsilon=False,
                             user_kpoints_settings=kpts_settings,
                             user_incar_settings=uis_static)

    # deformations wflow for elasticity calculation
    wf_elastic = get_wf_elastic_constant(structure, vasp_cmd=vasp_cmd, db_file=db_file,
                                         order=order, stencils=stencils, copy_vasp_outputs=True,
                                         vasp_input_set=vis_static, sym_reduce=sym_reduce)
    wf.append_wf(wf_elastic, wf.leaf_fw_ids)

    wf = add_common_powerups(wf, c)
    if c.get("ADD_WF_METADATA", ADD_WF_METADATA):
        wf = add_wf_metadata(wf, structure)

    return wf
Ejemplo n.º 30
0
    def setUp(self):
        coords = list()
        coords.append([0, 0, 0])
        coords.append([0.75, 0.5, 0.75])
        lattice = [
            [3.8401979337, 0.00, 0.00],
            [1.9200989668, 3.3257101909, 0.00],
            [0.00, -2.2171384943, 3.1355090603],
        ]

        structure = Structure(lattice, ["Si", "Si"], coords)

        input_sets = {
            "GGA Structure Optimization": MPRelaxSet(structure),
            "GGA Static": MPStaticSet(structure),
            "GGA NSCF Line": MPNonSCFSet(structure, mode="line"),
            "GGA NSCF Uniform": MPNonSCFSet(structure, mode="uniform"),
        }

        tasks = []
        t_id = 1
        for task_type, input_set in input_sets.items():
            doc = {
                "true_task_type": task_type,
                "last_updated": datetime.now(),
                "task_id": t_id,
                "state": "successful",
                "orig_inputs": {
                    "incar": input_set.incar.as_dict(),
                    "kpoints": input_set.kpoints.as_dict(),
                },
                "output": {
                    "structure": structure.as_dict()
                },
            }
            t_id += 1
            tasks.append(doc)

        self.test_tasks = MemoryStore("tasks")
        self.task_types = MemoryStore("task_types")
        self.test_tasks.connect()
        self.task_types.connect()

        self.test_tasks.update(tasks)
Ejemplo n.º 31
0
    def __init__(self,
                 structure,
                 transformations,
                 transformation_params=None,
                 vasp_input_set=None,
                 prev_calc_dir=None,
                 name="structure transmuter",
                 vasp_cmd=VASP_CMD,
                 copy_vasp_outputs=True,
                 db_file=DB_FILE,
                 parents=None,
                 override_default_vasp_params=None,
                 **kwargs):
        """
        Apply the transformations to the input structure, write the input set corresponding
        to the transformed structure, and run vasp on them.  Note that if a transformation yields 
        many structures from one, only the last structure in the list is used.

        Args:
            structure (Structure): Input structure.
            transformations (list): list of names of transformation classes as defined in
                the modules in pymatgen.transformations.
                eg:  transformations=['DeformStructureTransformation', 'SupercellTransformation']
            transformation_params (list): list of dicts where each dict specify the input 
                parameters to instantiate the transformation class in the transformations list.
            vasp_input_set (VaspInputSet): VASP input set, used to write the input set for the
                transmuted structure.
            name (string): Name for the Firework.
            vasp_cmd (string): Command to run vasp.
            copy_vasp_outputs (bool): Whether to copy outputs from previous run. Defaults to True.
            prev_calc_dir (str): Path to a previous calculation to copy from
            db_file (string): Path to file specifying db credentials.
            parents (Firework): Parents of this particular Firework. FW or list of FWS.
            override_default_vasp_params (dict): additional user input settings for vasp_input_set.
            \*\*kwargs: Other kwargs that are passed to Firework.__init__.
        """
        fw_name = "{}-{}".format(structure.composition.reduced_formula, name)
        override_default_vasp_params = override_default_vasp_params or {}
        t = []

        vasp_input_set = vasp_input_set or MPStaticSet(
            structure, force_gamma=True, **override_default_vasp_params)

        if prev_calc_dir:
            t.append(
                CopyVaspOutputs(calc_dir=prev_calc_dir,
                                contcar_to_poscar=True))
            t.append(
                WriteTransmutedStructureIOSet(
                    transformations=transformations,
                    transformation_params=transformation_params,
                    vasp_input_set=vasp_input_set,
                    override_default_vasp_params=override_default_vasp_params,
                    prev_calc_dir="."))
        elif copy_vasp_outputs:
            t.append(CopyVaspOutputs(calc_loc=True, contcar_to_poscar=True))
            t.append(
                WriteTransmutedStructureIOSet(
                    structure=structure,
                    transformations=transformations,
                    transformation_params=transformation_params,
                    vasp_input_set=vasp_input_set,
                    override_default_vasp_params=override_default_vasp_params,
                    prev_calc_dir="."))
        elif structure:
            t.append(
                WriteTransmutedStructureIOSet(
                    structure=structure,
                    transformations=transformations,
                    transformation_params=transformation_params,
                    vasp_input_set=vasp_input_set,
                    override_default_vasp_params=override_default_vasp_params))
        else:
            raise ValueError("Must specify structure or previous calculation")

        t.append(RunVaspCustodian(vasp_cmd=vasp_cmd))
        t.append(PassCalcLocs(name=name))
        t.append(
            VaspToDb(db_file=db_file,
                     additional_fields={
                         "task_label": name,
                         "transmuter": {
                             "transformations": transformations,
                             "transformation_params": transformation_params
                         }
                     }))

        super(TransmuterFW, self).__init__(t,
                                           parents=parents,
                                           name=fw_name,
                                           **kwargs)
Ejemplo n.º 32
0
def get_jobs(args):
    # Returns a generator of jobs. Allows of "infinite" jobs.
    vasp_command = args.command.split()
    # save initial INCAR for rampU runs
    n_ramp_u = args.jobs.count('rampU')
    ramps = 0
    if n_ramp_u:
        incar = Incar.from_file('INCAR')
        ldauu = incar['LDAUU']
        ldauj = incar['LDAUJ']

    njobs = len(args.jobs)
    post_settings = []  # append to this list to have settings applied on next job
    for i, job in enumerate(args.jobs):
        final = False if i != njobs - 1 else True
        if any(c.isdigit() for c in job):
            suffix = "." + job
        else:
            suffix = ".{}{}".format(job, i + 1)
        settings = post_settings
        post_settings = []
        backup = True if i == 0 else False
        copy_magmom = False
        vinput = VaspInput.from_directory(".")
        if i > 0:
            settings.append(
                {"file": "CONTCAR",
                 "action": {"_file_copy": {"dest": "POSCAR"}}})

        job_type = job.lower()
        auto_npar = True

        if args.no_auto_npar:
            auto_npar = False

        if job_type.startswith("static_derived"):
            from pymatgen.io.vasp.sets import MPStaticSet
            vis = MPStaticSet.from_prev_calc(
                ".", user_incar_settings={"LWAVE": True, "EDIFF": 1e-6},
                ediff_per_atom=False)
            settings.extend([
                {"dict"  : "INCAR",
                 "action": {"_set": dict(vis.incar)}},
                {'dict': 'KPOINTS',
                 'action': {'_set': vis.kpoints.as_dict()}}])

        if job_type.startswith("static_dielectric_derived"):
            from pymatgen.io.vasp.sets import MPStaticSet, MPStaticDielectricDFPTVaspInputSet

            # vis = MPStaticSet.from_prev_calc(
            #     ".", user_incar_settings={"EDIFF": 1e-6, "IBRION": 8,
            #                               "LEPSILON": True, 'LREAL':False,
            #                               "LPEAD": True, "ISMEAR": 0,
            #                               "SIGMA": 0.01},
            #     ediff_per_atom=False)
            vis = MPStaticDielectricDFPTVaspInputSet()
            incar = vis.get_incar(vinput["POSCAR"].structure)
            unset = {}
            for k in ["NPAR", "KPOINT_BSE", "LAECHG", "LCHARG", "LVHAR",
                      "NSW"]:
                incar.pop(k, None)
                if k in vinput["INCAR"]:
                    unset[k] = 1
            kpoints = vis.get_kpoints(vinput["POSCAR"].structure)
            settings.extend([
                {"dict": "INCAR",
                 "action": {"_set": dict(incar),
                            "_unset": unset}},
                {'dict': 'KPOINTS',
                 'action': {'_set': kpoints.as_dict()}}])
            auto_npar = False
        elif job_type.startswith("static"):
            m = [i * args.static_kpoint for i in vinput["KPOINTS"].kpts[0]]
            settings.extend([
                {"dict": "INCAR",
                 "action": {"_set": {"NSW": 0}}},
                {'dict': 'KPOINTS',
                 'action': {'_set': {'kpoints': [m]}}}])

        elif job_type.startswith("nonscf_derived"):
            from pymatgen.io.vasp.sets import MPNonSCFSet
            vis = MPNonSCFSet.from_prev_calc(".", copy_chgcar=False,
                                             user_incar_settings={"LWAVE": True})
            settings.extend([
                {"dict": "INCAR",
                 "action": {"_set": dict(vis.incar)}},
                {'dict': 'KPOINTS',
                 'action': {'_set': vis.kpoints.as_dict()}}])

        elif job_type.startswith("optics_derived"):
            from pymatgen.io.vasp.sets import MPNonSCFSet
            vis = MPNonSCFSet.from_prev_calc(
                ".", optics=True, copy_chgcar=False,
                nedos=2001, mode="uniform", nbands_factor=5,
                user_incar_settings={"LWAVE": True, "ALGO": "Exact", "SIGMA": 0.01, "EDIFF": 1e-6},
                ediff_per_atom=False)
            settings.extend([
                {"dict": "INCAR",
                 "action": {"_set": dict(vis.incar)}},
                {'dict': 'KPOINTS',
                 'action': {'_set': vis.kpoints.as_dict()}}])

        elif job_type.startswith("rampu"):
            f = ramps / (n_ramp_u - 1)
            settings.append(
                {"dict": "INCAR",
                 "action": {"_set": {"LDAUJ": [j * f for j in ldauj],
                                     "LDAUU": [u * f for u in ldauu]}}})
            copy_magmom = True
            ramps += 1
        elif job_type.startswith("quick_relax") or job_type.startswith(\
                "quickrelax"):
            kpoints = vinput["KPOINTS"]
            incar = vinput["INCAR"]
            structure = vinput["POSCAR"].structure
            if "ISMEAR" in incar:
                post_settings.append(
                    {"dict": "INCAR",
                     "action": {"_set": {"ISMEAR": incar["ISMEAR"]}}})
            else:
                post_settings.append(
                    {"dict": "INCAR",
                     "action": {"_unset": {"ISMEAR": 1}}})
            post_settings.append({"dict": "KPOINTS",
                                  "action": {"_set": kpoints.as_dict()}})
            # lattice vectors with length < 9 will get >1 KPOINT
            low_kpoints = Kpoints.gamma_automatic(
                [max(int(18/l), 1) for l in structure.lattice.abc])
            settings.extend([
                {"dict": "INCAR",
                 "action": {"_set": {"ISMEAR": 0}}},
                {'dict': 'KPOINTS',
                 'action': {'_set': low_kpoints.as_dict()}}])

            # let vasp determine encut (will be lower than
            # needed for compatibility with other runs)
            if "ENCUT" in incar:
                post_settings.append(
                    {"dict": "INCAR",
                     "action": {"_set": {"ENCUT": incar["ENCUT"]}}})
                settings.append(
                    {"dict": "INCAR",
                     "action": {"_unset": {"ENCUT": 1}}})

        elif job_type.startswith("relax"):
            pass
        elif job_type.startswith("full_relax"):
            for j in VaspJob.full_opt_run(
                    vasp_command):
                yield j
        else:
            print("Unsupported job type: {}".format(job))
            sys.exit(-1)

        if not job_type.startswith("full_relax"):
            yield VaspJob(vasp_command, final=final, suffix=suffix,
                          backup=backup, settings_override=settings,
                          copy_magmom=copy_magmom, auto_npar=auto_npar)