Skip to content

Commit 8a45af8

Browse files
Merge branch 'materialsproject:master' into master
2 parents cb4eb21 + bb37024 commit 8a45af8

File tree

19 files changed

+104
-114
lines changed

19 files changed

+104
-114
lines changed

.github/dependabot.yml

Lines changed: 0 additions & 11 deletions
This file was deleted.

.github/workflows/jekyll-gh-pages.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -27,7 +27,7 @@ jobs:
2727
runs-on: ubuntu-latest
2828
steps:
2929
- name: Checkout
30-
uses: actions/checkout@v3
30+
uses: actions/checkout@v4
3131
- name: Setup Pages
3232
uses: actions/configure-pages@v3
3333
- name: Build with Jekyll

README.md

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -87,10 +87,10 @@ If you use `pymatgen` in your research, please consider citing the following wor
8787
8888
In addition, some of `pymatgen`'s functionality is based on scientific advances/principles developed by the computational materials scientists in our team. Please refer to the [`pymatgen` docs] on how to cite them.
8989

90-
### Soliciting contributions to an updated pymatgen paper
90+
### Soliciting contributions to 2nd `pymatgen` paper
9191

9292
If you are a long-standing `pymatgen` contributor and would like to be involved in working on an updated `pymatgen` publication,
93-
please contact the maintainers [@shyuep, @mkhorton and @janosh](mailto:ongsp@ucsd.edu,m.k.horton@gmail.com,janosh@lbl.gov?subject=Contributing%20to%20updated%20pymatgen%20paper).
93+
please fill out this [co-author registration form](https://docs.google.com/forms/d/e/1FAIpQLSecIhD2YjdPGldrRTM8Go3VxVg_vjKjZAOXtIKDG7qckHLYaQ/viewform) or contact [@shyuep, @mkhorton and @janosh](mailto:ongsp@ucsd.edu,m.k.horton@gmail.com,janosh@lbl.gov?subject=Contributing%20to%20updated%20pymatgen%20paper) with questions.
9494

9595
## License
9696

dev_scripts/chemenv/explicit_permutations.py

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -91,8 +91,7 @@ class Algo:
9191
if len(cg.algorithms) != 1:
9292
raise ValueError("Multiple algorithms !")
9393
cg._algorithms = [ExplicitPermutationsAlgorithm(permutations=explicit_permutations)]
94-
newgeom_dir = "new_geometry_files"
95-
if not os.path.exists(newgeom_dir):
96-
os.makedirs(newgeom_dir)
97-
with open(f"{newgeom_dir}/{cg_symbol}.json", "w") as f:
94+
new_geom_dir = "new_geometry_files"
95+
os.makedirs(new_geom_dir, exist_ok=True)
96+
with open(f"{new_geom_dir}/{cg_symbol}.json", "w") as f:
9897
json.dump(cg.as_dict(), f)

dev_scripts/chemenv/get_plane_permutations_optimized.py

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -431,7 +431,6 @@ def random_permutations_iterator(initial_permutation, n_permutations):
431431
)
432432
if test == "y":
433433
new_geom_dir = "new_geometry_files"
434-
if not os.path.exists(new_geom_dir):
435-
os.makedirs(new_geom_dir)
434+
os.makedirs(new_geom_dir, exist_ok=True)
436435
with open(f"{new_geom_dir}/{cg_symbol}.json", "w") as file:
437436
json.dump(cg.as_dict(), file)

docs/index.md

Lines changed: 1 addition & 2 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

pymatgen/cli/pmg_config.py

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -143,8 +143,7 @@ def setup_potcars(potcar_dirs: list[str]):
143143
if len(filenames) > 0:
144144
try:
145145
base_dir = os.path.join(target_dir, basename)
146-
if not os.path.exists(base_dir):
147-
os.makedirs(base_dir)
146+
os.makedirs(base_dir, exist_ok=True)
148147
fname = filenames[0]
149148
dest = os.path.join(base_dir, os.path.basename(fname))
150149
shutil.copy(fname, dest)

pymatgen/command_line/critic2_caller.py

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -111,8 +111,8 @@ def __init__(self, input_script):
111111
self._stdout = stdout
112112
self._stderr = stderr
113113

114-
cpreport = loadfn("cpreport.json") if os.path.exists("cpreport.json") else None
115-
self._cpreport = cpreport
114+
cp_report = loadfn("cpreport.json") if os.path.exists("cpreport.json") else None
115+
self._cp_report = cp_report
116116

117117
yt = loadfn("yt.json") if os.path.exists("yt.json") else None
118118
self._yt = yt
@@ -240,7 +240,7 @@ def from_chgcar(
240240
structure,
241241
stdout=caller._stdout,
242242
stderr=caller._stderr,
243-
cpreport=caller._cpreport,
243+
cpreport=caller._cp_report,
244244
yt=caller._yt,
245245
zpsp=zpsp,
246246
)

pymatgen/electronic_structure/boltztrap.py

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -545,18 +545,19 @@ def run(
545545
if convergence and not write_input:
546546
raise ValueError("Convergence mode requires write_input to be true")
547547

548-
if self.run_type in ("BANDS", "DOS", "FERMI"):
548+
run_type = self.run_type
549+
if run_type in ("BANDS", "DOS", "FERMI"):
549550
convergence = False
550551
if self.lpfac > max_lpfac:
551552
max_lpfac = self.lpfac
552553

553-
if self.run_type == "BANDS" and self.bs.is_spin_polarized:
554+
if run_type == "BANDS" and self.bs.is_spin_polarized:
554555
print(
555-
f"Reminder: for run_type {self.run_type}, spin component are not separated! "
556+
f"Reminder: for {run_type=}, spin component are not separated! "
556557
"(you have a spin polarized band structure)"
557558
)
558559

559-
if self.run_type in ("FERMI", "DOS") and self.spin is None:
560+
if run_type in ("FERMI", "DOS") and self.spin is None:
560561
if self.bs.is_spin_polarized:
561562
raise BoltztrapError("Spin parameter must be specified for spin polarized band structures!")
562563
self.spin = 1
@@ -568,9 +569,8 @@ def run(
568569
else:
569570
path_dir = os.path.abspath(os.path.join(path_dir, dir_bz_name))
570571

571-
if not os.path.exists(path_dir):
572-
os.mkdir(path_dir)
573-
elif clear_dir:
572+
os.mkdir(path_dir, exist_ok=True)
573+
if clear_dir:
574574
for c in os.listdir(path_dir):
575575
os.remove(os.path.join(path_dir, c))
576576

pymatgen/ext/optimade.py

Lines changed: 14 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -16,9 +16,6 @@
1616
from pymatgen.util.due import Doi, due
1717
from pymatgen.util.provenance import StructureNL
1818

19-
# from retrying import retry
20-
21-
2219
# TODO: importing optimade-python-tool's data structures will make more sense
2320
Provider = namedtuple("Provider", ["name", "base_url", "description", "homepage", "prefix"])
2421

@@ -46,7 +43,9 @@ class OptimadeRester:
4643
# these aliases are provided as a convenient shortcut for users of the OptimadeRester class
4744
aliases = {
4845
"aflow": "http://aflow.org/API/optimade/",
46+
"alexandria": "https://alexandria.odbx.science",
4947
"cod": "https://www.crystallography.net/cod/optimade",
48+
"cmr": "https://cmr-optimade.fysik.dtu.dk",
5049
"mcloud.mc3d": "https://aiida.materialscloud.org/mc3d/optimade",
5150
"mcloud.mc2d": "https://aiida.materialscloud.org/mc2d/optimade",
5251
"mcloud.2dtopo": "https://aiida.materialscloud.org/2dtopo/optimade",
@@ -58,6 +57,7 @@ class OptimadeRester:
5857
"mcloud.tin-antimony-sulfoiodide": "https://aiida.materialscloud.org/tin-antimony-sulfoiodide/optimade",
5958
"mcloud.optimade-sample": "https://aiida.materialscloud.org/optimade-sample/optimade",
6059
"mp": "https://optimade.materialsproject.org",
60+
"mpdd": "http://mpddoptimade.phaseslab.org",
6161
"mpds": "https://api.mpds.io",
6262
"nmd": "https://nomad-lab.eu/prod/rae/optimade/",
6363
"odbx": "https://optimade.odbx.science",
@@ -154,11 +154,8 @@ def describe(self):
154154
provider_text = "\n".join(map(str, (provider for provider in self._providers.values() if provider)))
155155
return f"OptimadeRester connected to:\n{provider_text}"
156156

157-
# @retry(stop_max_attempt_number=3, wait_random_min=1000, wait_random_max=2000)
158157
def _get_json(self, url):
159-
"""Retrieves JSON, will attempt to (politely) try again on failure subject to a
160-
random delay and a maximum number of attempts.
161-
"""
158+
"""Retrieves and returns JSON resource from given url."""
162159
return self.session.get(url, timeout=self._timeout).json()
163160

164161
@staticmethod
@@ -215,8 +212,11 @@ def get_structures(
215212
elements: List of elements
216213
nelements: Number of elements, e.g. 4 or [2, 5] for the range >=2 and <=5
217214
nsites: Number of sites, e.g. 4 or [2, 5] for the range >=2 and <=5
218-
chemical_formula_anonymous: Anonymous chemical formula
219-
chemical_formula_hill: Chemical formula following Hill convention
215+
chemical_formula_anonymous: The desired chemical formula in OPTIMADE anonymous formula format
216+
(NB. The ordering is reversed from the pymatgen format, e.g., pymatgen "ABC2" should become "A2BC").
217+
chemical_formula_hill: The desired chemical formula in the OPTIMADE take on the Hill formula format.
218+
(NB. Again, this is different from the pymatgen format, as the OPTIMADE version is a reduced chemical
219+
formula simply using the IUPAC/Hill ordering.)
220220
221221
Returns:
222222
dict[str, Structure]: keyed by that database provider's id system
@@ -253,8 +253,11 @@ def get_snls(
253253
elements: List of elements
254254
nelements: Number of elements, e.g. 4 or [2, 5] for the range >=2 and <=5
255255
nsites: Number of sites, e.g. 4 or [2, 5] for the range >=2 and <=5
256-
chemical_formula_anonymous: Anonymous chemical formula
257-
chemical_formula_hill: Chemical formula following Hill convention
256+
chemical_formula_anonymous: The desired chemical formula in OPTIMADE anonymous formula format
257+
(NB. The ordering is reversed from the pymatgen format, e.g., pymatgen "ABC2" should become "A2BC").
258+
chemical_formula_hill: The desired chemical formula in the OPTIMADE take on the Hill formula format.
259+
(NB. Again, this is different from the pymatgen format, as the OPTIMADE version is a reduced chemical
260+
formula simply using the IUPAC/Hill ordering.)
258261
additional_response_fields: Any additional fields desired from the OPTIMADE API,
259262
these will be stored under the `'_optimade'` key in each `StructureNL.data` dictionary.
260263

pymatgen/io/abinit/inputs.py

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -614,8 +614,7 @@ def __str__(self):
614614
def write(self, filepath="run.abi"):
615615
"""Write the input file to file to filepath."""
616616
dirname = os.path.dirname(os.path.abspath(filepath))
617-
if not os.path.exists(dirname):
618-
os.makedirs(dirname)
617+
os.makedirs(dirname, exist_ok=True)
619618

620619
# Write the input file.
621620
with open(filepath, "w") as fh:

pymatgen/io/cp2k/sets.py

Lines changed: 6 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -507,11 +507,10 @@ def match_elecs(x):
507507
break
508508

509509
if basis is None:
510-
if basis_and_potential.get(el, {}).get("basis"):
511-
warnings.warn(f"Unable to validate basis for {el}. Exact name provided will be put in input file.")
512-
basis = basis_and_potential[el].get("basis")
513-
else:
514-
raise ValueError("No explicit basis found and matching has failed.")
510+
if not basis_and_potential.get(el, {}).get("basis"):
511+
raise ValueError(f"No explicit basis found for {el} and matching has failed.")
512+
warnings.warn(f"Unable to validate basis for {el}. Exact name provided will be put in input file.")
513+
basis = basis_and_potential[el].get("basis")
515514

516515
if aux_basis is None and basis_and_potential.get(el, {}).get("aux_basis"):
517516
warnings.warn(
@@ -528,7 +527,7 @@ def match_elecs(x):
528527
else:
529528
raise ValueError("No explicit potential found and matching has failed.")
530529

531-
if basis.filename:
530+
if hasattr(basis, "filename"):
532531
data["basis_filenames"].append(basis.filename)
533532
pfn1 = data.get("potential_filename")
534533
pfn2 = potential.filename
@@ -539,11 +538,7 @@ def match_elecs(x):
539538
)
540539
data["potential_filename"] = pfn2
541540

542-
data[el] = {
543-
"basis": basis,
544-
"aux_basis": aux_basis,
545-
"potential": potential,
546-
}
541+
data[el] = {"basis": basis, "aux_basis": aux_basis, "potential": potential}
547542
return data
548543

549544
@staticmethod

pymatgen/io/feff/sets.py

Lines changed: 10 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -91,8 +91,8 @@ def write_input(self, output_dir=".", make_dir_if_not_present=True):
9191
make_dir_if_not_present: Set to True if you want the directory (
9292
and the whole path) to be created if it is not present.
9393
"""
94-
if make_dir_if_not_present and not os.path.exists(output_dir):
95-
os.makedirs(output_dir)
94+
if make_dir_if_not_present:
95+
os.makedirs(output_dir, exist_ok=True)
9696

9797
feff = self.all_input()
9898

@@ -282,27 +282,27 @@ def __str__(self):
282282
output.append("")
283283
return "\n".join(output)
284284

285-
@staticmethod
286-
def from_directory(input_dir):
285+
@classmethod
286+
def from_directory(cls, input_dir):
287287
"""
288288
Read in a set of FEFF input files from a directory, which is
289289
useful when existing FEFF input needs some adjustment.
290290
"""
291291
sub_d = {}
292292
for fname, ftype in [("HEADER", Header), ("PARAMETERS", Tags)]:
293-
fullzpath = zpath(os.path.join(input_dir, fname))
294-
sub_d[fname.lower()] = ftype.from_file(fullzpath)
293+
full_zpath = zpath(os.path.join(input_dir, fname))
294+
sub_d[fname.lower()] = ftype.from_file(full_zpath)
295295

296296
# Generation of FEFFDict set requires absorbing atom, need to search
297297
# the index of absorption atom in the structure according to the
298298
# distance matrix and shell species information contained in feff.inp
299299

300300
absorber_index = []
301301
radius = None
302-
feffinp = zpath(f"{input_dir}/feff.inp")
302+
feff_inp = zpath(f"{input_dir}/feff.inp")
303303

304304
if "RECIPROCAL" not in sub_d["parameters"]:
305-
input_atoms = Atoms.cluster_from_file(feffinp)
305+
input_atoms = Atoms.cluster_from_file(feff_inp)
306306
shell_species = np.array([x.species_string for x in input_atoms])
307307

308308
# First row of distance matrix represents the distance from the absorber to
@@ -313,12 +313,7 @@ def from_directory(input_dir):
313313
from math import ceil
314314

315315
radius = int(
316-
ceil(
317-
input_atoms.get_distance(
318-
input_atoms.index(input_atoms[0]),
319-
input_atoms.index(input_atoms[-1]),
320-
)
321-
)
316+
ceil(input_atoms.get_distance(input_atoms.index(input_atoms[0]), input_atoms.index(input_atoms[-1])))
322317
)
323318

324319
for site_index, site in enumerate(sub_d["header"].struct):
@@ -342,7 +337,7 @@ def from_directory(input_dir):
342337
CONFIG = loadfn(f"{MODULE_DIR}/MPXANESSet.yaml")
343338
if radius is None:
344339
radius = 10
345-
return FEFFDictSet(
340+
return cls(
346341
absorber_index[0],
347342
sub_d["header"].struct,
348343
radius=radius,

pymatgen/io/lammps/inputs.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1077,8 +1077,8 @@ def write_lammps_inputs(
10771077
variables = {} if settings is None else settings
10781078
template = Template(script_template)
10791079
input_script = template.safe_substitute(**variables)
1080-
if make_dir_if_not_present and not os.path.exists(output_dir):
1081-
os.makedirs(output_dir)
1080+
if make_dir_if_not_present:
1081+
os.makedirs(output_dir, exist_ok=True)
10821082
with open(os.path.join(output_dir, script_filename), "w") as f:
10831083
f.write(input_script)
10841084
read_data = re.search(r"read_data\s+(.*)\n", input_script)

0 commit comments

Comments
 (0)