Skip to content

Commit 8f8253c

Browse files
committed
fix: change behavior to warning and use pytest parametrize to test it.
1 parent 40e8773 commit 8f8253c

File tree

2 files changed

+58
-36
lines changed

2 files changed

+58
-36
lines changed

src/diffpy/structure/structure.py

Lines changed: 8 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@
1717
import copy as copymod
1818

1919
import numpy
20+
import warnings
2021

2122
from diffpy.structure.atom import Atom
2223
from diffpy.structure.lattice import Lattice
@@ -175,14 +176,19 @@ def add_new_atom(self, *args, **kwargs):
175176
176177
Raises
177178
------
178-
ValueError
179+
UserWarning
179180
If an atom with the same element/type and coordinates already exists.
180181
"""
181182
kwargs["lattice"] = self.lattice
182183
atom = Atom(*args, **kwargs)
183184
for existing in self:
184185
if existing.element == atom.element and numpy.allclose(existing.xyz, atom.xyz):
185-
raise ValueError(f"Duplicate atom {atom.element} already exists at {atom.xyz!r}")
186+
warnings.warn(
187+
f"Duplicate atom {atom.element} already exists at {atom.xyz!r}",
188+
category=UserWarning,
189+
stacklevel=2,
190+
)
191+
break
186192
self.append(atom, copy=False)
187193
return
188194

tests/test_structure.py

Lines changed: 50 additions & 34 deletions
Original file line numberDiff line numberDiff line change
@@ -120,41 +120,7 @@ def test___copy__(self):
120120
# """check Structure.getLastAtom()"""
121121
# return
122122

123-
def test_add_new_atom(self):
124-
"""Check Structure.add_new_item()"""
125-
# Case 1: valid atom added to an empty structure.
126-
# Expect the atom list length to go from 0 to 1.
127-
# Expect the atom attributes are successfully loaded.
128-
s_lat = Lattice()
129-
structure = Structure(lattice=s_lat)
130-
length = len(structure)
131-
structure.add_new_atom(atype="C", xyz=[0.1, 0.2, 0.3])
132-
expected = len(structure)
133-
actual = length + 1
134-
assert expected == actual
135-
atom_object = structure[-1]
136-
assert atom_object.element == "C"
137-
assert numpy.allclose(atom_object.xyz, [0.1, 0.2, 0.3])
138123

139-
# Case 2: valid atom added to existing atom list.
140-
# Expect the atom list length to go from 1 to 2.
141-
# Expect the atom attributes are successfully loaded.
142-
length = len(structure)
143-
structure.add_new_atom(atype="Ni", xyz=[0.8, 1.2, 0.9])
144-
expected = len(structure)
145-
actual = length + 1
146-
assert expected == actual
147-
atom_object = structure[-1]
148-
assert atom_object.element == "Ni"
149-
assert numpy.allclose(atom_object.xyz, [0.8, 1.2, 0.9])
150-
151-
# Case 3: duplicated atom added to the existing atom list.
152-
# Expect the atom not to be added and gives a ValueError.
153-
with pytest.raises(ValueError, match=r"Duplicate atom C already exists at array\(\[0\.1, 0\.2, 0\.3\]\)"):
154-
structure.add_new_atom(atype="C", xyz=[0.1, 0.2, 0.3])
155-
actual = len(structure)
156-
expected = 2
157-
assert expected == actual
158124

159125
def test_addNewAtom(self):
160126
"""Duplicate test for the deprecated addNewAtom method.
@@ -655,6 +621,56 @@ def test_pickling(self):
655621
# End of class TestStructure
656622

657623
# ----------------------------------------------------------------------------
624+
@pytest.mark.parametrize(
625+
"existing, atype, xyz, expected_len, expected_element, expected_xyz",
626+
[
627+
# Case 1: valid atom added to an empty structure.
628+
# Expect the atom list length to go from 0 to 1.
629+
# Expect the atom attributes are successfully loaded.
630+
(
631+
None,
632+
"C",
633+
[0.1, 0.2, 0.3],
634+
1,
635+
"C",
636+
[0.1, 0.2, 0.3],
637+
),
638+
# Case 2: valid atom added to existing atom list.
639+
# Expect the atom list length to go from 1 to 2.
640+
# Expect the atom attributes are successfully loaded.
641+
(
642+
[Atom("C", [0, 0, 0])],
643+
"Ni",
644+
[0.8, 1.2, 0.9],
645+
2,
646+
"Ni",
647+
[0.8, 1.2, 0.9],
648+
),
649+
],
650+
)
651+
def test_add_new_atom(existing, atype, xyz, expected_len, expected_element, expected_xyz):
652+
"""Check Structure.add_new_item()"""
653+
structure = Structure(existing, lattice=Lattice())
654+
structure.add_new_atom(atype=atype, xyz=xyz)
655+
actual_length = len(structure)
656+
assert expected_len == actual_length
657+
atom_object = structure[-1]
658+
assert atom_object.element == expected_element
659+
assert numpy.allclose(atom_object.xyz, expected_xyz)
660+
661+
662+
def test_add_new_atom_duplicate():
663+
# Case 3: duplicated atom added to the existing atom list.
664+
# Expect the atom not to be added and gives a ValueError.
665+
structure = Structure(
666+
[Atom("C", [0.1, 0.2, 0.3]), Atom("Ni", [0.8, 1.2, 0.9])],
667+
lattice=Lattice(),
668+
)
669+
with pytest.warns(UserWarning):
670+
structure.add_new_atom(atype="C", xyz=[0.1, 0.2, 0.3])
671+
assert len(structure) == 3
672+
assert structure[-1].element == "C"
673+
assert numpy.allclose(structure[-1].xyz, [0.1, 0.2, 0.3])
658674

659675
if __name__ == "__main__":
660676
unittest.main()

0 commit comments

Comments
 (0)