def check_failure(self): """ Throws an exit code if scf failed """ try: scf_wc = self.ctx.scf_res except AttributeError: message = 'ERROR: Something went wrong I do not have new atom positions calculation' self.control_end_wc(message) return self.exit_codes.ERROR_NO_SCF_OUTPUT if not scf_wc.is_finished_ok: exit_statuses = FleurScfWorkChain.get_exit_statuses( ['ERROR_FLEUR_CALCULATION_FAILED']) if scf_wc.exit_status == exit_statuses[0]: fleur_calc = load_node( scf_wc.outputs.output_scf_wc_para.get_dict() ['last_calc_uuid']) if fleur_calc.exit_status == FleurCalc.get_exit_statuses( ['ERROR_VACUUM_SPILL_RELAX'])[0]: self.control_end_wc( 'ERROR: Failed due to atom and vacuum overlap') return self.exit_codes.ERROR_VACUUM_SPILL_RELAX elif fleur_calc.exit_status == FleurCalc.get_exit_statuses( ['ERROR_MT_RADII_RELAX'])[0]: self.control_end_wc('ERROR: Failed due to MT overlap') return self.exit_codes.ERROR_MT_RADII_RELAX return self.exit_codes.ERROR_SCF_FAILED
def test_fleur_scf_wc_init(self): """ Test the interface of the scf workchain """ from aiida_fleur.workflows.scf import FleurScfWorkChain builder = FleurScfWorkChain.get_builder()
def test_fleur_scf_non_convergence(run_with_cache, clear_database, fleur_local_code, inpgen_local_code, generate_structure2, clear_spec): """ Full regression test of FleurScfWorkchain starting with a crystal structure and parameters Check if calc parameters are given through, check if wf default parameters are updated """ # prepare input nodes and dicts options = { 'resources': { 'num_machines': 1, 'num_mpiprocs_per_machine': 1 }, 'max_wallclock_seconds': 5 * 60, 'withmpi': False, 'custom_scheduler_commands': '' } FleurCode = fleur_local_code InpgenCode = inpgen_local_code wf_parameters = {'add_comp_para': {'serial': True}, 'itmax_per_run': 3} calc_parameters = { 'atom': { 'element': 'Si', 'rmt': 2.1, 'jri': 981, 'lmax': 8, 'lnonsph': 6 }, 'comp': { 'kmax': 3.4 }, 'kpt': { 'div1': 10, 'div2': 10, 'div3': 10, 'tkb': 0.0005 } } # create process builder to set parameters builder = FleurScfWorkChain.get_builder() builder.metadata.description = 'Simple Fleur SCF test for Si bulk which does not converge' builder.metadata.label = 'FleurSCF_test_Si_bulk' builder.structure = generate_structure2().store() builder.options = Dict(dict=options).store() builder.calc_parameters = Dict(dict=calc_parameters).store() builder.wf_parameters = Dict(dict=wf_parameters).store() builder.fleur = FleurCode.store() builder.inpgen = InpgenCode.store() print(builder) # now run scf with cache fixture out, node = run_with_cache(builder) print(out) print(node) print(get_workchain_report(node, 'REPORT')) assert not node.is_finished_ok assert node.exit_status == 362
def test_fleur_scf_fleurinp_Si( #run_with_cache, with_export_cache, fleur_local_code, create_fleurinp, clear_database, clear_spec): """ full example using scf workflow with just a fleurinp data as input. Several fleur runs needed till convergence """ options = { 'resources': { 'num_machines': 1, 'num_mpiprocs_per_machine': 1 }, 'max_wallclock_seconds': 5 * 60, 'withmpi': False, 'custom_scheduler_commands': '' } FleurCode = fleur_local_code # create process builder to set parameters builder = FleurScfWorkChain.get_builder() builder.metadata.description = 'Simple Fleur SCF test for Si bulk with fleurinp data given' builder.metadata.label = 'FleurSCF_test_Si_bulk' builder.fleurinp = create_fleurinp(TEST_INP_XML_PATH).store() builder.options = Dict(dict=options).store() builder.fleur = FleurCode #print(builder) # now run calculation #run_with_cache(builder) data_dir_path = os.path.join( aiida_path, '../tests/workflows/caches/fleur_scf_fleurinp_Si.tar.gz') with with_export_cache(data_dir_abspath=data_dir_path): out, node = run_get_node(builder) #print(out) #print(node) print(get_workchain_report(node, 'REPORT')) #assert node.is_finished_ok # check output n = out['output_scf_wc_para'] n = n.get_dict() print(get_calcjob_report(load_node(n['last_calc_uuid']))) #print(n) assert abs(n.get('distance_charge') - 9.8993e-06) < 2.0e-6 assert n.get('errors') == []
'commandline_options': ['-wtime', '30'], 'blaha': ['bla'] }) wf_para = Dict( dict={ 'fleur_runmax': 4, 'density_criterion': 0.000001, #}) 'queue_name': 'th123_node', 'resources': { 'num_machines': 1, 'num_mpiprocs_per_machine': 12 }, 'walltime_sec': 10 * 60 }) res = FleurScfWorkChain.run( wf_parameters=wf_para, structure=s, #calc_parameters=parameters, inpgen=code, fleur=code2) #, settings=settings)# ''' code = Code.get_from_string('inpgen_mac_25_10_2016') code2 = Code.get_from_string('fleur_mac_v0_27') computer = Computer.get('local_mac') wf_para = ParameterData(dict={'fleur_runmax' : 4, 'density_criterion' : 0.0000001})#, 'queue' : 'th1'}) res = run(fleur_convergence, wf_parameters=wf_para, structure=load_node(24422), calc_parameters=load_node(24507), inpgen = code, fleur=code2) '''
def test_fleur_scf_structure_Si(run_with_cache, clear_database, fleur_local_code, inpgen_local_code, generate_structure2, clear_spec): """ Full regression test of FleurScfWorkchain starting with a crystal structure and parameters Check if calc parameters are given through, check if wf default parameters are updated """ # prepare input nodes and dicts options = { 'resources': { 'num_machines': 1, 'num_mpiprocs_per_machine': 1 }, 'max_wallclock_seconds': 5 * 60, 'withmpi': False, 'custom_scheduler_commands': '' } FleurCode = fleur_local_code InpgenCode = inpgen_local_code wf_parameters = {'serial': True, 'itmax_per_run': 30} calc_parameters = { 'atom': { 'element': 'Si', 'rmt': 2.1, 'jri': 981, 'lmax': 8, 'lnonsph': 6 }, 'comp': { 'kmax': 3.4 }, 'kpt': { 'div1': 10, 'div2': 10, 'div3': 10, 'tkb': 0.0005 } } #calc_parameters = {'atom': {'element': "W", 'rmt': 2.3, 'jri': 981, 'lmax': 10, # 'lnonsph': 6, 'econfig': '[Kr] 4d10 4f14 | 5s2 5p6 6s2 5d4', 'lo': '5s 5p'}, # 'comp': {'kmax': 3.5}, # 'kpt': {'div1': 15, 'div2': 15, 'div3': 15, 'tkb': 0.0005}} # create process builder to set parameters builder = FleurScfWorkChain.get_builder() builder.metadata.description = 'Simple Fleur SCF test for Si bulk with structure, calc para and wf para given' builder.metadata.label = 'FleurSCF_test_Si_bulk' builder.structure = generate_structure2().store() builder.options = Dict(dict=options).store() builder.calc_parameters = Dict(dict=calc_parameters).store() builder.wf_parameters = Dict(dict=wf_parameters).store() builder.fleur = FleurCode.store() builder.inpgen = InpgenCode.store() print(builder) # now run scf with cache fixture out, node = run_with_cache(builder) #out, node = run_get_node(builder) print(out) print(node) assert node.is_finished_ok # check output n = out['output_scf_wc_para'] n = n.get_dict() print(n) assert abs(n.get('distance_charge') - 8.0987e-06) < 10**-9 assert n.get('errors') == []
def test_fleur_scf_validation_wrong_inputs(run_with_cache, mock_code_factory, create_fleurinp, generate_structure2, clear_spec, clear_database): """ Test the validation behavior of FleurScfWorkchain if wrong input is provided it should throw an exitcode and not start a Fleur run or crash """ #from aiida.engine import run_get_node #clear_spec() # prepare input nodes and dicts options = { 'resources': { 'num_machines': 1, 'num_mpiprocs_per_machine': 1 }, 'max_wallclock_seconds': 5 * 60, 'withmpi': False, 'custom_scheduler_commands': '' } options = Dict(dict=options).store() FleurCode = mock_code_factory( label='fleur', data_dir_abspath=os.path.join( os.path.dirname(os.path.abspath(__file__)), 'calc_data_dir/'), entry_point=CALC_ENTRY_POINT, ignore_files=[ 'cdnc', 'out', 'FleurInputSchema.xsd', 'cdn.hdf', 'usage.json', 'cdn??' ]) InpgenCode = mock_code_factory( label='inpgen', data_dir_abspath=os.path.join( os.path.dirname(os.path.abspath(__file__)), 'calc_data_dir/'), entry_point=CALC2_ENTRY_POINT, ignore_files=['_aiidasubmit.sh', 'FleurInputSchema.xsd']) calc_parameters = Dict(dict={}) calc_parameters.store() structure = generate_structure2() structure.store() fleurinp = create_fleurinp(TEST_INP_XML_PATH) fleurinp.store() ################ # Create builders # 1. create builder structure and fleurinp builder_struc_fleurinp = FleurScfWorkChain.get_builder() builder_struc_fleurinp.structure = structure builder_struc_fleurinp.fleurinp = fleurinp builder_struc_fleurinp.options = options builder_struc_fleurinp.fleur = FleurCode builder_struc_fleurinp.inpgen = InpgenCode # 2. create builder structure no inpgen given builder_no_inpgen = FleurScfWorkChain.get_builder() builder_no_inpgen.structure = structure builder_no_inpgen.options = options builder_no_inpgen.fleur = FleurCode # 3. create builder no fleurcode given builder_no_fleur = FleurScfWorkChain.get_builder() builder_no_fleur.structure = structure builder_no_fleur.options = options builder_no_fleur.inpgen = InpgenCode # 4. wrong code given (here we swap) builder_wrong_code = FleurScfWorkChain.get_builder() builder_wrong_code.structure = structure builder_wrong_code.options = options builder_wrong_code.inpgen = FleurCode builder_wrong_code.fleur = InpgenCode # 5. create builder fleurinp and calc_parameter given builder_calc_para_fleurinp = FleurScfWorkChain.get_builder() builder_calc_para_fleurinp.calc_parameters = calc_parameters builder_calc_para_fleurinp.fleurinp = fleurinp builder_calc_para_fleurinp.options = options builder_calc_para_fleurinp.fleur = FleurCode builder_calc_para_fleurinp.inpgen = InpgenCode ################### # now run the buidlers all should fail early with exit codes # 1. structure and fleurinp given out, node = run_get_node(builder_struc_fleurinp) assert out == {} assert node.is_finished assert not node.is_finished_ok assert node.exit_status == 231 # 2. structure and no inpgen given out, node = run_get_node(builder_no_inpgen) assert out == {} assert node.is_finished assert not node.is_finished_ok assert node.exit_status == 231 # 3. no fleur code given, since not optional input, # caught by aiida during creation with pytest.raises(ValueError) as e_info: out, node = run_get_node(builder_no_fleur) # 4. wrong code type given out, node = run_get_node(builder_wrong_code) assert out == {} assert node.is_finished assert not node.is_finished_ok assert node.exit_status == 233 # 5. calc_parameter and fleurinp given out, node = run_get_node(builder_calc_para_fleurinp) assert out == {} assert node.is_finished assert not node.is_finished_ok assert node.exit_status == 231
def test_fleur_scf_fleurinp_Si_modifications( #run_with_cache, with_export_cache, #mock_code_factory, #aiida_local_code_factory, fleur_local_code, create_fleurinp, clear_database, clear_spec): """ Full regression test of FleurScfWorkchain starting with a fleurinp data, but adjusting the Fleur input file before the fleur run. """ wf_parameters = { 'fleur_runmax': 4, 'density_converged': 0.0002, 'energy_converged': 0.002, 'force_converged': 0.002, 'mode': 'density', # 'density', 'energy' or 'force' 'serial': True, 'itmax_per_run': 30, 'force_dict': { 'qfix': 2, 'forcealpha': 0.5, 'forcemix': 'BFGS' }, 'inpxml_changes': [('set_inpchanges', { 'change_dict': { 'Kmax': 3.8 } })], } options = { 'resources': { 'num_machines': 1, 'num_mpiprocs_per_machine': 1 }, 'max_wallclock_seconds': 5 * 60, 'withmpi': False, 'custom_scheduler_commands': '' } FleurCode = fleur_local_code # create process builder to set parameters builder = FleurScfWorkChain.get_builder() builder.metadata.description = 'Simple Fleur SCF test for Si bulk with fleurinp data given and mod request' builder.metadata.label = 'FleurSCF_test_Si_bulk_mod' builder.fleurinp = create_fleurinp(TEST_INP_XML_PATH).store() builder.options = Dict(dict=options).store() builder.wf_parameters = Dict(dict=wf_parameters).store() builder.fleur = FleurCode #print(builder) # now run calculation #run_with_cache(builder) data_dir_path = os.path.join( aiida_path, '../tests/workflows/caches/fleur_scf_fleurinp_Si_mod.tar.gz') with with_export_cache(data_dir_abspath=data_dir_path): out, node = run_get_node(builder) print(out) #print(node) assert node.is_finished_ok # check output n = out['output_scf_wc_para'] n = n.get_dict() lasto = out['last_fleur_calc_output'] calc = lasto.get_incoming().all()[0].node print(calc) print(calc.get_cache_source()) lasto = lasto.get_dict() print(n) #get kmax and minDistance assert abs(n.get('distance_charge') - 0.0001671267) < 10**-9 assert n.get('errors') == [] assert lasto['kmax'] == 3.8
def return_results(self): """ return the results of the relaxed DFT+U calculations (scf workchains) """ distancelist = [] t_energylist = [] failed_configs = [] non_converged_configs = [] configs_list = [] outnodedict = {} e_u = 'htr' dis_u = 'me/bohr^3' for index, config in enumerate(self.ctx.fixed_configurations): if f'Relaxed_{index}' in self.ctx: calc = self.ctx[f'Relaxed_{index}'] else: message = ( 'One SCF workflow was not run because the fixed calculation failed: {}'.format(f'Relaxed_{index}')) self.ctx.warnings.append(message) self.ctx.successful = False failed_configs.append(index) continue if not calc.is_finished_ok: message = ('One SCF workflow was not successful: {}'.format(f'Relaxed_{index}')) self.ctx.warnings.append(message) self.ctx.successful = False #We dont skip simply non-converged calculations #because we want to try to exctract the total_energy if calc.exit_status not in FleurScfWorkChain.get_exit_statuses(['ERROR_DID_NOT_CONVERGE']): failed_configs.append(index) continue non_converged_configs.append(index) try: outputnode_scf = calc.outputs.output_scf_wc_para except KeyError: message = ('One SCF workflow failed, no scf output node: {}.' ' I skip this one.'.format(f'Relaxed_{index}')) self.ctx.errors.append(message) self.ctx.successful = False failed_configs.append(index) continue try: fleurinp_scf = calc.outputs.fleurinp except KeyError: message = ('One SCF workflow failed, no fleurinp output node: {}.' ' I skip this one.'.format(f'Relaxed_{index}')) self.ctx.errors.append(message) self.ctx.successful = False failed_configs.append(index) continue # we loose the connection of the failed scf here. # link labels cannot contain '.' link_label = f'configuration_{index}' fleurinp_label = f'fleurinp_{index}' outnodedict[link_label] = outputnode_scf outnodedict[fleurinp_label] = fleurinp_scf outpara = outputnode_scf.get_dict() t_e = outpara.get('total_energy', float('nan')) e_u = outpara.get('total_energy_units', 'htr') dis = outpara.get('distance_charge', float('nan')) dis_u = outpara.get('distance_charge_units', 'me/bohr^3') t_energylist.append(t_e) distancelist.append(dis) configs_list.append(index) out = { 'workflow_name': self.__class__.__name__, 'workflow_version': self._workflowversion, 'configurations': self.ctx.fixed_configurations, 'total_energy': t_energylist, 'total_energy_units': e_u, 'distance_charge': distancelist, 'distance_charge_units': dis_u, 'successful_configs': configs_list, 'non_converged_configs': non_converged_configs, 'failed_configs': failed_configs, 'info': self.ctx.info, 'warnings': self.ctx.warnings, 'errors': self.ctx.errors } if self.ctx.successful: self.report('Done, Orbital occupation control calculation complete') elif len(t_energylist) != 0: self.report('Done, but something went wrong.... Probably some individual calculation failed or' ' a scf-cycle did not reach the desired distance.') else: self.report('Done, but something went wrong.... All Calculations failed. Probably something is' ' wrong in your setup') outnode = Dict(dict=out) outnodedict['results_node'] = outnode # create links between all these nodes... outputnode_dict = create_orbcontrol_result_node(**outnodedict) outputnode = outputnode_dict.get('output_orbcontrol_wc_para') outputnode.label = 'output_orbcontrol_wc_para' outputnode.description = ( 'Contains orbital occupation control results and information of an FleurOrbControlWorkChain run.') returndict = {} returndict['output_orbcontrol_wc_para'] = outputnode outputscf = outputnode_dict.get('output_orbcontrol_wc_gs_scf', None) if outputscf: outputscf.label = 'output_orbcontrol_wc_gs_scf' outputscf.description = ('SCF output from the run with the lowest total ' 'energy extracted from FleurOrbControlWorkChain') returndict['output_orbcontrol_wc_gs_scf'] = outputscf outputfleurinp = outputnode_dict.get('output_orbcontrol_wc_gs_fleurinp', None) if outputscf: outputscf.label = 'output_orbcontrol_wc_gs_fleurinp' outputscf.description = ('Fleurinp from the scf run with the lowest total ' 'energy extracted from FleurOrbControlWorkChain') returndict['output_orbcontrol_wc_gs_fleurinp'] = outputfleurinp # create link to workchain node for link_name, node in returndict.items(): self.out(link_name, node) if len(t_energylist) == 0: return self.exit_codes.ERROR_ALL_CONFIGS_FAILED elif not self.ctx.successful: return self.exit_codes.ERROR_SOME_CONFIGS_FAILED
ParameterData = DataFactory('parameter') KpointsData = DataFactory('array.kpoints') #FleurinpData = DataFactory('fleurinp.fleurinp') FleurinpData = DataFactory('fleur.fleurinp') ############################### # Set your values here codename = 'inpgen_iff@local_iff' #'inpgen_mac_30_11_2016@local_mac' codename2 = 'fleur_iff@local_iff' #'fleur_mac_v0_27@local_mac' ############################### code = Code.get_from_string(codename) code2 = Code.get_from_string(codename2) wf_para = Dict( dict={ 'relax_runmax': 4, 'density_criterion': 0.0000002, 'energy_criterion': 0.0005, 'converge_energy': True, 'converge_density': True }) fleurinp = load_node(1339) remote = load_node(1353) wf_para = load_node(1333) res = FleurScfWorkChain.run(wf_parameters=wf_para, fleurinp=fleurinp, remote_data=remote, fleur=code2)