Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add FHI-aims DFT calculator #562

Merged
merged 127 commits into from
Feb 29, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
127 commits
Select commit Hold shift + click to select a range
66d4664
Move files from: https://github.com/tpurcell90/atomate2-fhi-aims
tpurcell90 Oct 11, 2023
6d82a87
Fix errors in the tests from the migration
tpurcell90 Oct 11, 2023
ace8c4f
Ran isort on all of the source files
tpurcell90 Oct 11, 2023
69a534b
Restore data=[Structure] to generate_phonon_displacements
tpurcell90 Oct 11, 2023
5af4c85
Fix all linter errors
tpurcell90 Oct 11, 2023
7f49c8e
Replaced typing X | Y with Union[X, Y]
tpurcell90 Oct 11, 2023
8f1186e
Update src/atomate2/common/jobs/phonons.py
tpurcell90 Oct 11, 2023
e877b0e
Make requested change from @JaGeo
tpurcell90 Oct 11, 2023
1e0dfc2
Modify forcefields phonon workflow to be the same as Aims and VASP
tpurcell90 Oct 11, 2023
5f8190c
Update documentation of phonon workflows
tpurcell90 Oct 11, 2023
c2cddcd
Restore changes from main in the phonon flow files
tpurcell90 Oct 11, 2023
59830d8
Make sure that phonon schema changes are incorporated
tpurcell90 Oct 11, 2023
d63a2e0
Minor fixes for consistency checks in phonon jobs
tpurcell90 Oct 11, 2023
0d8b18d
Add ASE requirement
tpurcell90 Oct 11, 2023
c7330b1
Fix FHI-aims errors
tpurcell90 Oct 12, 2023
1d0ef20
Correct prev_dir issue
tpurcell90 Oct 12, 2023
c5ef206
Fix pymatgen structure issue after bulk job in phonon workflow
tpurcell90 Oct 12, 2023
b9b5722
Make ASE an optional dependecy under aims
tpurcell90 Oct 12, 2023
8b16cc6
Phonon Diff clean up
tpurcell90 Oct 12, 2023
841aec3
Final documentation formatting checks
tpurcell90 Oct 12, 2023
6a30b1f
Add ase to strict
tpurcell90 Oct 12, 2023
29739f1
Minor Bug Fixes
tpurcell90 Oct 12, 2023
c175a8c
Make requested changes from @ansovolev
tpurcell90 Oct 13, 2023
0090f39
Change parser to convert stresses to kbar
tpurcell90 Oct 13, 2023
6e221c0
Remove tests that only test ASE
tpurcell90 Oct 13, 2023
498327f
Merge branch 'main' into atomate2-aims
Zhuoying Oct 13, 2023
de4171f
Standardize aims schema with respect to structure
tpurcell90 Oct 16, 2023
159f013
Add myself to contributors.md
ansobolev Oct 16, 2023
628ab6b
Check the pydantic errors on the workflows
tpurcell90 Oct 16, 2023
f4a51d2
Merge branch 'main' of https://github.com/materialsproject/atomate2 i…
tpurcell90 Oct 16, 2023
e1810b5
Fix Pydantic2 and Phonon Schema errors from updated main
tpurcell90 Oct 16, 2023
24598a3
Correct phonon schema for the skipped tests
tpurcell90 Oct 16, 2023
f8b9425
Merge branch 'main' into atomate2-aims
tpurcell90 Oct 16, 2023
020ed88
Adopt CBM/VBM terminology for consistency
ansobolev Oct 16, 2023
48cfa36
Adjust Schema names to match the updated nomenclature
tpurcell90 Oct 17, 2023
4bb1206
Use ASE 3.22.1 not ASE 3.23
tpurcell90 Oct 17, 2023
e9ac531
Clean up FHI-aims job to job management
tpurcell90 Oct 17, 2023
0e62c4d
remove copying all outputs by default
ansobolev Oct 18, 2023
ea9f1d4
Merge pull request #1 from tpurcell90/restart-maker
tpurcell90 Oct 18, 2023
9000c32
Move test_data for aims from `aims/test_data` to `test_data/aims`
tpurcell90 Oct 19, 2023
3e114bd
Merge branch 'main' into atomate2-aims
utf Oct 19, 2023
915ede8
Compress all test_data files
tpurcell90 Oct 19, 2023
346cf78
Merge branch 'atomate2-aims' of github.com:tpurcell90/atomate2 into a…
tpurcell90 Oct 19, 2023
2b855c9
Fix linter errors
tpurcell90 Oct 19, 2023
26ad822
`write_aim_input_set` structure->atoms name convention
tpurcell90 Oct 19, 2023
8bb8c6b
remove debug print lines
tpurcell90 Oct 19, 2023
997a576
Create AIMS_CMD setting
tpurcell90 Oct 19, 2023
6696071
Fix the reading of previous images in the socket calculator
tpurcell90 Oct 19, 2023
5e30355
Automatically gzip output files when jobs end
tpurcell90 Oct 19, 2023
f038749
Addressing comments by @utf
ansobolev Oct 19, 2023
c9ca05f
Revert change in files.py
tpurcell90 Oct 19, 2023
434a15f
Merge branch 'main' into atomate2-aims
tpurcell90 Oct 20, 2023
edb4e82
Correct issues that came from resolving merge conflicts
tpurcell90 Oct 20, 2023
f291c81
Added test for GW molecule maker
ansobolev Oct 20, 2023
717cc22
Fix typing and annotations lint errors
tpurcell90 Oct 20, 2023
fd5f423
Rewritten GW convergence maker and added test for that
ansobolev Oct 20, 2023
05aad05
Merge remote-tracking branch 'origin/atomate2-aims' into atomate2-aims
ansobolev Oct 20, 2023
498ab75
Add Flow type hint to common workflow make
tpurcell90 Oct 20, 2023
3dcd2a9
Modify species_dir paths
tpurcell90 Oct 20, 2023
fc424f3
Factored update file job out of convergence maker
ansobolev Oct 20, 2023
de22985
Refactor the ConvergenceMaker to be a flow maker
tpurcell90 Oct 20, 2023
6a35895
Remove `convergence_iteration`
tpurcell90 Oct 20, 2023
526ea49
Move ConvergenceMaker to `aims.jobs.convergence`
tpurcell90 Oct 20, 2023
a094278
Removed default values from of convergence maker
ansobolev Oct 20, 2023
78427b2
Merge remote-tracking branch 'origin/atomate2-aims' into atomate2-aims
ansobolev Oct 20, 2023
780f6c6
Remove convergenceMaker.last_idx and detour from ConvergenceMaker
tpurcell90 Oct 20, 2023
01984d8
Removed default values from of convergence maker
ansobolev Oct 20, 2023
5618dff
Update run aims docstrings
tpurcell90 Oct 20, 2023
5ce12ee
Remove phonon_utils file and move get_factor to common.phonons.jobs
tpurcell90 Oct 20, 2023
2f51cb5
Merge branch 'atomate2-aims' of github.com:tpurcell90/atomate2 into a…
tpurcell90 Oct 20, 2023
a2ee7dd
Update src/atomate2/forcefields/flows/phonons.py
tpurcell90 Oct 20, 2023
43b5160
fix linter errors from accepting the previous change
tpurcell90 Oct 20, 2023
1abef6e
Removed correct default values from of convergence maker
ansobolev Oct 20, 2023
7fa04de
Fix a typo in the docs
ansobolev Oct 20, 2023
dd9b53c
Move get_factor to common.schemas.phonons
tpurcell90 Oct 20, 2023
ef0f4ee
Typo fix
tpurcell90 Oct 20, 2023
7e0fded
Merge branch 'main' into atomate2-aims
tpurcell90 Oct 30, 2023
7de6ad6
Add compare_files to the input set generator tests
tpurcell90 Oct 31, 2023
2169e47
prev_vasp_dir -> prev_dir
tpurcell90 Oct 31, 2023
bf1463e
Merge branch 'main' into atomate2-aims
tpurcell90 Nov 8, 2023
6dad72b
Remove MSONaableAtoms from src
tpurcell90 Nov 9, 2023
2407a26
Changed band structure input to use Pymatgen structures
ansobolev Nov 9, 2023
88d8761
Changed test fixture to use Pymatgen structures
ansobolev Nov 9, 2023
c7d9e11
Changed band structure input set generators
ansobolev Nov 9, 2023
30e4db4
Removing MSONableAtoms from tests
tpurcell90 Nov 9, 2023
6eb27d1
Merge branch 'main' of https://github.com/materialsproject/atomate2 i…
tpurcell90 Nov 9, 2023
4907413
Fix some bugs with the changes
tpurcell90 Nov 9, 2023
3df0f5f
Update refrence files
tpurcell90 Nov 9, 2023
9b77329
Commit to merge in tests for bandpath
tpurcell90 Nov 9, 2023
5469312
Merge branch 'atomate2-aims' of github.com:tpurcell90/atomate2 into a…
tpurcell90 Nov 9, 2023
25bc647
Update the ref files for bs and gw tests
tpurcell90 Nov 9, 2023
7aa8b9b
Correct the band structure and gw tests
tpurcell90 Nov 9, 2023
5682a6a
Update ref data for a final time
tpurcell90 Nov 9, 2023
cbd4015
Bug Fix
tpurcell90 Nov 9, 2023
78dc195
Correct socket calculations
tpurcell90 Nov 9, 2023
4e054f3
Remove unused modules
tpurcell90 Nov 9, 2023
5ddd690
Test if master pymatgen will pass tests
tpurcell90 Nov 10, 2023
c71f1c0
update pymatgen version
tpurcell90 Nov 13, 2023
1a27c19
Be more prcsie with output band checks
tpurcell90 Nov 13, 2023
3ebea3f
Remove io tests
tpurcell90 Nov 13, 2023
ec157db
Some cleaning up
ansobolev Nov 13, 2023
13186a9
Fix issues with calculation schemas
tpurcell90 Nov 15, 2023
69148b0
Merge branch 'atomate2-aims' of github.com:tpurcell90/atomate2 into a…
tpurcell90 Nov 15, 2023
0745866
Update pyproject.toml
tpurcell90 Nov 16, 2023
57fc052
Convergence maker rewritten
ansobolev Nov 17, 2023
77c2c5f
Remove sets from atomate2.aims
tpurcell90 Dec 19, 2023
bd664ce
Replace atomate.aims.io.sets with pymatgen.io.aims.sets
tpurcell90 Dec 19, 2023
afa6984
remove img_format from PhononBSPlotter call
tpurcell90 Dec 19, 2023
30089bd
Merge branch 'main' into atomate2-aims
tpurcell90 Jan 16, 2024
8fbc023
Merge branch 'atomate2-aims' of github.com:tpurcell90/atomate2 into a…
tpurcell90 Jan 16, 2024
5adabde
fix lint errors
tpurcell90 Jan 17, 2024
089a799
Update tests from inputsets/generators moved to pymatgen
tpurcell90 Jan 30, 2024
8f9bd78
Remove old test files
tpurcell90 Jan 30, 2024
6fb5f8b
Fix pre-commit hooks
tpurcell90 Jan 30, 2024
fa7315e
Update pymatgen version
tpurcell90 Feb 8, 2024
174d874
Merge branch 'main' into atomate2-aims
tpurcell90 Feb 8, 2024
24ca9e2
Merge branch 'main' into atomate2-aims
tpurcell90 Feb 17, 2024
1ee0172
Update pymatgen vesrion on this branch
tpurcell90 Feb 17, 2024
f58c34c
Update monty to see if this works
tpurcell90 Feb 17, 2024
e782ad9
Merge branch 'main' into atomate2-aims
tpurcell90 Feb 21, 2024
7c2a781
Fix merge conflicts
tpurcell90 Feb 21, 2024
317549b
1) Update pyproject to use monty==2024.2.2
tpurcell90 Feb 21, 2024
639e1c8
pre-commit got removed by accident
tpurcell90 Feb 21, 2024
52b98a7
Merge branch 'main' into atomate2-aims
tpurcell90 Feb 27, 2024
07d654a
Merge branch 'main' into atomate2-aims
tpurcell90 Feb 28, 2024
c2ac17a
Fix Lint errors
tpurcell90 Feb 28, 2024
b3e7029
revert pyproject changes
tpurcell90 Feb 28, 2024
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 7 additions & 0 deletions docs/about/contributors.md
Original file line number Diff line number Diff line change
Expand Up @@ -103,6 +103,13 @@ University of Arizona
[tpurcell90]: https://github.com/tpurcell90
[0000-0003-4564-7206]: https://orcid.org/0000-0003-4564-7206

**Andrei Sobolev** [![gh]][ansobolev] [![orc]][0000-0001-5086-6601] \
Software Scientist \
MS1P e.V.

[ansobolev]: https://github.com/ansobolev
[0000-0001-5086-6601]: https://orcid.org/0000-0001-5086-6601

**Alexander Bonkowski** [![gh]][ab5424] [![orc]][0000-0002-0525-4742] \
PhD student in Chemistry \
RWTH Aachen University
Expand Down
1 change: 1 addition & 0 deletions src/atomate2/aims/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
"""FHI-aims interface for atomate2."""
151 changes: 151 additions & 0 deletions src/atomate2/aims/files.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,151 @@
"""Functions dealing with FHI-aims files."""
from __future__ import annotations

import logging
from glob import glob
from pathlib import Path
from typing import TYPE_CHECKING

from atomate2.common.files import copy_files, get_zfile, gunzip_files
from atomate2.utils.file_client import FileClient, auto_fileclient
from atomate2.utils.path import strip_hostname

if TYPE_CHECKING:
from collections.abc import Sequence

from pymatgen.core import Molecule, Structure
from pymatgen.io.aims.sets.base import AimsInputGenerator

logger = logging.getLogger(__name__)

__all__ = ["copy_aims_outputs", "write_aims_input_set", "cleanup_aims_outputs"]


@auto_fileclient
def copy_aims_outputs(
src_dir: Path | str,
src_host: str | None = None,
additional_aims_files: list[str] | None = None,
restart_to_input: bool = False,
file_client: FileClient | None = None,
) -> None:
"""
Copy FHI-aims output files to the current directory (inspired by CP2K plugin).

Parameters
----------
src_dir : str or Path
The source directory.
src_host : str or None
The source hostname used to specify a remote filesystem. Can be given as
either "username@remote_host" or just "remote_host" in which case the username
will be inferred from the current user. If ``None``, the local filesystem will
be used as the source.
additional_aims_files : list[str]
Additional files to copy
restart_to_input : bool
Move the aims restart files to by the aims input in the new directory
file_client : .FileClient
A file client to use for performing file operations.
"""
src_dir = strip_hostname(src_dir)
logger.info(f"Copying FHI-aims inputs from {src_dir}")
directory_listing = file_client.listdir(src_dir, host=src_host)
# additional files like bands, DOS, *.cube, whatever
additional_files = additional_aims_files if additional_aims_files else []

# copy files
# (no need to copy aims.out by default; it can be added to additional_aims_files
# explicitly if needed)
files: list[str] = (
["hessian.aims", "geometry.in.next_step", "*.csc"] if restart_to_input else []
)

files += [
Path(f).name
for pattern in set(files + additional_files)
for f in glob((Path(src_dir) / pattern).as_posix())
]

all_files = [
get_zfile(directory_listing, str(r), allow_missing=True) for r in files
]
all_files = [f for f in all_files if f]

copy_files(
src_dir,
src_host=src_host,
include_files=all_files,
file_client=file_client,
)

zipped_files = [f for f in all_files if f.name.endswith("gz")]

gunzip_files(
include_files=zipped_files,
allow_missing=True,
file_client=file_client,
)

logger.info("Finished copying inputs")


def write_aims_input_set(
structure: Structure | Molecule,
input_set_generator: AimsInputGenerator,
directory: str | Path = ".",
prev_dir: str | Path | None = None,
**kwargs,
) -> None:
"""
Write FHI-aims input set.

Parameters
----------
structure : Structure or Molecule
A to write the input set for.
input_set_generator : .AimsInputGenerator
An GHI-aims input set generator.
directory : str or Path
The directory to write the input files to.
prev_dir : str or Path or None
If the input set is to be initialized from a previous calculation,
the previous calc directory
**kwargs
Keyword arguments to pass to :obj:`.AimsInputSet.write_input`.
"""
properties = kwargs.get("properties", [])
aims_is = input_set_generator.get_input_set(
structure, prev_dir=prev_dir, properties=properties
)

logger.info("Writing FHI-aims input set.")
aims_is.write_input(directory, **kwargs)


@auto_fileclient
def cleanup_aims_outputs(
directory: Path | str,
host: str | None = None,
file_patterns: Sequence[str] = (),
file_client: FileClient | None = None,
) -> None:
"""Remove unnecessary files.

Parameters
----------
directory: Path or str
Directory containing files
host: str or None
File client host
file_patterns: Sequence[str]
Glob patterns to find files for deletion.
file_client: .FileClient
A file client to use for performing file operations.
"""
files_to_delete = []
for pattern in file_patterns:
files_to_delete.extend(file_client.glob(Path(directory) / pattern, host=host))

for file in files_to_delete:
file_client.remove(file)
1 change: 1 addition & 0 deletions src/atomate2/aims/flows/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
"""Workflows for FHI-aims."""
105 changes: 105 additions & 0 deletions src/atomate2/aims/flows/core.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,105 @@
"""(Work)flows for FHI-aims."""
from __future__ import annotations

from copy import deepcopy
from dataclasses import dataclass, field
from pathlib import Path
from typing import TYPE_CHECKING, Any

from jobflow import Flow, Maker
from pymatgen.io.aims.sets.core import RelaxSetGenerator

from atomate2.aims.jobs.core import RelaxMaker

if TYPE_CHECKING:
from pymatgen.core import Molecule, Structure

from atomate2.aims.jobs.base import BaseAimsMaker


@dataclass
class DoubleRelaxMaker(Maker):
"""Double relaxation maker for FHI-aims.

A maker to perform a double relaxation in FHI-aims (first with light,
and then with tight species_defaults).

Parameters
----------
name : str
A name for the flow
relax_maker1: .BaseAimsMaker
A maker that generates the first relaxation
relax_maker2: .BaseAimsMaker
A maker that generates the second relaxation
"""

name: str = "Double relaxation"
relax_maker1: BaseAimsMaker = field(default_factory=RelaxMaker)
relax_maker2: BaseAimsMaker = field(default_factory=RelaxMaker)

def make(
self,
structure: Structure | Molecule,
prev_dir: str | Path | None = None,
) -> Flow:
"""Create a flow with two chained relaxations.

Parameters
----------
structure : Structure or Molecule
The structure to relax.
prev_dir : str or Path or None
A previous FHI-aims calculation directory to copy output files from.
"""
relax1 = self.relax_maker1.make(structure, prev_dir=prev_dir)
relax1.name += " 1"

relax2 = self.relax_maker2.make(
relax1.output.structure, prev_dir=relax1.output.dir_name
)
relax2.name += " 2"

return Flow([relax1, relax2], relax2.output, name=self.name)

@classmethod
def from_parameters(
cls,
parameters: dict[str, Any],
species_defaults: list[str] | tuple[str, str] = ("light", "tight"),
) -> DoubleRelaxMaker:
"""Create the maker from an ASE parameter set.

Creates a DoubleRelaxFlow for the same parameters with two different
species defaults.

Parameters
----------
parameters : dict
a dictionary with calculation parameters
species_defaults: list | tuple
paths for species defaults to use relative to the given `species_dir`
in parameters
"""
# various checks
if len(species_defaults) != 2:
raise ValueError(
"Two species defaults directories must be provided for DoubleRelaxFlow"
)
if "species_dir" not in parameters:
raise KeyError("Provided parameters do not include species_dir")
species_dir = Path(parameters["species_dir"])
for basis_set in species_defaults:
if not (species_dir / basis_set).exists():
basis_set_dir = (species_dir / basis_set).as_posix()
raise OSError(
f"The species defaults directory {basis_set_dir} does not exist"
)

# now the actual work begins
makers = []
for basis_set in species_defaults:
parameters["species_dir"] = (species_dir / basis_set).as_posix()
input_set = RelaxSetGenerator(user_params=deepcopy(parameters))
makers.append(RelaxMaker(input_set_generator=input_set))
return cls(relax_maker1=makers[0], relax_maker2=makers[1])
38 changes: 38 additions & 0 deletions src/atomate2/aims/flows/gw.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
"""GW workflows for FHI-aims with automatic convergence."""
from dataclasses import dataclass, field

from atomate2.aims.jobs.convergence import ConvergenceMaker
from atomate2.aims.jobs.core import GWMaker


@dataclass
class GWConvergenceMaker(ConvergenceMaker):
"""A maker to perform a GW workflow with automatic convergence in FHI-aims.

Basically a .ConvergenceMaker with adjusted defaults. Employs the fact that
GW calculations in FHI-aims scale as O(N^4) with a large prefactor, which makes
running a DFT part for any structure negligible with respect to the GW
postprocessing.

Parameters
----------
name : str
A name for the job
maker: .GWMaker
A maker for the run
criterion_name: str
A name for the convergence criterion. Must be in the run results
epsilon: float
A difference in criterion value for subsequent runs
convergence_field: str
An input parameter that changes to achieve convergence
convergence_steps: Iterable
An iterable of the possible values for the convergence field.
If the iterable is depleted and the convergence is not reached,
then the job is failed
"""

name: str = "GW convergence"
maker: GWMaker = field(default_factory=GWMaker)
criterion_name: str = "bandgap"
epsilon: float = 0.1
Loading
Loading