コード例 #1
0
    def _parser_function(self):
        parser_warnings = {}  # for compatibility

        try:
            errfile = self._params['SCHED_ERROR_FILE']
            errfile = self._out_folder.get_abs_path(errfile)
        except KeyError:
            raise OutputParsingError(
                "{} expects the SCHED_ERROR_FILE to "
                "be provided as a parameter.".format(
                    self.__class__.__name__)
            )
        except OSError:
            raise OutputParsingError(
                "SCHED_ERROR_FILE ({}/{}) not found !".format(
                    self._out_folder.get_abs_path(),
                    self._params['SCHED_ERROR_FILE']
                )
            )

        # === parse errors & warnings ===
        # just a text blob --> no way to parse things more cleanly ?!!
        with open(errfile, 'r') as f:
            errors = f.read()
        # use if/else to make things more explicit
        if errors:
            errors = ParameterData(dict={'runtime_errors': errors})
        else:
            errors = ParameterData(dict={'runtime_errors': None})

        # return [('runtime_errors', errors), ('bad.key', errors)], parser_warnings  # for debug
        return [('runtime_errors', errors)], parser_warnings
コード例 #2
0
ファイル: __init__.py プロジェクト: kjappelbaum/aiida-raspa
    def __init__(self, calc):
        """Initialize the instance of RaspaParser."""
        super(RaspaParser, self).__init__(calc)

        # check for valid input
        if not isinstance(calc, RaspaCalculation):
            raise OutputParsingError("Input calc must be a RaspaCalculation")
コード例 #3
0
    def _parser_function(self):
        """
        Parses the vasprun.xml using the Pymatgen Vasprun function.
        """

        vasp_param = {}  # ParameterData

        parser_warnings = {}  # return non-critical errors

        vspr = vasp.Vasprun(self._out_folder.get_abs_path('vasprun.xml'),
                            exception_on_bad_xml=False)
        # vasp_param['final_energy'] = vspr.final_energy  # This includes PV
        vasp_param['energy'] = vspr.ionic_steps[-1]['electronic_steps'][-1][
            'e_wo_entrp']  # Pure internal energy (U) as appear in OUTCAR

        # construct proper output format
        try:
            nodes_list = []
            parameter_data = ParameterData(dict=vasp_param)
            nodes_list.append(('output_parameters', parameter_data))
        except Exception, e:
            msg = ("Failed to create AiiDA data structures "
                   "(ParameterData/ArrrayData) from parsed data, "
                   "with error message:\n>> {}".format(e))
            raise OutputParsingError(msg)
コード例 #4
0
    def _parser_function(self):
        """
        Parses the XDATCAR using custom function.
        """

        parser_warnings = {}  # return non-critical errors

        timestep = self._calc.inp.incar.dict.NSW * 1e-3  # In picoseconds

        # extract data
        try:
            step_ids, positions, time, cells, symbols = read_VASP_XDATCAR(
                self._out_folder.get_abs_path('XDATCAR'), timestep)
        except:
            print('Error parsing XDATCAR')

        #  construct proper trajectory data format
        trajectory_data = TrajectoryData()
        try:
            nodes_list = []
            trajectory_data.set_trajectory(step_ids,
                                           cells,
                                           symbols,
                                           positions,
                                           times=time)
            nodes_list.append(('trajectory_data', trajectory_data))
        except Exception, e:
            msg = ("Failed to create AiiDA data structures "
                   "(ParameterData/ArrrayData) from parsed data, "
                   "with error message:\n>> {}".format(e))
            raise OutputParsingError(msg)
コード例 #5
0
    def _parser_function(self):
        """
        Parses the vasprun.xml.
        """

        # Get born charges and epsilon
        nodes_list = []
        array_data = ArrayData()

        try:
            import xml.etree.cElementTree as ET

            tree = ET.parse(self._out_folder.get_abs_path('vasprun.xml'))
            root = tree.getroot()

            for elements in root.iter('varray'):
                if elements.attrib['name'] == 'epsilon':
                    epsilon = []
                    for row in elements:
                        epsilon.append(np.array(row.text.split(), dtype=float))

                    epsilon = np.array(epsilon)
                    array_data.set_array('epsilon', epsilon)
                    break

            for elements in root.iter('array'):
                try:
                    if elements.attrib['name'] == 'born_charges':
                        born_charges = []
                        for atom in elements[1:]:
                            atom_array = []
                            for c in atom:
                                atom_array.append(
                                    np.array(c.text.split(), dtype=float))
                            born_charges.append(atom_array)

                        born_charges = np.array(born_charges)
                        array_data.set_array('born_charges', born_charges)

                        break
                except KeyError:
                    pass
        except:
            pass

        # Use pymatgen vasp parser to get atomic forces and stress tensor

        vspr = Vasprun(self._out_folder.get_abs_path('vasprun.xml'),
                       exception_on_bad_xml=False)

        # Get forces using pymatgen
        try:
            forces = np.array([vspr.ionic_steps[-1]['forces']])
            array_data.set_array('forces', forces)

        except Exception, e:
            msg = ("Processing forces, "
                   "with error Message:\n>> {}".format(e))
            raise OutputParsingError(msg)
コード例 #6
0
    def __init__(self, calculation):
        from .calculations import Wannier90Calculation

        # check for valid input
        if not isinstance(calculation, Wannier90Calculation):
            raise OutputParsingError("Input must calc must be a "
                                     "Wannier90Calculation")
        super(Wannier90Parser, self).__init__(calculation)
コード例 #7
0
 def __init__(self,calculation):
     """
     Initialize the instance of AseParser
     """
     # check for valid input
     if not isinstance(calculation,AseCalculation):
         raise OutputParsingError("Input calculation must be a AseCalculation")
     self._calc = calculation
コード例 #8
0
ファイル: network.py プロジェクト: yakutovicha/aiida-zeopp
    def __init__(self, calculation):
        """
        Initialize Parser instance
        """
        super(NetworkParser, self).__init__(calculation)

        # check for valid input
        if not isinstance(calculation, NetworkCalculation):
            raise OutputParsingError("Can only parse NetworkCalculation")
コード例 #9
0
ファイル: ape.py プロジェクト: bosonie/aiida-ape
 def __init__(self, calculation):
     #        """
     #        Initialize Parser instance
     #        """
     super(ApeParser, self).__init__(calculation)
     #
     #        # check for valid input
     if not isinstance(calculation, ApeCalculation):
         raise OutputParsingError("Can only parse ApeCalculation")
コード例 #10
0
 def __init__(self, calculation):
     '''
     initializes with a Calculation object
     '''
     super(VaspParser, self).__init__(calculation)
     if not isinstance(calculation, VaspCalculation):
         raise OutputParsingError(
             'Input calculation must be a VaspCalculation')
     self._calc = calculation
コード例 #11
0
    def parse_chi(self, filepath):
        """
        Parse the contents of the file {prefix}.chi.dat as written by a HpCalculation

        :param filepath: absolute filepath to the chi.dat output file
        :returns: dictionary with parsed contents
        """
        try:
            with open(filepath, 'r') as handle:
                data = handle.readlines()
        except IOError as exception:
            raise OutputParsingError(
                "could not read the '{}' output file".format(
                    os.path.basename(filepath)))

        result = {}
        blocks = {
            'chi0': [None, None],
            'chi1': [None, None],
        }

        for line_number, line in enumerate(data):
            if 'chi0' in line:
                blocks['chi0'][0] = line_number + 1

            if 'chi1' in line:
                blocks['chi0'][1] = line_number
                blocks['chi1'][0] = line_number + 1
                blocks['chi1'][1] = len(data)
                break

        if not all(sum(blocks.values(), [])):
            raise OutputParsingError(
                "could not determine beginning and end of all blocks in '{}'".
                format(os.path.basename(filepath)))

        for matrix_name in ('chi0', 'chi1'):
            matrix_block = blocks[matrix_name]
            matrix_data = data[matrix_block[0]:matrix_block[1]]
            matrix = numpy.matrix(self.parse_hubbard_matrix(matrix_data))
            result[matrix_name] = matrix

        return result
コード例 #12
0
ファイル: rips.py プロジェクト: vishalbelsare/aiida-gudhi
    def __init__(self, calculation):
        """
        Initialize Parser instance
        """
        super(RipsParser, self).__init__(calculation)

        # check for valid input
        if not isinstance(calculation, RipsDistanceMatrixCalculation):
            raise OutputParsingError(
                "Can only parse RipsDistanceMatrixCalculation")
コード例 #13
0
 def __init__(self,calculation):
     """
     Initialize the instance of ShirleyParser
     """
     # check for valid input
     if not isinstance(calculation,ShirleyCalculation):
         raise OutputParsingError("Input calculation must be a "
                                  "ShirleyCalculation")
     super(ShirleyParser, self).__init__(calculation)
     
     self._eps_re_array_linkname = 'array_eps_re'
     self._eps_im_array_linkname = 'array_eps_im'
コード例 #14
0
    def _parser_function(self):
        """
        Parses CONTCAR/POSCAR file.

        :output_structure: name of the structure file; must be specified in
        parameters list.
        """
        parser_warnings = {}  # return non-critical errors
        nodes_list = []

        try:
            ofile = self._params['OUTPUT_STRUCTURE']
            out_structure = self._out_folder.get_abs_path(ofile)
            out_structure = vasp.Poscar.from_file(out_structure)
            out_structure = disassemble_poscar(out_structure)
        except KeyError:
            raise OutputParsingError(
                "Output structure file was not specified in params!")
        except OSError:
            raise OutputParsingError(
                "Output structure file ({}/{}) not found!".format(
                    self.out_folder.get_abs_path(), ofile))
        except Exception as e:
            raise OutputParsingError("Parsing of output structure failed! "
                                     "Error: {}".format(e))

        # Small hack to change name of output structure node to be consistent with QE plugin
        out_structure['output_structure'] = out_structure.pop('structure')
        for item in out_structure:
            nodes_list.append((item, out_structure[item]))

        if not nodes_list:
            parser_warnings.setdefault(
                'Returning empty node list.',
                'Parsing of the output structure may have quietly failed!')

        if not parser_warnings:
            parser_warnings = None

        return nodes_list, parser_warnings
コード例 #15
0
    def __init__(self, calculation):
        """
        Initialize Parser instance
        """
        CryBasicCalculation = CalculationFactory('crystal17.basic')
        CryMainCalculation = CalculationFactory('crystal17.main')
        # check for valid input
        if not isinstance(calculation,
                          (CryBasicCalculation, CryMainCalculation)):
            raise OutputParsingError(
                "Can only parse CryBasicCalculation or CryMainCalculation")

        super(CryBasicParser, self).__init__(calculation)
コード例 #16
0
ファイル: __init__.py プロジェクト: ltalirz/aiida-cp2k
    def _parse_stdout(self, out_folder, new_nodes_list):
        fn = self._calc._OUTPUT_FILE_NAME
        if fn not in out_folder.get_folder_list():
            raise OutputParsingError("Cp2k output file not retrieved")

        result_dict = {'exceeded_walltime': False}
        abs_fn = out_folder.get_abs_path(fn)
        with open(abs_fn, "r") as f:
            for line in f.readlines():
                if line.startswith(' ENERGY| '):
                    result_dict['energy'] = float(line.split()[8])
                    result_dict['energy_units'] = "a.u."
                if 'The number of warnings for this run is' in line:
                    result_dict['nwarnings'] = int(line.split()[-1])
                if 'exceeded requested execution time' in line:
                    result_dict['exceeded_walltime'] = True

        if 'nwarnings' not in result_dict:
            raise OutputParsingError("CP2K did not finish properly.")

        pair = ('output_parameters', ParameterData(dict=result_dict))
        new_nodes_list.append(pair)
コード例 #17
0
    def _parser_function(self):
        """
        Parses the vasprun.xml using the Pymatgen Vasprun function.
        """

        vasp_param = {}  # ParameterData
        vasp_array = {}  # ArrayData

        parser_warnings = {}  # return non-critical errors

        # parameter data keys
        _vasprun_keys = [  # directly accessible, by name
            # logical
            'converged',
            'converged_electronic',
            'converged_ionic',
            'dos_has_errors',
            'is_spin',
            'is_hubbard',
            # value
            'efermi'
        ]
        _vasprun_special_keys = [  # can't be accessed directly
            # logical
            'is_band_gap_direct',
            # value
            'no_ionic_steps',
            'final_energy',  # returned as FloatWithUnit
            'energy_units',
            'free_energy',
            'energy_wo_entropy',
            'energy_T0',
            'entropy_TS',
            'no_electronic_steps',
            'total_no_electronic_steps',
            'band_gap',
            'cbm',
            'vbm',
        ]

        # array data keys
        # TODO
        # list --> array; see what exactly ArrayData supports

        # parsing output files
        try:
            vspr = vasp.Vasprun(self._out_folder.get_abs_path('vasprun.xml'))
        except Exception, e:
            msg = ("Parsing vasprun file in pymatgen failed, "
                   "with error message:\n>> {}".format(e))
            raise OutputParsingError(msg)
コード例 #18
0
class Custom_vasprun_parserInstruction(BaseInstruction):

    _input_file_list_ = ['vasprun.xml', 'OUTCAR']

    def _parser_function(self):
        """
        Parses the vasprun.xml using the Pymatgen Vasprun function.
        """
        vasp_param = {}  # ParameterData

        parser_warnings = {}  # return non-critical errors

        # extract data
        try:
            with open(self._out_folder.get_abs_path('OUTCAR'), 'r') as f:
                text = f.readlines()
        except:
            print('Error opening')

        try:
            vspr = vasp.Vasprun(self._out_folder.get_abs_path('vasprun.xml'))
            vasp_param['energy'] = vspr.final_energy
#            vasp_param['volume'] = vspr.final_structure.lattice.volume  #Not here!, not necessary

        except Exception, e:
            msg = ("Parsing vasprun file in pymatgen failed, "
                   "with error message:\n>> {}".format(e))
            raise OutputParsingError(msg)

        # Get forces using phonopy functions
        try:
            force = vasp_phonopy._get_forces_vasprun_xml(
                vasp_phonopy._iterparse(
                    self._out_folder.get_abs_path('vasprun.xml'),
                    tag='varray'))

            vasp_param['atomic_force'] = force.tolist()

        except Exception, e:
            msg = ("Processing of extracted data failed, "
                   "with error Message:\n>> {}".format(e))
            raise OutputParsingError(msg)
コード例 #19
0
    def __init__(self, calculation):
        """Initialize the instance of YamboParser"""
        from aiida.common import aiidalogger
        self._logger = aiidalogger.getChild('parser').getChild(
            self.__class__.__name__)
        # check for valid input
        if not isinstance(calculation, YamboCalculation):
            raise OutputParsingError(
                "Input calculation must be a YamboCalculation")
        self._calc = calculation

        self._eels_array_linkname = 'array_eels'
        self._eps_array_linkname = 'array_eps'
        self._alpha_array_linkname = 'array_alpha'
        self._qp_array_linkname = 'array_qp'
        self._ndb_linkname = 'array_ndb'
        self._ndb_QP_linkname = 'array_ndb_QP'
        self._ndb_HF_linkname = 'array_ndb_HFlocXC'
        self._lifetime_bands_linkname = 'bands_lifetime'
        self._quasiparticle_bands_linkname = 'bands_quasiparticle'
        self._parameter_linkname = 'output_parameters'
        super(YamboParser, self).__init__(calculation)
コード例 #20
0
    def _parser_function(self):
        """
        Parses the vasprun.xml using the Pymatgen Vasprun function.
        """
        vasp_param = {}  # ParameterData

        parser_warnings = {}  # return non-critical errors

        # extract data
        try:
            with open(self._out_folder.get_abs_path('OUTCAR'), 'r') as f:
                text = f.readlines()
        except:
            print('Error opening')

        try:
            vspr = vasp.Vasprun(self._out_folder.get_abs_path('vasprun.xml'))
            vasp_param['energy'] = vspr.final_energy
#            vasp_param['volume'] = vspr.final_structure.lattice.volume  #Not here!, not necessary

        except Exception, e:
            msg = ("Parsing vasprun file in pymatgen failed, "
                   "with error message:\n>> {}".format(e))
            raise OutputParsingError(msg)
コード例 #21
0
def create_inputs(inpath, outpath):
    """ create ``crystal17.main`` input nodes from an existing run

    NB: none of the nodes are stored, also
    existing basis will be retrieved if availiable

    :param inpath: path to .d12 file
    :param outpath: path to .out file
    :return: dictionary of inputs, with keys 'structure', 'parameters', 'settings', 'structure', 'basis'
    """
    from aiida.orm import DataFactory, CalculationFactory
    calc_cls = CalculationFactory('crystal17.main')
    basis_cls = DataFactory('crystal17.basisset')
    struct_cls = DataFactory('structure')
    structsettings_cls = DataFactory('crystal17.structsettings')

    inputs = {}

    with open(inpath) as f:
        d12content = f.read()

    output_dict, basis_sets, atom_props = extract_data(d12content)

    cryparse = CrystalOutputPlugin()
    if not os.path.exists(outpath):
        raise OutputParsingError(
            "The raw data file does not exist: {}".format(outpath))
    with open(outpath) as f:
        try:
            data = cryparse.read_file(f, log_warnings=False)
        except IOError as err:
            raise OutputParsingError(
                "Error in CRYSTAL 17 run output: {}".format(err))

    # we retrieve the initial primitive geometry and symmetry
    atoms = _create_atoms(data)

    # convert fragment (i.e. unfixed) to fixed
    if "fragment" in atom_props:
        frag = atom_props.pop("fragment")
        atom_props["fixed"] = [
            i + 1 for i in range(atoms.get_number_of_atoms())
            if i + 1 not in frag
        ]

    atoms.set_tags(_create_tags(atom_props, atoms))

    structure = struct_cls(ase=atoms)
    inputs['structure'] = structure

    settings_dict = {"kinds": {}}
    for key, vals in atom_props.items():
        settings_dict["kinds"][key] = [
            structure.sites[i - 1].kind_name for i in vals
        ]

    settings_dict["operations"] = data["initial"]["primitive_symmops"]
    # TODO retrieve centering code, crystal system and spacegroup
    settings_dict["space_group"] = 1
    settings_dict["crystal_type"] = 1
    settings_dict["centring_code"] = 1
    settings = structsettings_cls(data=settings_dict)

    parameters = calc_cls.prepare_and_validate(output_dict, structure,
                                               settings)
    inputs['parameters'] = parameters
    inputs['settings'] = settings

    inputs["basis"] = {}
    for bset in basis_sets:

        bfile = tempfile.NamedTemporaryFile(delete=False)
        try:
            with open(bfile.name, "w") as f:
                f.write(bset)
            bdata, _ = basis_cls.get_or_create(
                bfile.name, use_first=False, store_basis=False)
            # TODO report if bases created or retrieved
        finally:
            os.remove(bfile.name)

        inputs["basis"][bdata.element] = bdata

    return inputs
コード例 #22
0
    def parse_hubbard(self, filepath):
        """
        Parse the contents of the file {prefix}.Hubbard_U.dat as written by a HpCalculation

        :param filepath: absolute filepath to the Hubbard_U.dat output file
        :returns: dictionary with parsed contents
        """
        try:
            with open(filepath, 'r') as handle:
                data = handle.readlines()
        except IOError as exception:
            raise OutputParsingError(
                "could not read the '{}' output file".format(
                    os.path.basename(filepath)))

        result = {'hubbard_U': {'sites': []}}
        blocks = {
            'chi0': [None, None],
            'chi1': [None, None],
            'chi0_inv': [None, None],
            'chi1_inv': [None, None],
            'hubbard': [None, None],
        }

        for line_number, line in enumerate(data):

            if 'site n.' in line:
                parsed = False
                subline_number = line_number + 1
                while not parsed:
                    subline = data[subline_number].strip()
                    if subline:
                        subline_number += 1
                        subdata = subline.split()
                        result['hubbard_U']['sites'].append({
                            'index':
                            subdata[0],
                            'type':
                            subdata[1],
                            'kind':
                            subdata[2],
                            'spin':
                            subdata[3],
                            'new_type':
                            subdata[4],
                            'new_kind':
                            subdata[5],
                            'value':
                            subdata[6],
                        })
                    else:
                        parsed = True

            if 'chi0 matrix' in line:
                blocks['chi0'][0] = line_number + 1

            if 'chi1 matrix' in line:
                blocks['chi0'][1] = line_number
                blocks['chi1'][0] = line_number + 1

            if 'chi0^{-1} matrix' in line:
                blocks['chi1'][1] = line_number
                blocks['chi0_inv'][0] = line_number + 1

            if 'chi1^{-1} matrix' in line:
                blocks['chi0_inv'][1] = line_number
                blocks['chi1_inv'][0] = line_number + 1

            if 'Hubbard matrix' in line:
                blocks['chi1_inv'][1] = line_number
                blocks['hubbard'][0] = line_number + 1
                blocks['hubbard'][1] = len(data)
                break

        if not all(sum(blocks.values(), [])):
            raise OutputParsingError(
                "could not determine beginning and end of all matrix blocks in '{}'"
                .format(os.path.basename(filepath)))

        for matrix_name in ('chi0', 'chi1', 'chi0_inv', 'chi1_inv', 'hubbard'):
            matrix_block = blocks[matrix_name]
            matrix_data = data[matrix_block[0]:matrix_block[1]]
            matrix = self.parse_hubbard_matrix(matrix_data)

            if len(set(matrix.shape)) != 1:
                raise OutputParsingError(
                    "the matrix '{}' in '{}'' is not square but has shape {}".
                    format(matrix_name, os.path.basename(filepath),
                           matrix.shape))

            result[matrix_name] = matrix

        return result
コード例 #23
0
        try:
            forces = np.array([vspr.ionic_steps[-1]['forces']])
            array_data.set_array('forces', forces)

        except Exception, e:
            msg = ("Processing forces, "
                   "with error Message:\n>> {}".format(e))
            raise OutputParsingError(msg)

        try:
            stress = np.array(vspr.ionic_steps[-1]['stress'])
            array_data.set_array('stress', stress)

        except Exception, e:
            msg = ("Processing stress, "
                   "with error Message:\n>> {}".format(e))
            raise OutputParsingError(msg)

        try:
            nodes_list.append(('output_array', array_data))

        except Exception, e:
            msg = ("Failed to create AiiDA data structures "
                   "(ParameterData/ArrrayData) from parsed data, "
                   "with error message:\n>> {}".format(e))
            raise OutputParsingError(msg)

        parser_warnings = None

        return nodes_list, parser_warnings
コード例 #24
0
ファイル: __init__.py プロジェクト: kjappelbaum/aiida-raspa
    def _parse_stdout(self, out_folder, new_nodes_list):
        fn = None
        fs = out_folder.get_folder_list()
        for f in fs:
            if f.endswith('.data'):
                fn = f
        if fn is None:
            raise OutputParsingError(
                "Calculation did not produce an output file. Please make sure that it run "
                "correctly")

        res_per_component = []
        component_names = []
        inp_params = self._calc.inp.parameters.get_dict()
        ncomponents = len(inp_params['Component'])
        for i in range(ncomponents):
            res_per_component.append({})
            component_names.append(inp_params['Component'][i]['MoleculeName'])
        # self.logger.info("list of components: {}".format(component_names))

        output_abs_path = out_folder.get_abs_path(fn)
        result_dict = {'exceeded_walltime': False}
        framework_density = re.compile("Framework Density:")
        num_of_molec = re.compile("Number of molecules:$")

        with open(output_abs_path, "r") as f:
            # 1st parsing part
            icomponent = 0
            res_cmp = res_per_component[0]
            for line in f:
                # TODO maybe change for parse_line?
                if "WARNING" in line:
                    self.logger.warning(line)
                if "Conversion factor molecules/unit cell -> mol/kg:" in line:
                    res_cmp['conversion_factor_molec_uc_to_mol_kg'] = float(
                        line.split()[6])
                    res_cmp[
                        'conversion_factor_molec_uc_to_mol_kg_unit'] = "(mol/kg)/(molec/uc)"
                if "Conversion factor molecules/unit cell -> gr/gr:" in line:
                    res_cmp['conversion_factor_molec_uc_to_gr_gr'] = float(
                        line.split()[6])
                    res_cmp[
                        'conversion_factor_molec_uc_to_gr_gr_unit'] = "(gr/gr)/(molec/uc)"
                if "Conversion factor molecules/unit cell -> cm^3 STP/gr:" in line:
                    res_cmp['conversion_factor_molec_uc_to_cm3stp_gr'] = float(
                        line.split()[7])
                    res_cmp[
                        'conversion_factor_molec_uc_to_cm3stp_gr_unit'] = "(cm^3_STP/gr)/(molec/uc)"
                if "Conversion factor molecules/unit cell -> cm^3 STP/cm^3:" in line:
                    res_cmp[
                        'conversion_factor_molec_uc_to_cm3stp_cm3'] = float(
                            line.split()[7])
                    res_cmp[
                        'conversion_factor_molec_uc_to_cm3stp_cm3_unit'] = "(cm^3_STP/cm^3)/(molec/uc)"
                if "MolFraction:" in line:
                    res_cmp['mol_fraction'] = float(line.split()[1])
                    res_cmp['mol_fraction_unit'] = "-"
                if "Partial pressure:" in line:
                    res_cmp['partial_pressure'] = float(line.split()[2])
                    res_cmp['partial_pressure_unit'] = "Pa"
                if "Partial fugacity:" in line:
                    res_cmp['partial_fugacity'] = float(line.split()[2])
                    res_cmp['partial_fugacity_unit'] = "Pa"
                    icomponent += 1
                    if icomponent < ncomponents:
                        res_cmp = res_per_component[icomponent]
                    else:
                        break
            # end of the 1st parsing part

            # 2nd parsing part
            for line in f:
                for parse in block1_list:
                    if parse[0].match(line):
                        parse_block1(f, result_dict, parse[1], *parse[2])
                        for i, cmpnt in enumerate(component_names):
                            # I assume here that properties per component are present right in the next line. The order of
                            # properties per molecule is the same as the order of molecules in the input file. So if component
                            # name was not found in the next line, I break the loop immidiately as there is no reason to
                            # continue it
                            line = next(f)
                            if cmpnt in line:
                                parse_block1(f, res_per_component[i], parse[1],
                                             *parse[2])
                            else:
                                break

                        continue  # no need to perform further checks, propperty has been found already
                for parse in energy_block_list:
                    if parse[0].match(line):
                        parse_block_energy(f, result_dict, prop=parse[1])
                        continue  # no need to perform further checks, propperty has been found already
                if framework_density.match(line) is not None:
                    result_dict['framework_density'] = line.split()[2]
                    result_dict['framework_density_units'] = line.split(
                    )[3].translate(None, '[](){}')

                elif num_of_molec.match(line) is not None:
                    break  # this stops the cycle
            # end of the 2nd parsing part

            # 3rd parsing part
            icomponent = 0
            for line in f:
                # TODO: change for parse_line?
                if 'Average loading absolute [molecules/unit cell]' in line:
                    res_per_component[icomponent][
                        'loading_absolute_average'] = float(line.split()[5])
                    res_per_component[icomponent][
                        'loading_absolute_dev'] = float(line.split()[7])
                    res_per_component[icomponent][
                        'loading_absolute_units'] = 'molecules/unit cell'
                elif 'Average loading excess [molecules/unit cell]' in line:
                    res_per_component[icomponent][
                        'loading_excess_average'] = float(line.split()[5])
                    res_per_component[icomponent][
                        'loading_excess_dev'] = float(line.split()[7])
                    res_per_component[icomponent][
                        'loading_excess_units'] = 'molecules/unit cell'
                    icomponent += 1
                if icomponent >= ncomponents:
                    break
            # end of the 3rd parsing part

            # 4th parsing part
            for line in f:
                for to_parse in lines_with_component_list:
                    if to_parse[0].search(line):
                        parse_lines_with_component(res_per_component,
                                                   component_names, line,
                                                   to_parse[1])
            # end of the 4th parsing part

        pair = (self.get_linkname_outparams(), ParameterData(dict=result_dict))
        new_nodes_list.append(pair)
        for i, item in enumerate(res_per_component):
            pair = ('component_' + str(i), ParameterData(dict=item))
            new_nodes_list.append(pair)
コード例 #25
0
    def _parse_stdout(self, out_folder, new_nodes_list):
        fn = None
        fs = out_folder.get_folder_list()
        for f in fs:
            if f.endswith('.data'):
                fn = f
        if fn is None:
            raise OutputParsingError(
                "Calculation did not produce an output"
                " file. Please make sure that it run correctly")

        res_per_component = []
        component_names = []
        inp_params = self._calc.inp.parameters.get_dict()
        ncomponents = len(inp_params['Component'])
        for i in range(ncomponents):
            res_per_component.append({})
            component_names.append(inp_params['Component'][i]['MoleculeName'])
        # self.logger.info("list of components: {}".format(component_names))

        abs_fn = out_folder.get_abs_path(fn)

        with open(abs_fn, "r") as f:
            # Parse the "Adsorbate properties" section
            if ncomponents > 0:
                icomponent = 0
                for line in f:
                    if "MolFraction:" in line:
                        res_per_component[icomponent]['mol_fraction'] = float(
                            line.split()[1])
                        res_per_component[icomponent][
                            'mol_fraction_unit'] = "-"
                    if "Conversion factor molecules/unit cell -> mol/kg:" in line:
                        res_per_component[icomponent][
                            'conversion_factor_molec_uc_to_mol_kg'] = float(
                                line.split()[6])
                        res_per_component[icomponent][
                            'conversion_factor_molec_uc_to_mol_kg_unit'] = "(mol/kg)/(molec/uc)"
                    if "Conversion factor molecules/unit cell -> gr/gr:" in line:
                        res_per_component[icomponent][
                            'conversion_factor_molec_uc_to_gr_gr'] = float(
                                line.split()[6])
                        res_per_component[icomponent][
                            'conversion_factor_molec_uc_to_gr_gr_unit'] = "(gr/gr)/(molec/uc)"
                    if "Conversion factor molecules/unit cell -> cm^3 STP/gr:" in line:
                        res_per_component[icomponent][
                            'conversion_factor_molec_uc_to_cm3stp_gr'] = float(
                                line.split()[7])
                        res_per_component[icomponent][
                            'conversion_factor_molec_uc_to_cm3stp_gr_unit'] = "(cm^3_STP/gr)/(molec/uc)"
                    if "Conversion factor molecules/unit cell -> cm^3 STP/cm^3:" in line:
                        res_per_component[icomponent][
                            'conversion_factor_molec_uc_to_cm3stp_cm3'] = float(
                                line.split()[7])
                        res_per_component[icomponent][
                            'conversion_factor_molec_uc_to_cm3stp_cm3_unit'] = "(cm^3_STP/cm^3)/(molec/uc)"
                    if "Partial pressure:" in line:
                        res_per_component[icomponent][
                            'partial_pressure'] = float(line.split()[2])
                        res_per_component[icomponent][
                            'partial_pressure_unit'] = "Pa"
                    if "Partial fugacity:" in line:
                        res_per_component[icomponent][
                            'partial_fugacity'] = float(line.split()[2])
                        res_per_component[icomponent][
                            'partial_fugacity_unit'] = "Pa"
                        icomponent += 1
                    if icomponent == ncomponents:
                        break

            # Jump to the "Results" section (if not present: exceeded_walltime=True)
            result_dict = {'exceeded_walltime': True}
            for line in f:
                if 'Finishing simulation' in line:
                    result_dict['exceeded_walltime'] = False
                    break

            # Parse the "System results" section
            for line in f:
                if 'Enthalpy of adsorption:' in line:
                    for line in f:
                        if 'Average' in line:
                            result_dict[
                                'enthalpy_of_adsorption_units'] = 'KJ/MOL'
                            result_dict[
                                'enthalpy_of_adsorption_average'] = float(
                                    line.split()[1]) * KELVIN_TO_KJ_PER_MOL
                            result_dict['enthalpy_of_adsorption_dev'] = float(
                                line.split()[3]) * KELVIN_TO_KJ_PER_MOL
                            break
                break
            for line in f:
                if 'Average Adsorbate-Adsorbate energy:' in line:
                    for line in f:
                        if 'Average' in line:
                            result_dict['ads_ads_total_energy_unit'] = 'KJ/MOL'
                            result_dict['ads_ads_wdv_energy_unit'] = 'KJ/MOL'
                            result_dict[
                                'ads_ads_coulomb_energy_unit'] = 'KJ/MOL'
                            result_dict[
                                'ads_ads_total_energy_average'] = float(
                                    line.split()[1]) * KELVIN_TO_KJ_PER_MOL
                            result_dict['ads_ads_wdv_energy_average'] = float(
                                line.split()[5]) * KELVIN_TO_KJ_PER_MOL
                            result_dict[
                                'ads_ads_coulomb_energy_average'] = float(
                                    line.split()[7]) * KELVIN_TO_KJ_PER_MOL
                        if '+/-' in line:
                            result_dict['ads_ads_total_energy_dev'] = float(
                                line.split()[1]) * KELVIN_TO_KJ_PER_MOL
                            result_dict['ads_ads_wdv_energy_dev'] = float(
                                line.split()[3]) * KELVIN_TO_KJ_PER_MOL
                            result_dict['ads_ads_coulomb_energy_dev'] = float(
                                line.split()[5]) * KELVIN_TO_KJ_PER_MOL
                            break
                    break
            for line in f:
                if 'Average Host-Adsorbate energy:' in line:
                    for line in f:
                        if 'Average' in line:
                            result_dict[
                                'host_ads_total_energy_unit'] = 'KJ/MOL'
                            result_dict['host_ads_wdv_energy_unit'] = 'KJ/MOL'
                            result_dict[
                                'host_ads_coulomb_energy_unit'] = 'KJ/MOL'
                            result_dict[
                                'host_ads_total_energy_average'] = float(
                                    line.split()[1]) * KELVIN_TO_KJ_PER_MOL
                            result_dict['host_ads_wdv_energy_average'] = float(
                                line.split()[5]) * KELVIN_TO_KJ_PER_MOL
                            result_dict[
                                'host_ads_coulomb_energy_average'] = float(
                                    line.split()[7]) * KELVIN_TO_KJ_PER_MOL
                        if '+/-' in line:
                            result_dict['host_ads_total_energy_dev'] = float(
                                line.split()[1]) * KELVIN_TO_KJ_PER_MOL
                            result_dict['host_ads_wdv_energy_dev'] = float(
                                line.split()[3]) * KELVIN_TO_KJ_PER_MOL
                            result_dict['host_ads_coulomb_energy_dev'] = float(
                                line.split()[5]) * KELVIN_TO_KJ_PER_MOL
                            break
                    break

            # Jump to the "Adsorbate results" section
            for line in f:
                if 'Number of molecules:' in line:
                    break

            # Parse the "Adsorbate results" section
            if ncomponents > 0:
                icomponent = 0
                for line in f:
                    if 'Average loading absolute [molecules/unit cell]' in line:
                        res_per_component[icomponent][
                            'loading_absolute_average'] = float(
                                line.split()[5])
                        res_per_component[icomponent][
                            'loading_absolute_dev'] = float(line.split()[7])
                        res_per_component[icomponent][
                            'loading_absolute_units'] = 'molec/uc'
                    if 'Average loading excess [molecules/unit cell]' in line:
                        res_per_component[icomponent][
                            'loading_excess_average'] = float(line.split()[5])
                        res_per_component[icomponent][
                            'loading_excess_dev'] = float(line.split()[7])
                        res_per_component[icomponent][
                            'loading_excess_units'] = 'molec/uc'
                        icomponent += 1
                    if icomponent == ncomponents:
                        break

            for line in f:
                if 'Average Henry coefficient:' in line:
                    for line in f:
                        for icomponent in range(len(component_names)):
                            if component_names[icomponent] in line:
                                res_per_component[icomponent][
                                    'average_henry_coefficient_units'] = 'mol/kg/Pa'
                                res_per_component[icomponent][
                                    'average_henry_coefficient'] = float(
                                        line.split()[4])
                                res_per_component[icomponent][
                                    'average_henry_coefficient_dev'] = float(
                                        line.split()[6])
                        if 'Average adsorption energy' in line:
                            break
                    break
            #End of the Raspa file

        pair = (self.get_linkname_outparams(), ParameterData(dict=result_dict))
        new_nodes_list.append(pair)
        for i, item in enumerate(res_per_component):
            pair = ('component_' + str(i), ParameterData(dict=item))
            new_nodes_list.append(pair)
コード例 #26
0
def parse_mainout(abs_path, parser_class, init_struct=None,
                  init_settings=None):
    """ parse the main output file and create the required output nodes

    :param abs_path: absolute path of stdout file
    :param parser_class: a string denoting the parser class
    :param init_struct: input structure
    :param init_settings: input structure settings

    :return psuccess: a boolean that is False in case of failed calculations
    :return output_nodes: containing "paramaters" and (optionally) "structure" and "settings"
    """
    from aiida.orm import DataFactory

    psuccess = True
    param_data = {"parser_warnings": []}
    output_nodes = {}

    cryparse = CrystalOutputPlugin()
    if not os.path.exists(abs_path):
        raise OutputParsingError(
            "The raw data file does not exist: {}".format(abs_path))
    with open(abs_path) as f:
        try:
            data = cryparse.read_file(f, log_warnings=False)
        except IOError as err:
            param_data["parser_warnings"].append(
                "Error in CRYSTAL 17 run output: {}".format(err))
            output_nodes["parameters"] = DataFactory("parameter")(
                dict=param_data)
            return False, output_nodes

    # data contains the top-level keys:
    # "warnings" (list), "errors" (list), "meta" (dict), "creator" (dict),
    # "initial" (None or dict), "optimisation" (None or dict), "final" (dict)
    # "mulliken" (optional dict)

    # TODO could also read .gui file for definitive final (primitive) geometry, with symmetries
    # TODO could also read .SCFLOG, to get scf output for each opt step
    # TODO could also read files in .optstory folder, to get (primitive) geometries (+ symmetries) for each opt step
    # Note the above files are only available for optimisation runs

    perrors = data["errors"]
    pwarnings = data["warnings"]
    if perrors:
        psuccess = False
    param_data["errors"] = perrors
    # aiida-quantumespresso only has warnings, so we group errors and warnings for compatibility
    param_data["warnings"] = perrors + pwarnings

    # get meta data
    meta_data = data.pop("meta")
    if "elapsed_time" in meta_data:
        h, m, s = meta_data["elapsed_time"].split(':')
        param_data["wall_time_seconds"] = int(h) * 3600 + int(m) * 60 + int(s)

    # get initial data
    initial_data = data.pop("initial")
    initial_data = {} if not initial_data else initial_data
    for name, val in initial_data.get("calculation", {}).items():
        param_data["calculation_{}".format(name)] = val
    init_scf_data = initial_data.get("scf", [])
    param_data["scf_iterations"] = len(init_scf_data)
    # TODO create TrajectoryData from init_scf_data data

    # optimisation trajectory data
    opt_data = data.pop("optimisation")
    if opt_data:
        param_data["opt_iterations"] = len(
            opt_data) + 1  # the first optimisation step is the initial scf
    # TODO create TrajectoryData from optimisation data

    final_data = data.pop("final")

    # TODO read separate energy contributions
    energy = final_data["energy"]["total_corrected"]
    param_data["energy"] = energy["magnitude"]
    param_data["energy_units"] = energy["units"]

    # TODO read from .gui file and check consistency of final cell/symmops
    structure = _extract_structure(final_data["primitive_cell"], init_struct,
                                   param_data)
    if opt_data or not init_struct:
        output_nodes["structure"] = structure

    ssuccess = _extract_symmetry(final_data, init_settings, output_nodes,
                                 param_data)
    psuccess = False if not ssuccess else psuccess

    _extract_mulliken(data, param_data)

    # add the version and class of parser
    param_data["parser_version"] = str(pkg_version)
    param_data["parser_class"] = str(parser_class)
    param_data["ejplugins_version"] = str(ejplugins.__version__)

    output_nodes["parameters"] = DataFactory("parameter")(dict=param_data)

    # if array_dict:
    #     arraydata = DataFactory("array")()
    #     for name, array in array_dict.items():
    #         arraydata.set_array(name, np.array(array))
    # else:
    #     arraydata = None

    return psuccess, output_nodes
コード例 #27
0
class Default_vasprun_parserInstruction(BaseInstruction):

    _input_file_list_ = ['vasprun.xml']

    def _parser_function(self):
        """
        Parses the vasprun.xml using the Pymatgen Vasprun function.
        """

        vasp_param = {}  # ParameterData
        vasp_array = {}  # ArrayData

        parser_warnings = {}  # return non-critical errors

        # parameter data keys
        _vasprun_keys = [  # directly accessible, by name
            # logical
            'converged',
            'converged_electronic',
            'converged_ionic',
            'dos_has_errors',
            'is_spin',
            'is_hubbard',
            # value
            'efermi'
        ]
        _vasprun_special_keys = [  # can't be accessed directly
            # logical
            'is_band_gap_direct',
            # value
            'no_ionic_steps',
            'final_energy',  # returned as FloatWithUnit
            'energy_units',
            'free_energy',
            'energy_wo_entropy',
            'energy_T0',
            'entropy_TS',
            'no_electronic_steps',
            'total_no_electronic_steps',
            'band_gap',
            'cbm',
            'vbm',
        ]

        # array data keys
        # TODO
        # list --> array; see what exactly ArrayData supports

        # parsing output files
        try:
            vspr = vasp.Vasprun(self._out_folder.get_abs_path('vasprun.xml'))
        except Exception, e:
            msg = ("Parsing vasprun file in pymatgen failed, "
                   "with error message:\n>> {}".format(e))
            raise OutputParsingError(msg)

        # extract data
        try:
            for k in _vasprun_keys:
                vasp_param[k] = getattr(vspr, k)

            # acessing special keys manually
            band_gap, cbm, vbm, is_direct = tuple(
                vspr.eigenvalue_band_properties)
            vasp_param['band_gap'] = band_gap
            vasp_param['cbm'] = cbm
            vasp_param['vbm'] = vbm
            vasp_param['is_band_gap_direct'] = is_direct

            vasp_param['no_ionic_steps'] = len(vspr.ionic_steps)

            last_ionic = vspr.ionic_steps[-1]
            vasp_param['free_energy'] = last_ionic['e_fr_energy']
            vasp_param['energy_wo_entropy'] = last_ionic[
                'e_wo_entrp']  # CHECK: looks like a bug in pymatgen !!!
            vasp_param['energy_T0'] = last_ionic['e_0_energy']
            vasp_param['entropy_TS'] = (last_ionic['e_fr_energy'] -
                                        last_ionic['e_wo_entrp'])
            vasp_param['no_electronic_steps'] = len(
                last_ionic['electronic_steps'])
            vasp_param['total_no_electronic_steps'] = 0
            for step in vspr.ionic_steps:
                vasp_param['total_no_electronic_steps'] += len(
                    step['electronic_steps'])

            final_en = vspr.final_energy
            vasp_param['final_energy'] = final_en.real
            vasp_param['energy_units'] = str(final_en.unit)

        except Exception, e:
            msg = ("Processing of extracted data failed, "
                   "with error message:\n>> {}".format(e))
            raise OutputParsingError(msg)