Skip to content

Commit bb78218

Browse files
authored
Adding impl/test crumbs for nucDir (#1482)
1 parent 9856649 commit bb78218

4 files changed

Lines changed: 136 additions & 19 deletions

File tree

‎armi/nucDirectory/elements.py‎

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,10 @@
1616
This module provides fundamental element information to be used throughout the framework
1717
and applications.
1818
19+
.. impl:: A tool for querying basic data for elements of the periodic table.
20+
:id: I_ARMI_ND_ELEMENTS0
21+
:implements: R_ARMI_ND_ELEMENTS
22+
1923
The element class structure is outlined :ref:`here <elements-class-diagram>`.
2024
2125
.. _elements-class-diagram:
@@ -149,6 +153,10 @@ def __init__(self, z, symbol, name, phase="UNKNOWN", group="UNKNOWN"):
149153
"""
150154
Creates an instance of an Element.
151155
156+
.. impl:: An element of the periodic table.
157+
:id: I_ARMI_ND_ELEMENTS1
158+
:implements: R_ARMI_ND_ELEMENTS
159+
152160
Parameters
153161
----------
154162
z : int

‎armi/nucDirectory/nuclideBases.py‎

Lines changed: 54 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,10 @@
1515
This module provides fundamental nuclide information to be used throughout the framework
1616
and applications.
1717
18+
.. impl:: Isotopes and isomers can be queried by name, label, MC2-3 ID, MCNP ID, and AAAZZZS ID.
19+
:id: I_ARMI_ND_ISOTOPES0
20+
:implements: R_ARMI_ND_ISOTOPES
21+
1822
The nuclide class structure is outlined :ref:`here <nuclide-bases-class-diagram>`.
1923
2024
.. _nuclide-bases-class-diagram:
@@ -423,7 +427,7 @@ def _processBurnData(self, burnInfo):
423427
)
424428

425429
def getDecay(self, decayType):
426-
r"""Get a :py:class:`~armi.nucDirectory.transmutations.DecayMode`.
430+
"""Get a :py:class:`~armi.nucDirectory.transmutations.DecayMode`.
427431
428432
Retrieve the first :py:class:`~armi.nucDirectory.transmutations.DecayMode`
429433
matching the specified decType.
@@ -493,7 +497,12 @@ def getAAAZZZSId(self):
493497

494498

495499
class NuclideBase(INuclide, IMcnpNuclide):
496-
"""Represents an individual nuclide/isotope."""
500+
"""Represents an individual nuclide/isotope.
501+
502+
.. impl:: Isotopes and isomers can be queried by name and label.
503+
:id: I_ARMI_ND_ISOTOPES1
504+
:implements: R_ARMI_ND_ISOTOPES
505+
"""
497506

498507
def __init__(self, element, a, weight, abundance, state, halflife):
499508
IMcnpNuclide.__init__(self)
@@ -558,22 +567,35 @@ def getNaturalIsotopics(self):
558567
return self.element.getNaturalIsotopics()
559568

560569
def getMcc2Id(self):
561-
"""Return the MC2-2 nuclide identification label based on the ENDF/B-V.2 cross section library."""
570+
"""Return the MC2-2 nuclide identification label based on the ENDF/B-V.2 cross section library.
571+
572+
.. impl:: Isotopes and isomers can be queried by MC2-2 ID.
573+
:id: I_ARMI_ND_ISOTOPES2
574+
:implements: R_ARMI_ND_ISOTOPES
575+
"""
562576
return self.mcc2id
563577

564578
def getMcc3Id(self):
565-
"""Return the MC2-3 nuclide identification label based on the ENDF/B-VII.0 cross section library."""
579+
"""Return the MC2-3 nuclide identification label based on the ENDF/B-VII.0 cross section library.
580+
581+
.. impl:: Isotopes and isomers can be queried by MC2-3 ID.
582+
:id: I_ARMI_ND_ISOTOPES3
583+
:implements: R_ARMI_ND_ISOTOPES
584+
"""
566585
return self.mcc3id
567586

568587
def getMcnpId(self):
569588
"""
570589
Gets the MCNP label for this nuclide.
571590
591+
.. impl:: Isotopes and isomers can be queried by MCNP ID.
592+
:id: I_ARMI_ND_ISOTOPES4
593+
:implements: R_ARMI_ND_ISOTOPES
594+
572595
Returns
573596
-------
574597
id : str
575598
The MCNP ID e.g. ``92235``, ``94239``, ``6000``
576-
577599
"""
578600
z, a = self.z, self.a
579601

@@ -595,6 +617,10 @@ def getAAAZZZSId(self):
595617
"""
596618
Return a string that is ordered by the mass number, A, the atomic number, Z, and the isomeric state, S.
597619
620+
.. impl:: Isotopes and isomers can be queried by AAAZZZS ID.
621+
:id: I_ARMI_ND_ISOTOPES5
622+
:implements: R_ARMI_ND_ISOTOPES
623+
598624
Notes
599625
-----
600626
An example would be for U235, where A=235, Z=92, and S=0, returning ``2350920``.
@@ -629,7 +655,6 @@ def getEndfMatNum(self):
629655
-------
630656
id : str
631657
The MAT number e.g. ``9237`` for U238
632-
633658
"""
634659
z, a = self.z, self.a
635660
if self.element.symbol in BASE_ENDFB7_MAT_NUM:
@@ -679,7 +704,7 @@ def __repr__(self):
679704
return f"<{self.__class__.__name__} {self.name}: Z:{self.z}, W:{self.weight:<12.6e}, Label:{self.label}>"
680705

681706
def getNaturalIsotopics(self):
682-
r"""Gets the natural isotopics root :py:class:`~elements.Element`.
707+
"""Gets the natural isotopics root :py:class:`~elements.Element`.
683708
684709
Gets the naturally occurring nuclides for this nuclide.
685710
@@ -789,7 +814,7 @@ def __lt__(self, other):
789814
)
790815

791816
def getNaturalIsotopics(self):
792-
r"""Gets the natural isotopics, an empty iterator.
817+
"""Gets the natural isotopics, an empty iterator.
793818
794819
Gets the naturally occurring nuclides for this nuclide.
795820
@@ -855,7 +880,7 @@ def __lt__(self, other):
855880
)
856881

857882
def getNaturalIsotopics(self):
858-
r"""Gets the natural isotopics, an empty iterator.
883+
"""Gets the natural isotopics, an empty iterator.
859884
860885
Gets the naturally occurring nuclides for this nuclide.
861886
@@ -1115,12 +1140,12 @@ def factory():
11151140
"Nuclides are already initialized and cannot be re-initialized unless "
11161141
"`nuclideBases.destroyGlobalNuclides` is called first."
11171142
)
1118-
__addNuclideBases()
1143+
addNuclideBases()
11191144
__addNaturalNuclideBases()
11201145
__addDummyNuclideBases()
11211146
__addLumpedFissionProductNuclideBases()
1122-
__updateNuclideBasesForSpecialCases()
1123-
__readMCCNuclideData()
1147+
updateNuclideBasesForSpecialCases()
1148+
readMCCNuclideData()
11241149
__renormalizeNuclideToElementRelationship()
11251150
__deriveElementalWeightsByNaturalNuclideAbundances()
11261151

@@ -1130,11 +1155,15 @@ def factory():
11301155
thermalScattering.factory()
11311156

11321157

1133-
def __addNuclideBases():
1158+
def addNuclideBases():
11341159
"""
11351160
Read natural abundances of any natural nuclides.
11361161
11371162
This adjusts already-existing NuclideBases and Elements with the new information.
1163+
1164+
.. impl:: Separating natural abundance data from code.
1165+
:id: I_ARMI_ND_DATA0
1166+
:implements: R_ARMI_ND_DATA
11381167
"""
11391168
with open(os.path.join(context.RES, "nuclides.dat")) as f:
11401169
for line in f:
@@ -1190,8 +1219,13 @@ def __addLumpedFissionProductNuclideBases():
11901219
LumpNuclideBase(name="LREGN", weight=1.0)
11911220

11921221

1193-
def __readMCCNuclideData():
1194-
"""Read in the label data for the MC2-2 and MC2-3 cross section codes to the nuclide bases."""
1222+
def readMCCNuclideData():
1223+
"""Read in the label data for the MC2-2 and MC2-3 cross section codes to the nuclide bases.
1224+
1225+
.. impl:: Separating MCC data from code.
1226+
:id: I_ARMI_ND_DATA1
1227+
:implements: R_ARMI_ND_DATA
1228+
"""
11951229
with open(os.path.join(context.RES, "mcc-nuclides.yaml"), "r") as f:
11961230
yaml = YAML(typ="rt")
11971231
nuclides = yaml.load(f)
@@ -1208,10 +1242,14 @@ def __readMCCNuclideData():
12081242
byMcc3Id[nb.getMcc3Id()] = nb
12091243

12101244

1211-
def __updateNuclideBasesForSpecialCases():
1245+
def updateNuclideBasesForSpecialCases():
12121246
"""
12131247
Update the nuclide bases for special case name changes.
12141248
1249+
.. impl:: The special case name Am242g is supported.
1250+
:id: I_ARMI_ND_ISOTOPES6
1251+
:implements: R_ARMI_ND_ISOTOPES
1252+
12151253
Notes
12161254
-----
12171255
This function is specifically added to change the definition of

‎armi/nucDirectory/tests/test_elements.py‎

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,14 +35,32 @@ def test_elements_elementBulkProperties(self):
3535
self.assertIsNotNone(ee.standardWeight)
3636

3737
def test_element_elementByNameReturnsElement(self):
38+
"""Get elements by name.
39+
40+
.. test:: Get elements by name.
41+
:id: I_ARMI_ND_ELEMENTS0
42+
:tests: R_ARMI_ND_ELEMENTS
43+
"""
3844
for ee in elements.byZ.values():
3945
self.assertIs(ee, elements.byName[ee.name])
4046

4147
def test_element_elementByZReturnsElement(self):
48+
"""Get elements by Z.
49+
50+
.. test:: Get elements by Z.
51+
:id: I_ARMI_ND_ELEMENTS1
52+
:tests: R_ARMI_ND_ELEMENTS
53+
"""
4254
for ee in elements.byZ.values():
4355
self.assertIs(ee, elements.byZ[ee.z])
4456

4557
def test_element_elementBySymbolReturnsElement(self):
58+
"""Get elements by symbol.
59+
60+
.. test:: Get elements by symbol.
61+
:id: I_ARMI_ND_ELEMENTS2
62+
:tests: R_ARMI_ND_ELEMENTS
63+
"""
4664
for ee in elements.byZ.values():
4765
self.assertIs(ee, elements.bySymbol[ee.symbol])
4866

@@ -84,6 +102,10 @@ def test_element_isNaturallyOccurring(self):
84102
85103
Uses RIPL definitions of naturally occurring. Protactinium is debated as naturally
86104
occurring. Yeah it exists as a U235 decay product but it's kind of pseudo-natural.
105+
106+
.. test:: Get elements by Z, to show if they are naturally occurring.
107+
:id: I_ARMI_ND_ELEMENTS3
108+
:tests: R_ARMI_ND_ELEMENTS
87109
"""
88110
for ee in elements.byZ.values():
89111
if ee.z == 43 or ee.z == 61 or 84 <= ee.z <= 89 or ee.z >= 93:
@@ -104,6 +126,12 @@ def test_abundancesAddToOne(self):
104126
)
105127

106128
def test_isHeavyMetal(self):
129+
"""Get elements by Z.
130+
131+
.. test:: Get elements by Z, to show if they are heavy metals.
132+
:id: I_ARMI_ND_ELEMENTS4
133+
:tests: R_ARMI_ND_ELEMENTS
134+
"""
107135
for ee in elements.byZ.values():
108136
if ee.z > 89:
109137
self.assertTrue(ee.isHeavyMetal())

‎armi/nucDirectory/tests/test_nuclideBases.py‎

Lines changed: 46 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -137,6 +137,12 @@ def test_NaturalNuclide_atomicWeightIsAverageOfNaturallyOccuringIsotopes(self):
137137
)
138138

139139
def test_nucBases_labelAndNameCollsionsAreForSameNuclide(self):
140+
"""The name and labels for correct for nuclides.
141+
142+
.. test:: Validate the name, label, and DB name are accessible for nuclides.
143+
:id: I_ARMI_ND_ISOTOPES0
144+
:tests: R_ARMI_ND_ISOTOPES
145+
"""
140146
count = 0
141147
for nuc in nuclideBases.where(lambda nn: nn.name == nn.label):
142148
count += 1
@@ -185,6 +191,12 @@ def test_nucBases_imposeBurnChainTransmutationBulkStatistics(self):
185191
) # ternary fission
186192

187193
def test_nucBases_imposeBurn_nuSF(self):
194+
"""Test the nuclide data from file (specifically neutrons / sponaneous fission).
195+
196+
.. test:: Test that nuclide data was read from file instead of code.
197+
:id: I_ARMI_ND_DATA0
198+
:tests: R_ARMI_ND_DATA
199+
"""
188200
actual = {
189201
nn.name: nn.nuSF for nn in nuclideBases.where(lambda nn: nn.nuSF > 0.0)
190202
}
@@ -235,6 +247,12 @@ def test_nucBases_AllDatabaseNamesAreUnique(self):
235247
)
236248

237249
def test_nucBases_Am242m(self):
250+
"""Test the correct am242g and am242m abbreviations are supported.
251+
252+
.. test:: Specifically test for Am242 and Am242g because it is a special case.
253+
:id: I_ARMI_ND_ISOTOPES1
254+
:tests: R_ARMI_ND_ISOTOPES
255+
"""
238256
am242m = nuclideBases.byName["AM242"]
239257
self.assertEqual(am242m, nuclideBases.byName["AM242M"])
240258
self.assertEqual("nAm242m", am242m.getDatabaseName())
@@ -263,6 +281,12 @@ def test_getDecay(self):
263281
self.assertIsNone(nb.getDecay("sf"))
264282

265283
def test_getEndfMatNum(self):
284+
"""Test get nuclides by name.
285+
286+
.. test:: Test get nuclides by name.
287+
:id: I_ARMI_ND_ISOTOPES2
288+
:tests: R_ARMI_ND_ISOTOPES
289+
"""
266290
self.assertEqual(nuclideBases.byName["U235"].getEndfMatNum(), "9228")
267291
self.assertEqual(nuclideBases.byName["U238"].getEndfMatNum(), "9237")
268292
self.assertEqual(nuclideBases.byName["PU239"].getEndfMatNum(), "9437")
@@ -365,7 +389,12 @@ def test_curieDefinitionWithRa226(self):
365389
self.assertAlmostEqual(activity, 0.9885593, places=6)
366390

367391
def test_loadMcc2Data(self):
368-
"""Tests consistency with the `mcc-nuclides.yaml` input and the nuclides in the data model."""
392+
"""Tests consistency with the `mcc-nuclides.yaml` input and the nuclides in the data model.
393+
394+
.. test:: Test that MCC v2 IDs can be queried by nuclides.
395+
:id: I_ARMI_ND_ISOTOPES3
396+
:tests: R_ARMI_ND_ISOTOPES
397+
"""
369398
with open(os.path.join(RES, "mcc-nuclides.yaml")) as f:
370399
yaml = YAML(typ="rt")
371400
data = yaml.load(f)
@@ -381,7 +410,16 @@ def test_loadMcc2Data(self):
381410
self.assertEqual(len(nuclideBases.byMcc2Id), len(expectedNuclides))
382411

383412
def test_loadMcc3Data(self):
384-
"""Tests consistency with the `mcc-nuclides.yaml` input and the nuclides in the data model."""
413+
"""Tests consistency with the `mcc-nuclides.yaml` input and the nuclides in the data model.
414+
415+
.. test:: Test that MCC v3 IDs can be queried by nuclides.
416+
:id: I_ARMI_ND_ISOTOPES4
417+
:tests: R_ARMI_ND_ISOTOPES
418+
419+
.. test:: Test the MCC nuclide data that was read from file instead of code.
420+
:id: I_ARMI_ND_DATA1
421+
:tests: R_ARMI_ND_DATA
422+
"""
385423
with open(os.path.join(RES, "mcc-nuclides.yaml")) as f:
386424
yaml = YAML(typ="rt")
387425
data = yaml.load(f)
@@ -398,9 +436,14 @@ def test_loadMcc3Data(self):
398436
self.assertEqual(len(nuclideBases.byMcc3Id), len(expectedNuclides) - 1)
399437

400438

401-
class test_getAAAZZZSId(unittest.TestCase):
439+
class TestAAAZZZSId(unittest.TestCase):
402440
def test_AAAZZZSNameGenerator(self):
441+
"""Test that AAAZZS ID name generator.
403442
443+
.. test:: Query the AAAZZS IDs can be retrieved for nuclides.
444+
:id: I_ARMI_ND_ISOTOPES5
445+
:tests: R_ARMI_ND_ISOTOPES
446+
"""
404447
referenceNucNames = [
405448
("C", "120060"),
406449
("U235", "2350920"),

0 commit comments

Comments
 (0)