Skip to content
Snippets Groups Projects
Commit f0ce17c0 authored by Lauri Himanen's avatar Lauri Himanen
Browse files

Single point parsing basics done, trying to get the scala integration working.

parent 11e7b780
No related branches found
No related tags found
No related merge requests found
......@@ -16,3 +16,10 @@ class CPMDCommonParser(CommonParser):
def onClose_section_run(self, backend, gIndex, section):
backend.addValue("program_name", "CPMD")
backend.addValue("program_basis_set_type", "plane waves")
def onClose_section_method(self, backend, gIndex, section):
backend.addValue("electronic_structure_method", "DFT")
basis_id = backend.openSection("section_method_basis_set")
backend.addValue("method_basis_set_kind", "wavefunction")
backend.addValue("mapping_section_method_basis_set_cell_associated", 0)
backend.closeSection("section_method_basis_set", basis_id)
......@@ -22,6 +22,7 @@ class CPMDMainParser(MainHierarchicalParser):
"""
super(CPMDMainParser, self).__init__(file_path, parser_context)
self.setup_common_matcher(CPMDCommonParser(parser_context))
self.n_scf_iterations = 0
#=======================================================================
# Cache levels
......@@ -54,7 +55,7 @@ class CPMDMainParser(MainHierarchicalParser):
SM( " PATH TO THE RESTART FILES:\s+{}".format(self.regexs.regex_eol)),
SM( " GRAM-SCHMIDT ORTHOGONALIZATION"),
SM( " MAXIMUM NUMBER OF STEPS:\s+{} STEPS".format(self.regexs.regex_i)),
SM( " MAXIMUM NUMBER OF ITERATIONS FOR SC:\s+{} STEPS".format(self.regexs.regex_i)),
SM( " MAXIMUM NUMBER OF ITERATIONS FOR SC:\s+(?P<scf_max_iteration>{}) STEPS".format(self.regexs.regex_i)),
SM( " PRINT INTERMEDIATE RESULTS EVERY\s+{} STEPS".format(self.regexs.regex_i)),
SM( " STORE INTERMEDIATE RESULTS EVERY\s+{} STEPS".format(self.regexs.regex_i)),
SM( " NUMBER OF DISTINCT RESTART FILES:\s+{}".format(self.regexs.regex_i)),
......@@ -62,7 +63,7 @@ class CPMDMainParser(MainHierarchicalParser):
SM( " FICTITIOUS ELECTRON MASS:\s+{}".format(self.regexs.regex_f)),
SM( " TIME STEP FOR ELECTRONS:\s+{}".format(self.regexs.regex_f)),
SM( " TIME STEP FOR IONS:\s+{}".format(self.regexs.regex_f)),
SM( " CONVERGENCE CRITERIA FOR WAVEFUNCTION OPTIMIZATION:\s+{}".format(self.regexs.regex_f)),
SM( " CONVERGENCE CRITERIA FOR WAVEFUNCTION OPTIMIZATION:\s+(?P<scf_threshold_energy_change__hartree>{})".format(self.regexs.regex_f)),
SM( " WAVEFUNCTION OPTIMIZATION BY PRECONDITIONED DIIS"),
SM( " THRESHOLD FOR THE WF-HESSIAN IS\s+{}".format(self.regexs.regex_f)),
SM( " MAXIMUM NUMBER OF VECTORS RETAINED FOR DIIS:\s+{}".format(self.regexs.regex_i)),
......@@ -81,7 +82,7 @@ class CPMDMainParser(MainHierarchicalParser):
# SM( " PROGRAM CPMD STARTED AT: (?P<x_cpmd_start_datetime>{})".format(self.regexs.regex_eol)),
]
),
SM( " ***************************** ATOMS ****************************".replace("*", "\*"),
SM( re.escape(" ***************************** ATOMS ****************************"),
sections=["x_cpmd_section_system_information"],
subMatchers=[
SM( " NR TYPE X(BOHR) Y(BOHR) Z(BOHR) MBL".replace("(", "\(").replace(")", "\)"),
......@@ -90,13 +91,19 @@ class CPMDMainParser(MainHierarchicalParser):
SM( " CHARGE:\s+(?P<total_charge>{})".format(self.regexs.regex_i)),
]
),
SM( " \| Pseudopotential Report",
SM( re.escape(" | Pseudopotential Report"),
sections=["x_cpmd_section_pseudopotential_information"],
),
SM( re.escape(" * ATOM MASS RAGGIO NLCC PSEUDOPOTENTIAL *"),
sections=["x_cpmd_section_atom_kinds"],
subMatchers=[
# SM( " PROGRAM CPMD STARTED AT: (?P<x_cpmd_start_datetime>{})".format(self.regexs.regex_eol)),
SM( " \*\s+(?P<x_cpmd_atom_kind_label>{0})\s+(?P<x_cpmd_atom_kind_mass>{1})\s+(?P<x_cpmd_atom_kind_raggio>{1})\s+(?P<x_cpmd_atom_kind_nlcc>{0})\s+(?P<x_cpmd_atom_kind_pseudopotential_l>{0})\s+(?P<x_cpmd_atom_kind_pseudopotential_type>{0})\s+\*".format(self.regexs.regex_word, self.regexs.regex_f),
sections=["x_cpmd_section_atom_kind"],
repeats=True,
),
]
),
SM( " ************************** SUPERCELL ***************************".replace("*", "\*"),
SM( re.escape(" ************************** SUPERCELL ***************************"),
sections=["x_cpmd_section_supercell"],
subMatchers=[
SM( " SYMMETRY:\s+(?P<x_cpmd_cell_symmetry>{})".format(self.regexs.regex_eol)),
......@@ -126,13 +133,13 @@ class CPMDMainParser(MainHierarchicalParser):
SM( " NFI GEMAX CNORM ETOT DETOT TCPU",
sections=["x_cpmd_section_scf"],
subMatchers=[
SM( "\s+{0}\s+{1}\s+{1}\s+{1}\s+{1}\s+{1}".format(self.regexs.regex_i, self.regexs.regex_f),
sections=["section_scf_iteration"],
SM( "\s+(?P<x_cpmd_scf_nfi>{0})\s+(?P<x_cpmd_scf_gemax>{1})\s+(?P<x_cpmd_scf_cnorm>{1})\s+(?P<x_cpmd_scf_etot__hartree>{1})\s+(?P<x_cpmd_scf_detot__hartree>{1})\s+(?P<x_cpmd_scf_tcpu__s>{1})".format(self.regexs.regex_i, self.regexs.regex_f),
sections=["x_cpmd_section_scf_iteration"],
repeats=True,
),
]
),
SM( " * FINAL RESULTS *".replace("*", "\*"),
SM( re.escape(" * FINAL RESULTS *"),
sections=["x_cpmd_section_final_results"],
subMatchers=[
SM( " ATOM COORDINATES GRADIENTS \(-FORCES\)",
......@@ -143,7 +150,7 @@ class CPMDMainParser(MainHierarchicalParser):
SM( " \(X\) EXCHANGE-CORRELATION ENERGY =\s+(?P<energy_XC_potential__hartree>{}) A\.U\.".format(self.regexs.regex_f)),
]
),
SM( " * TIMING *".replace("*", "\*"),
SM( re.escape(" * TIMING *"),
sections=["x_cpmd_section_timing"],
subMatchers=[
]
......@@ -196,6 +203,33 @@ class CPMDMainParser(MainHierarchicalParser):
backend.addValue("basis_set_planewave_cutoff", si_cutoff)
backend.closeSection("section_basis_set_cell_dependent", basis_id)
def onClose_x_cpmd_section_scf_iteration(self, backend, gIndex, section):
# SCF step energy and energy change
scf_id = backend.openSection("section_scf_iteration")
energy = section.get_latest_value("x_cpmd_scf_etot")
backend.addValue("energy_total_scf_iteration", energy)
denergy = section.get_latest_value("x_cpmd_scf_detot")
backend.addValue("energy_change_scf_iteration", denergy)
backend.closeSection("section_scf_iteration", scf_id)
self.n_scf_iterations += 1
def onClose_x_cpmd_section_scf(self, backend, gIndex, section):
backend.addValue("number_of_scf_iterations", self.n_scf_iterations)
def onClose_x_cpmd_section_atom_kind(self, backend, gIndex, section):
# Atomic kinds
label = section.get_latest_value("x_cpmd_atom_kind_label")
number = self.get_atom_number(label)
id_kind = backend.openSection("section_method_atom_kind")
backend.addValue("method_atom_kind_atom_number", number)
backend.addValue("method_atom_kind_label", label)
backend.closeSection("section_method_atom_kind", id_kind)
def onClose_section_single_configuration_calculation(self, backend, gIndex, section):
# For single point calculations there is only one method and system.
backend.addValue("single_configuration_calculation_to_system_ref", 0)
backend.addValue("single_configuration_to_calculation_method_ref", 0)
#=======================================================================
# adHoc
def debug(self):
......@@ -287,3 +321,42 @@ class CPMDMainParser(MainHierarchicalParser):
vectorstr = vectorstr.strip().split()
vec_array = np.array([float(x) for x in vectorstr])
return vec_array
def get_atom_number(self, symbol):
""" Returns the atomic number when given the atomic symbol.
Args:
symbol: atomic symbol as string
Returns:
The atomic number (number of protons) for the given symbol.
"""
chemical_symbols = [
'X', 'H', 'He', 'Li', 'Be',
'B', 'C', 'N', 'O', 'F',
'Ne', 'Na', 'Mg', 'Al', 'Si',
'P', 'S', 'Cl', 'Ar', 'K',
'Ca', 'Sc', 'Ti', 'V', 'Cr',
'Mn', 'Fe', 'Co', 'Ni', 'Cu',
'Zn', 'Ga', 'Ge', 'As', 'Se',
'Br', 'Kr', 'Rb', 'Sr', 'Y',
'Zr', 'Nb', 'Mo', 'Tc', 'Ru',
'Rh', 'Pd', 'Ag', 'Cd', 'In',
'Sn', 'Sb', 'Te', 'I', 'Xe',
'Cs', 'Ba', 'La', 'Ce', 'Pr',
'Nd', 'Pm', 'Sm', 'Eu', 'Gd',
'Tb', 'Dy', 'Ho', 'Er', 'Tm',
'Yb', 'Lu', 'Hf', 'Ta', 'W',
'Re', 'Os', 'Ir', 'Pt', 'Au',
'Hg', 'Tl', 'Pb', 'Bi', 'Po',
'At', 'Rn', 'Fr', 'Ra', 'Ac',
'Th', 'Pa', 'U', 'Np', 'Pu',
'Am', 'Cm', 'Bk', 'Cf', 'Es',
'Fm', 'Md', 'No', 'Lr'
]
atom_numbers = {}
for Z, name in enumerate(chemical_symbols):
atom_numbers[name] = Z
return atom_numbers[symbol]
......@@ -21,15 +21,17 @@ object CpmdParser extends SimpleExternalParserGenerator(
)) :: Nil
),
mainFileTypes = Seq("text/.*"),
mainFileRe = """ \*\*\*\*\*\* \*\*\*\*\*\* \*\*\*\* \*\*\*\* \*\*\*\*\*\*
\*\*\*\*\*\*\* \*\*\*\*\*\*\* \*\*\*\*\*\*\*\*\*\* \*\*\*\*\*\*\*
\*\*\* \*\* \*\*\* \*\* \*\*\*\* \*\* \*\* \*\*\*
\*\* \*\* \*\*\* \*\* \*\* \*\* \*\* \*\*
\*\* \*\*\*\*\*\*\* \*\* \*\* \*\* \*\*
\*\*\* \*\*\*\*\*\* \*\* \*\* \*\* \*\*\*
\*\*\*\*\*\*\* \*\* \*\* \*\* \*\*\*\*\*\*\*
\*\*\*\*\*\* \*\* \*\* \*\* \*\*\*\*\*\*""".r,
cmd = Seq(DefaultPythonInterpreter.python2Exe(), "${envDir}/parsers/cpmd/parser/parser-cpmd/cpmdparser/scalainterface.py",
mainFileRe = """ \*\*\*\* \*\*\*\* \*\*\*\*\*\* \*\* PROGRAM STARTED AT\s(?<cpmdStartedAt>.*)
\*\*\*\*\* \*\* \*\*\* \*\*\* \*\* PROGRAM STARTED ON\s*.*
\*\* \*\*\*\* \*\*\*\*\*\* PROGRAM STARTED BY .*
\*\*\*\*\* \*\* \*\* \*\* \*\* PROGRAM PROCESS ID .*
\*\*\*\* \*\* \*\*\*\*\*\*\* \*\* PROGRAM STARTED IN .*
(?:\s*\n| \s+.*
)*
(?:\s*CP2K\| version string:\s*(?<cpmdVersionString>.*)
)?(?:\s*CP2K\| source code revision number:\s*(?<cpmdRevision>.*)
)?""".r,
cmd = Seq(DefaultPythonInterpreter.pythonExe(), "${envDir}/parsers/cpmd/parser/parser-cpmd/cpmdparser/scalainterface.py",
"${mainFilePath}"),
cmdCwd = "${mainFilePath}/..",
resList = Seq(
......@@ -37,16 +39,15 @@ object CpmdParser extends SimpleExternalParserGenerator(
"parser-cpmd/cpmdparser/setup_paths.py",
"parser-cpmd/cpmdparser/parser.py",
"parser-cpmd/cpmdparser/scalainterface.py",
"parser-cpmd/cpmdparser/generic/__init__.py",
"parser-cpmd/cpmdparser/versions/__init__.py",
"parser-cpmd/cpmdparser/versions/cpmd41/__init__.py",
"parser-cpmd/cpmdparser/versions/cpmd41/commonparser.py",
"parser-cpmd/cpmdparser/versions/cpmd41/mainparser.py",
"parser-cpmd/cpmdparser/versions/cpmd41/inputparser.py",
"parser-cpmd/cpmdparser/versions/cpmd41/commonparser.py",
"nomad_meta_info/public.nomadmetainfo.json",
"nomad_meta_info/common.nomadmetainfo.json",
"nomad_meta_info/meta_types.nomadmetainfo.json",
"nomad_meta_info/cpmd.nomadmetainfo.json",
"nomad_meta_info/cpmd.nomadmetainfo.json"
) ++ DefaultPythonInterpreter.commonFiles(),
dirMap = Map(
"parser-cpmd" -> "parsers/cpmd/parser/parser-cpmd",
......
......@@ -3,6 +3,12 @@ package eu.nomad_lab.parsers
import org.specs2.mutable.Specification
object CpmdParserSpec extends Specification {
"CpmdParserTest" >> {
"test with json-events" >> {
ParserRun.parse(CpmdParser, "parsers/cpmd/test/examples/single_point/output.out", "json-events") must_== ParseResult.ParseSuccess
}
}
"test energy_force with json" >> {
ParserRun.parse(CpmdParser, "parsers/cpmd/test/examples/single_point/output.out", "json") must_== ParseResult.ParseSuccess
}
......
......@@ -160,115 +160,70 @@ class TestSinglePoint(unittest.TestCase):
expected_result = convert_unit(np.array(-0.65031699), "hartree")
self.assertTrue(np.array_equal(result, expected_result))
# def test_energy_total_scf_iteration(self):
# result = self.results["energy_total_scf_iteration"]
# expected_result = convert_unit(np.array(-32.2320848878), "hartree")
# self.assertTrue(np.array_equal(result[0], expected_result))
# def test_program_compilation_host(self):
# result = self.results["program_compilation_host"]
# self.assertEqual(result, "lenovo700")
# def test_scf_max_iteration(self):
# result = self.results["scf_max_iteration"]
# self.assertEqual(result, 300)
# def test_scf_threshold_energy_change(self):
# result = self.results["scf_threshold_energy_change"]
# self.assertEqual(result, 1.00E-07)
# def test_number_of_spin_channels(self):
# result = self.results["number_of_spin_channels"]
# self.assertEqual(result, 1)
# def test_electronic_structure_method(self):
# result = self.results["electronic_structure_method"]
# self.assertEqual(result, "DFT")
# def test_energy_change_scf_iteration(self):
# energy_change = self.results["energy_change_scf_iteration"]
# expected_result = convert_unit(np.array(-3.22E+01), "hartree")
# self.assertTrue(np.array_equal(energy_change[0], expected_result))
# def test_energy_XC_scf_iteration(self):
# result = self.results["energy_XC_scf_iteration"]
# expected_result = convert_unit(np.array(-9.4555961214), "hartree")
# self.assertTrue(np.array_equal(result[0], expected_result))
# def test_electronic_kinetic_energy(self):
# result = self.results["electronic_kinetic_energy"]
# expected_result = convert_unit(np.array(13.31525592466419), "hartree")
# self.assertTrue(np.array_equal(result, expected_result))
# def test_x_cp2k_filenames(self):
# input_filename = self.results["x_cp2k_input_filename"]
# expected_input = "si_bulk8.inp"
# self.assertTrue(input_filename, expected_input)
# bs_filename = self.results["x_cp2k_basis_set_filename"]
# expected_bs = "../BASIS_SET"
# self.assertEqual(bs_filename, expected_bs)
# geminal_filename = self.results["x_cp2k_geminal_filename"]
# expected_geminal = "BASIS_GEMINAL"
# self.assertEqual(geminal_filename, expected_geminal)
# potential_filename = self.results["x_cp2k_potential_filename"]
# expected_potential = "../GTH_POTENTIALS"
# self.assertEqual(potential_filename, expected_potential)
def test_energy_total_scf_iteration(self):
result = self.results["energy_total_scf_iteration"]
# Test the first and last energies
expected_result = convert_unit(np.array(
[
[-1.096898],
[-1.132460],
]), "hartree")
self.assertTrue(np.array_equal(np.array([[result[0]], [result[-1]]]), expected_result))
def test_energy_change_scf_iteration(self):
result = self.results["energy_change_scf_iteration"]
expected_result = convert_unit(np.array(
[
[0.000E+00],
[-8.606E-13],
]), "hartree")
self.assertTrue(np.array_equal(np.array([[result[0]], [result[-1]]]), expected_result))
# mm_potential_filename = self.results["x_cp2k_mm_potential_filename"]
# expected_mm_potential = "MM_POTENTIAL"
# self.assertEqual(mm_potential_filename, expected_mm_potential)
def test_scf_max_iteration(self):
result = self.results["scf_max_iteration"]
self.assertEqual(result, 10000)
# coordinate_filename = self.results["x_cp2k_coordinate_filename"]
# expected_coordinate = "__STD_INPUT__"
# self.assertEqual(coordinate_filename, expected_coordinate)
def test_scf_threshold_energy_change(self):
result = self.results["scf_threshold_energy_change"]
self.assertEqual(result, convert_unit(1.00E-07, "hartree"))
# def test_target_multiplicity(self):
# multiplicity = self.results["spin_target_multiplicity"]
# self.assertEqual(multiplicity, 1)
def test_electronic_structure_method(self):
result = self.results["electronic_structure_method"]
self.assertEqual(result, "DFT")
def test_scf_dft_number_of_iterations(self):
result = self.results["number_of_scf_iterations"]
self.assertEqual(result, 10)
# def test_section_basis_set_atom_centered(self):
# basis = self.results["section_basis_set_atom_centered"][0]
# name = basis["basis_set_atom_centered_short_name"][0]
# number = basis["basis_set_atom_number"][0]
# self.assertEquals(name, "DZVP-GTH-PADE")
# self.assertEquals(number, 14)
def test_section_method_atom_kind(self):
kind = self.results["section_method_atom_kind"][0]
self.assertEqual(kind["method_atom_kind_atom_number"][0], 1)
self.assertEqual(kind["method_atom_kind_label"][0], "H")
# def test_section_basis_set_cell_dependent(self):
# basis = self.results["section_basis_set_cell_dependent"][0]
# cutoff = basis["basis_set_planewave_cutoff"][0]
# self.assertEquals(cutoff, convert_unit(300.0, "hartree"))
def test_section_method_basis_set(self):
kind = self.results["section_method_basis_set"][0]
self.assertEqual(kind["method_basis_set_kind"][0], "wavefunction")
self.assertTrue(np.array_equal(kind["mapping_section_method_basis_set_cell_associated"][0], 0))
# def test_section_method_atom_kind(self):
# kind = self.results["section_method_atom_kind"][0]
# self.assertEqual(kind["method_atom_kind_atom_number"][0], 14)
# self.assertEqual(kind["method_atom_kind_label"][0], "Si1")
def test_single_configuration_to_calculation_method_ref(self):
result = self.results["single_configuration_to_calculation_method_ref"]
self.assertEqual(result, 0)
# def test_section_method_basis_set(self):
# kind = self.results["section_method_basis_set"][0]
# self.assertEqual(kind["method_basis_set_kind"][0], "wavefunction")
# self.assertEqual(kind["number_of_basis_sets_atom_centered"][0], 1)
# self.assertTrue(np.array_equal(kind["mapping_section_method_basis_set_atom_centered"][0], np.array([[0,0]])))
def test_single_configuration_calculation_to_system_description_ref(self):
result = self.results["single_configuration_calculation_to_system_ref"]
self.assertEqual(result, 0)
# def test_single_configuration_calculation_converged(self):
# result = self.results["single_configuration_calculation_converged"]
# self.assertTrue(result)
# def test_scf_dft_number_of_iterations(self):
# result = self.results["number_of_scf_iterations"]
# self.assertEqual(result, 10)
# def test_single_configuration_to_calculation_method_ref(self):
# result = self.results["single_configuration_to_calculation_method_ref"]
# self.assertEqual(result, 0)
# def test_number_of_spin_channels(self):
# result = self.results["number_of_spin_channels"]
# self.assertEqual(result, 1)
# def test_single_configuration_calculation_to_system_description_ref(self):
# result = self.results["single_configuration_calculation_to_system_ref"]
# self.assertEqual(result, 0)
# def test_target_multiplicity(self):
# multiplicity = self.results["spin_target_multiplicity"]
# self.assertEqual(multiplicity, 1)
# def test_stress_tensor(self):
# result = self.results["stress_tensor"]
......@@ -307,7 +262,6 @@ class TestSinglePoint(unittest.TestCase):
# self.assertTrue(np.array_equal(result, expected_result))
# #===============================================================================
# class TestErrors(unittest.TestCase):
# """Test misc. error stuations which may occur during the parsing.
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment