### MPI Example Script Setup Source: https://terrapower.github.io/armi/developer/parallel_coding.html Initializes necessary modules for an MPI example script, including random number generation, ARMI context, and iterable utilities for managing distributed data. ```Python """mpi_example.py""" from random import random from armi import context from armi.utils import iterables ``` -------------------------------- ### Install ARMI and Run Tests Source: https://terrapower.github.io/armi/developer/first_time_contributors.html Installs ARMI with testing dependencies and runs the unit tests using pytest. Ensure you have pytest installed. ```bash $ pip install -e .[test] $ pytest -n 4 armi ``` -------------------------------- ### Test Optimal Assembly Rotation Setup Source: https://terrapower.github.io/armi/_modules/armi/physics/fuelCycle/tests/test_assemblyRotationAlgorithms.html Sets up the test environment for optimal assembly rotation, including loading the reactor and getting the first fuel assembly. ```python class TestOptimalAssemblyRotation(ShuffleAndRotateTestHelper): """Test the burnup dependent assembly rotation methods.""" def setUp(self): super().setUp() self.assembly: HexAssembly = self.r.core.getFirstAssembly(Flags.FUEL) ``` -------------------------------- ### Install ARMI from Source with Dependencies Source: https://terrapower.github.io/armi/installation.html After cloning the repository, navigate into the ARMI directory and install it in editable mode with all dependencies, including testing dependencies. ```bash (armi-venv) $ cd armi (armi-venv) $ pip install -e ".[test]" ``` -------------------------------- ### Setup Test Reactor and Zones Source: https://terrapower.github.io/armi/_modules/armi/reactor/tests/test_zones.html Initializes a test reactor and builds manual zones based on provided definitions. This setup is used for subsequent zone-related tests. ```python self.o, self.r = loadTestReactor( inputFilePath=TESTING_ROOT, inputFileName="reactors/thirdSmallHexReactor/thirdSmallHexReactor.yaml" ) # build some generic test zones to get started with newSettings = {} newSettings["zoneDefinitions"] = [ "ring-1: 001-001", "ring-2: 002-001, 002-002", "ring-3: 003-001, 003-002, 003-003", ] cs = self.o.cs.modified(newSettings=newSettings) self.r.core.buildManualZones(cs) self.zonez = self.r.core.zones ``` -------------------------------- ### Install Documentation Requirements Source: https://terrapower.github.io/armi/developer/documenting.html Install the necessary packages for building ARMI documentation. This command should be run within your ARMI virtual environment. ```bash pip install -e .[docs] ``` -------------------------------- ### Setup Material Properties with Symbolic Function Source: https://terrapower.github.io/armi/_modules/armi/matProps/tests/test_symbolicFunction.html This setup defines a material with a density property governed by a symbolic function. It specifies the input variables (X, Y, Z) and their ranges, along with the mathematical equation. ```python self.yaml = { "file format": "TESTS", "material type": "Metal", "composition": {"a": "balance"}, "density": { "function": { "type": "symbolic", "X": {"min": -10, "max": 500.0}, "Y": {"min": 1.0, "max": 20.0}, "Z": {"min": -30.0, "max": -10.0}, "equation": 1.0, } }, } ``` -------------------------------- ### Test MultiPin Conservation Setup Source: https://terrapower.github.io/armi/_modules/armi/reactor/converters/tests/test_axialExpansionChanger_MultiPin.html Initializes the multi-pin conservation test suite by calling the base class setup. ```python class TestMultiPinConservation(TestMultiPinConservationBase): def setUp(self): super().setUp() ``` -------------------------------- ### Install ARMI as a Library Source: https://terrapower.github.io/armi/installation.html Install ARMI directly from its GitHub repository using pip. This method is suitable for quick evaluations or when using ARMI as a dependency in another project. ```bash (armi-venv) $ pip install https://github.com/terrapower/armi/archive/main.zip ``` -------------------------------- ### Setup for Full Core Expansion Test Source: https://terrapower.github.io/armi/_modules/armi/operators/tests/test_operatorSnapshots.html Configures a temporary directory, loads a partial core reactor, initializes a database, and prepares snapshot settings for a full core expansion test. ```python class TestSnapshotFullCoreExpan(unittest.TestCase): """Test that a snapshot operator can do full core analysis with a 1/3 core DB.""" DB_PATH = Path("test_operator_snapshot_full_core_expansion.h5") @classmethod def setUpClass(cls): cls.td = TemporaryDirectoryChanger() cls.td.__enter__() o, cls.symmetricReactor = loadTestReactor( inputFilePath=TESTING_ROOT, inputFileName="reactors/thirdSmallHexReactor/thirdSmallHexReactor.yaml" ) dbi: DatabaseInterface = next(filter(lambda i: isinstance(i, DatabaseInterface), o.interfaces)) dbi.initDB(cls.DB_PATH) dbi.writeDBEveryNode() dbi.closeDB() cls.snapshotSettings: settings.Settings = o.cs.modified( newSettings={"runType": RunTypes.SNAPSHOTS, "reloadDBName": str(cls.DB_PATH)} ) ``` -------------------------------- ### Get Number of Hex Rings Source: https://terrapower.github.io/armi/_modules/armi/reactor/cores.html Calculates and returns the number of hexagonal rings in the core based on assembly locations. Indexing starts at 1. ```python def getNumHexRings(self): """Return the number of hex rings in the core. Based on location so indexing starts at 1.""" maxRing = 0 for a in self: ring, _pos = self.spatialGrid.getRingPos(a.spatialLocator) maxRing = max(maxRing, ring) return maxRing ``` -------------------------------- ### Assembly Setup and Initialization Source: https://terrapower.github.io/armi/_modules/armi/reactor/tests/test_assemblies.html Sets up a test environment for assembly tests, including reactor and assembly creation with specific configurations. ```python def setUp(self): self.name = "A0015" self.assemNum = 15 self.height = 10 self.cs = settings.Settings() # Print nothing to the screen that would normally go to the log. runLog.setVerbosity("error") self.r = tests.getEmptyHexReactor() self.r.core.symmetry = geometry.SymmetryType(geometry.DomainType.THIRD_CORE, geometry.BoundaryType.PERIODIC) self.assembly = makeTestAssembly(NUM_BLOCKS, self.assemNum, r=self.r) # Use these if they are needed self.blockParams = { "height": self.height, "bondRemoved": 0.0, "envGroupNum": 0, "buLimit": 35, "buRate": 0.0, "eqRegion": -1, "id": 212.0, "pdens": 10.0, "percentBu": 25.3, "power": 100000.0, "residence": 4.0, "smearDensity": 0.6996721711791459, "timeToLimit": 2.7e5, "xsTypeNum": 65, "zbottom": 97.3521, "ztop": 111.80279999999999, } # add some blocks with a component self.blockList = [] for i in range(NUM_BLOCKS): b = blocks.HexBlock("TestHexBlock") b.setHeight(self.height) self.hexDims = { "Tinput": 273.0, "Thot": 273.0, "op": 0.76, "ip": 0.0, "mult": 1.0, } h = components.Hexagon("fuel", "UZr", **self.hexDims) # non-flaggy name important for testing b.setType("igniter fuel unitst") b.add(h) b.parent = self.assembly b.setName(b.makeName(self.assembly.getNum(), i)) self.assembly.add(b) self.blockList.append(b) self.r.core.add(self.assembly) self.assembly.calculateZCoords() ``` -------------------------------- ### Operator Restart Setup Source: https://terrapower.github.io/armi/_modules/armi/operators/tests/test_operators.html Sets up the ARMI reactor and operator for restart tests, configuring database loading and specifying start cycle and node. ```python cls.START_CYCLE = 4 cls.START_NODE = 2 cls.o, cls.r = test_reactors.loadTestReactor( inputFileName="smallestTestReactor/armiRunSmallest.yaml", customSettings={ "loadStyle": "fromDB", "startCycle": cls.START_CYCLE, "startNode": cls.START_NODE, # Need more cycles than we're restarting "nCycles": cls.START_CYCLE + 3, }, ) ``` -------------------------------- ### Example Settings Input File Source: https://terrapower.github.io/armi/user/inputs.html This excerpt shows common settings for a simulation, including availability factor, beta, verbosity, burnup groups, burn steps, cycle length, and fuel loading file. ```yaml settings: # global availabilityFactor: 1 beta: 0.003454 branchVerbosity: debug buGroups: - 100 burnSteps: 2 comment: Simple test input. cycleLength: 2000.0 detailAssemLocationsBOL: - 002-001 freshFeedType: igniter fuel loadingFile: refSmallReactor.yaml ``` -------------------------------- ### Initialize Database Interface Source: https://terrapower.github.io/armi/_modules/armi/bookkeeping/db/tests/test_database.html Sets up the DatabaseInterface and initializes a new database file for testing. ```python self.dbi = DatabaseInterface(self.r, self.o.cs) self.dbi.initDB(fName=self._testMethodName + ".h5") self.db: Database = self.dbi.database self.stateRetainer = self.r.retainState().__enter__() ``` -------------------------------- ### Test Get Decay Functionality Source: https://terrapower.github.io/armi/_modules/armi/nucDirectory/tests/test_nuclideBases.html Retrieves a nuclide with atomic number 89 and proceeds to test its decay properties. This snippet is a starting point for testing the `getDecay` functionality. ```python nb = list(self.nuclideBases.where(lambda nn: nn.z == 89))[0] ``` -------------------------------- ### Setup and Teardown for Database Tests Source: https://terrapower.github.io/armi/_modules/armi/bookkeeping/db/tests/test_database.html Initializes a temporary directory, copies test files, creates a reactor configuration with an EVST, and sets up the Database Interface. Cleans up the temporary directory and closes the database connection after tests. ```python def setUp(self): self.td = TemporaryDirectoryChanger() self.td.__enter__() # copy these test files over, so we can edit them thisDir = self.td.destination yamls = glob(os.path.join(TEST_ROOT, "smallestTestReactor", "*.yaml")) for yam in yamls: safeCopy(os.path.join(TEST_ROOT, "smallestTestReactor", yam), thisDir) # Add an EVST to this reactor with open("refSmallestReactor.yaml", "w") as f: f.write(self.SMALL_YAML) self.o, self.r = loadTestReactor(thisDir, inputFileName="armiRunSmallest.yaml") self.dbi = DatabaseInterface(self.r, self.o.cs) self.dbi.initDB(fName=f"{self._testMethodName}.h5") self.db: Database = self.dbi.database def tearDown(self): self.db.close() self.td.__exit__(None, None, None) ``` -------------------------------- ### Configure BasicArmiSymmetryTestHelper Source: https://terrapower.github.io/armi/_modules/armi/testing/symmetryTesting.html Subclass `BasicArmiSymmetryTestHelper` and configure test attributes in `setUp` before calling `super.setUp()`. This example shows how to set parameters to test, expected symmetric parameters, and overrides. ```python class MySymmetryTest(symmetryTesting.BasicArmiSymmetryTestHelper): def setUp(): # Tests are configured using attributes. Attributes must be set prior to calling super.setUp() # Note that it is not required to set any attributes, all have empty defaults # Repeat for self.coreParamsToTest and self.assemblyParamsToTest as necessary: self.blockParamsToTest = [p if isinstance(p, str) else p.name for p in getPluginBlockParameterDefinitions()] # Repeat for self.expectedSymmetricCoreParams and self.expectedSymmetricAssemblyParams as necessary: self.expectedSymmetricBlockParams = ["mySymmetricBlockParam1", "mySymmetricBlockParam2"] # Set specific parameter overrides if the parameters need a specific value (usually due to input validators) self.parameterOverrides = {"parameterName1": value1, "parameterName2": value2} # Set specific parameters to ignore in comparison. self.paramsToIgnore = ["myIgnoredParameter"] # Finish setting up the tests by calling the parent's `setUp` method. super.setUp() ``` -------------------------------- ### Get Base i,j for ASCII Line Source: https://terrapower.github.io/armi/_modules/armi/utils/asciimaps.html Determines the starting i,j indices for a given ASCII line number, counting from the top. The upper-left corner is shifted by (size-1)//2. ```python def _getIJBaseByAsciiLine(self, asciiLineNum): """ Get i,j base (starting point) for a row counting from the top. Upper left is shifted by (size-1)//2 for a 19-line grid, we have the top left as (-18,9) and then: (-17, 8), (-16, 7), ... """ shift = self._ijMax iBase = -shift * 2 + asciiLineNum jBase = shift - asciiLineNum return iBase, jBase ``` -------------------------------- ### Setup Source Reactor for Conversion Source: https://terrapower.github.io/armi/_modules/armi/reactor/converters/geometryConverters.html Prepares the source reactor for conversion by summarizing its statistics and optionally expanding its geometry. This is a prerequisite step before initiating the conversion process. ```python def _setupSourceReactorForConversion(self): self._sourceReactor.core.summarizeReactorStats() if self._expandSourceReactor: self._expandSourceReactorGeometry() ``` -------------------------------- ### Test Zone Setup Source: https://terrapower.github.io/armi/_modules/armi/reactor/tests/test_zones.html Sets up a test reactor with a spatial grid and populates it with assemblies and blocks for zone testing. ```python def setUp(self): # set up a Reactor, for the spatialLocator bp = blueprints.Blueprints() r = reactors.Reactor("zonetest", bp) r.add(reactors.Core("Core")) r.core.spatialGrid = grids.HexGrid.fromPitch(1.0) r.core.spatialGrid._bounds = ( [0, 1, 2, 3, 4], [0, 10, 20, 30, 40], [0, 20, 40, 60, 80], ) r.core.spatialGrid.symmetry = geometry.SymmetryType( geometry.DomainType.THIRD_CORE, geometry.BoundaryType.PERIODIC ) r.core.spatialGrid.geomType = geometry.HEX # some testing constants self.numAssems = 5 self.numBlocks = 5 # build a list of Assemblies self.aList = [] for ring in range(self.numAssems): a = assemblies.HexAssembly("fuel") a.spatialGrid = r.core.spatialGrid a.spatialLocator = r.core.spatialGrid[ring, 1, 0] a.parent = r.core self.aList.append(a) # build a list of Blocks self.bList = [] for _ in range(self.numBlocks): b = blocks.HexBlock("TestHexBlock") b.setType("defaultType") b.p.nPins = 3 b.setHeight(3.0) self.aList[0].add(b) self.bList.append(b) ``` -------------------------------- ### Get Previous Time Node Source: https://terrapower.github.io/armi/_modules/armi/utils.html Determines the time step (cycle, node) immediately preceding a given time step. Handles the wrap-around from the start of a cycle to the end of the previous one. ```python def getPreviousTimeNode(cycle, node, cs): """Return the (cycle, node) before the specified (cycle, node).""" if (cycle, node) == (0, 0): raise ValueError("There is no time step before (0, 0)") if node != 0: return (cycle, node - 1) else: nodesPerCycle = getNodesPerCycle(cs) nodesInLastCycle = nodesPerCycle[cycle - 1] indexOfLastNode = nodesInLastCycle - 1 # zero based indexing for nodes return (cycle - 1, indexOfLastNode) ``` -------------------------------- ### Test Third Core to Full Core Conversion Setup Source: https://terrapower.github.io/armi/_modules/armi/reactor/converters/tests/test_geometryConverters.html Sets up a temporary directory and loads a reactor model that represents a third of a hexagonal core. It initializes block powers uniformly, accounting for the core's symmetry. ```python def setUp(self): self.td = TemporaryDirectoryChanger() self.td.__enter__() self.o, self.r = loadTestReactor( inputFilePath=TESTING_ROOT, inputFileName="reactors/thirdSmallHexReactor/thirdSmallHexReactor.yaml" ) # initialize the block powers to a uniform power profile, accounting for the loaded reactor being 1/3 core numBlocksInFullCore = 0 for a in self.r.core: if a.getLocation() == "001-001": for b in a: numBlocksInFullCore += 1 else: for b in a: # account for the 1/3 symmetry numBlocksInFullCore += 3 for a in self.r.core: if a.getLocation() == "001-001": for b in a: b.p["power"] = self.o.cs["power"] / numBlocksInFullCore / 3 else: for b in a: b.p["power"] = self.o.cs["power"] / numBlocksInFullCore ``` ```python def tearDown(self): del self.o del self.r self.td.__exit__(None, None, None) ``` -------------------------------- ### Test Get Total Job Memory Source: https://terrapower.github.io/armi/_modules/armi/bookkeeping/tests/test_memoryProfiler.html Tests the `getTotalJobMemory` function by mocking `psutil.virtual_memory` and `cpu_count`. This example sets up the mocks to simulate a node with 50 GB of RAM and 10 CPUs. ```python @patch("psutil.virtual_memory") @patch("armi.bookkeeping.memoryProfiler.cpu_count") def test_getTotalJobMemory(self, mockCpuCount, mockVMem): """Use an example node with 50 GB of total physical memory and 10 CPUs.""" mockCpuCount.return_value = 10 ``` -------------------------------- ### Get Minimum Percent Flux in Fuel Source: https://terrapower.github.io/armi/_modules/armi/reactor/cores.html Determines the ring with the minimum percentage of total reactor flux in its fuel assemblies, starting from the outer ring. Useful for identifying regions with low flux. ```python def getMinimumPercentFluxInFuel(self, target=0.005): """ Starting with the outer ring, this method goes through the entire Reactor to determine what percentage of flux occurs at each ring. Parameters ---------- target : float This is the fraction of the total reactor fuel flux compared to the flux in a specific assembly in a ring Returns ------- targetRing, fraction of flux : tuple targetRing is the ring with the fraction of flux that best meets the target. """ # get the total number of assembly rings numRings = self.getNumRings() # old target assembly fraction fluxFraction = 0 targetRing = numRings allFuelBlocks = self.getBlocks(Flags.FUEL) # loop there all of the rings for ringNumber in range(numRings, 0, -1): # Compare to outer most ring. flatten list into one list of all blocks blocksInRing = list( itertools.chain.from_iterable([a.iterBlocks(Flags.FUEL) for a in self.getAssembliesInRing(ringNumber)]) ) totalPower = self.getTotalBlockParam("flux", objs=allFuelBlocks) ringPower = self.getTotalBlockParam("flux", objs=blocksInRing) # make sure that there is a non zero return if fluxFraction == 0 and ringPower > 0: fluxFraction = ringPower / totalPower targetRing = ringNumber # this will only get the leakage if the target fraction isn't too low if ringPower / totalPower < target and ringPower / totalPower > fluxFraction: fluxFraction = ringPower / totalPower targetRing = ringNumber return targetRing, fluxFraction ``` -------------------------------- ### Register User Plugins from Settings Source: https://terrapower.github.io/armi/_modules/armi/tests/test_user_plugins.html Illustrates registering user plugins by reading their paths from ARMI's case settings. ```python def test_registerUserPluginsFromSettings(self): app = getApp() cs = caseSettings.Settings().modified( caseTitle="test_registerUserPluginsFromSettings", ``` -------------------------------- ### Get IJ Base by Ascii Line for Full Flats Up Hex Map Source: https://terrapower.github.io/armi/_modules/armi/utils/asciimaps.html Calculates the starting (i, j) coordinates for a given ASCII line number, accounting for potentially omitted corners and the jagged nature of the grid. This is used in the AsciiMapHexFullFlatsUp class. ```python def _getIJBaseByAsciiLine(self, asciiLineNum): """ Get i,j base (starting point) for a row from bottom. Starts out in simple pattern and then shifts. Recall that there are 2 ascii lines per j index because jagged. If hex corners are omitted, we must offset the line num to get the base right (complexity!) In this orientation, we need the _ijMax to help orient us. This represents the number of ascii lines between the center of the core and the top (or bottom) """ # handle potentially-omitted corners asciiLineNum += self._asciiLinesOffCorner if asciiLineNum < self._ijMax: # goes from (0,-9), (-1,-8), (-2,7)... i, j = -asciiLineNum, -self._ijMax + asciiLineNum elif not (asciiLineNum - self._ijMax) % 2: # goes JAGGED from (-9,0), (-8, 0), (-9,2)... # this is the outermost upward ray index = (asciiLineNum - self._ijMax) // 2 i, j = -self._ijMax, index else: # this is the innermost upward ray index = (asciiLineNum - self._ijMax) // 2 i, j = -self._ijMax + 1, index return i, j ``` -------------------------------- ### Tight Coupler Setup Source: https://terrapower.github.io/armi/_modules/armi/tests/test_interfaces.html Sets up a `DummyInterface` with tight coupling enabled in its settings. This includes specifying the action and convergence parameters. ```python def setUp(self): cs = settings.Settings() cs["tightCoupling"] = True cs["tightCouplingSettings"] = {"dummyAction": {"parameter": "nothing", "convergence": 1.0e-5}} self.interface = DummyInterface(None, cs) ``` -------------------------------- ### Setup for Database Reading Tests Source: https://terrapower.github.io/armi/_modules/armi/bookkeeping/db/tests/test_databaseInterface.html Sets up the test environment for database reading tests. This includes creating a temporary directory, loading a reactor with custom settings, initializing the database interface, and writing initial flux data. ```python @classmethod def setUpClass(cls): cls.td = directoryChangers.TemporaryDirectoryChanger() cls.td.__enter__() # The database writes the settings object to the DB rather than the original input file. # This allows settings to be changed in memory like this and survive for testing. newSettings = {"verbosity": "extra"} cls.nCycles = 2 newSettings["nCycles"] = cls.nCycles newSettings["burnSteps"] = 2 o, r = loadTestReactor( inputFilePath=TESTING_ROOT, inputFileName="reactors/thirdSmallHexReactor/thirdSmallHexReactor.yaml", customSettings=newSettings, ) reduceTestReactorRings(r, o.cs, 3) o.interfaces = [i for i in o.interfaces if isinstance(i, (DatabaseInterface))] dbi = o.getInterface("database") dbi.enabled(True) dbi.initDB() # Main Interface normally does this # update a few parameters def writeFlux(cycle, node): for bi, b in enumerate(o.r.core.iterBlocks()): b.p.flux = 1e6 * bi + cycle * 100 + node b.p.mgFlux = np.repeat(b.p.flux / 33, 33) o.interfaces.insert(0, MockInterface(o.r, o.cs, writeFlux)) with o: o.operate() cls.cs = o.cs cls.bp = o.r.blueprints cls.dbName = o.cs.caseTitle + ".h5" # needed for test_readWritten cls.r = o.r ``` -------------------------------- ### Get Cycle Node at Time Source: https://terrapower.github.io/armi/_modules/armi/bookkeeping/db/database.html Retrieves cycle and node identifiers from an ARMI database file within a specified time range. It includes validation for start and end times and can optionally raise an error if exactly one time node is not found. ```python import h5py # ... (rest of the function definition) # open the H5 file directly with h5py.File(dbPath, "r") as h5: # read time steps in H5 file thisTime = 0.0 cycleNodes = [] for h5Key in h5.keys(): if h5Key == "inputs": continue thisTime = h5[h5Key]["Reactor"]["time"][0] if thisTime >= endTime: cycleNodes.append(h5Key) break elif thisTime >= startTime: cycleNodes.append(h5Key) # more validation if not cycleNodes: raise ValueError(f"Provided start time ({startTime}) was greater than the modeled period: {thisTime}.") elif errorIfNotExactlyOne and len(cycleNodes) != 1: raise ValueError(f"Did not find exactly one cycle/node pair: {cycleNodes}") return cycleNodes ``` -------------------------------- ### Test Lattice Physics Writer Setup Source: https://terrapower.github.io/armi/_modules/armi/physics/neutronics/latticePhysics/tests/test_latticeWriter.html Sets up the test environment by loading a test reactor, configuring cross-section settings, and initializing a FakeLatticePhysicsWriter instance. ```python def setUp(self): self.o, self.r = loadTestReactor(TEST_ROOT) self.cs = self.o.cs self.cs[CONF_CROSS_SECTION].setDefaults( self.cs[CONF_XS_BLOCK_REPRESENTATION], self.cs[CONF_DISABLE_BLOCK_TYPE_EXCLUSION_IN_XS_GENERATION], ) self.block = self.r.core.getFirstBlock() self.w = FakeLatticePhysicsWriter(self.block, self.r, self.o) ``` -------------------------------- ### Verify ARMI Installation Source: https://terrapower.github.io/armi/installation.html Run this command to check if ARMI has been installed correctly. A successful installation will display the ARMI splash screen without errors. ```bash (armi-venv) $ armi ``` ```bash (armi-venv) $ python -m armi ``` -------------------------------- ### Test Snapshot Interface Setup Source: https://terrapower.github.io/armi/_modules/armi/bookkeeping/tests/test_snapshot.html Sets up the test environment for SnapshotInterface, initializing settings and the interface itself with mock reactor objects. ```python class TestSnapshotInterface(unittest.TestCase): @classmethod def setUpClass(self): self.cs = settings.Settings() def setUp(self): self.cs.revertToDefaults() self.si = snapshotInterface.SnapshotInterface(MockReactor(self.cs), self.cs) ``` -------------------------------- ### Timer Start Method Source: https://terrapower.github.io/armi/_modules/armi/utils/codeTiming.html Starts the timer. If the timer is already active, it increments the overStart count and closes the previous interval before starting a new one. Returns the current timestamp. ```python def start(self): """Start this Timer. Returns ------- float : Time stamp for the current time / start time. """ curTime = MasterTimer.time() if self._frozen: return curTime elif self.isActive: # call was made on an active timer, we're now over-started self.overStart += 1 self._closeTimePair(curTime) self._active = True self._openTimePair(curTime) return curTime ``` -------------------------------- ### OSC 8 Hyperlink Example Source: https://terrapower.github.io/armi/_modules/armi/utils/tabulate.html An example demonstrating how to use the OSC 8 escape code to display a hyperlink in a terminal. The example shows the escape sequence for a specific URI and the text to be displayed. ```text # Example: ]8;;https://example.com\text to show]8;;\ ``` -------------------------------- ### Build HTML Documentation Source: https://terrapower.github.io/armi/developer/documenting.html Navigate to the 'doc' folder and run this command to build the ARMI documentation as HTML files. The output will be in the '_build/html' folder. ```bash make html ``` -------------------------------- ### MultiSettingModifier Example Source: https://terrapower.github.io/armi/_modules/armi/cases/inputModifiers/inputModifiers.html Initializes a modifier to adjust multiple settings simultaneously. This is a constructor example. ```python class MultiSettingModifier(InputModifier): """ Adjust multiple settings to specified values. Examples -------- >>> inputModifiers.MultiSettingModifier({CONF_NEUTRONICS_TYPE: "both", CONF_COARSE_MESH_REBALANCE: -1}) """ def __init__(self, settingVals: dict): ``` -------------------------------- ### Setup Blueprints for Testing Source: https://terrapower.github.io/armi/_modules/armi/reactor/tests/test_assemblies.html Helper method to set up the necessary blueprints for testing. It modifies the configuration to load a specific blueprint file and prepares the blueprints for construction. ```python def _setup_blueprints(self, filename="refSmallReactor.yaml"): # need this for the getAllNuclides call with directoryChangers.DirectoryChanger(TEST_ROOT): newSettings = {CONF_LOADING_FILE: filename} self.cs = self.cs.modified(newSettings=newSettings) with open(self.cs[CONF_LOADING_FILE], "r") as y: y = textProcessors.resolveMarkupInclusions(y, pathlib.Path(self.cs.inputDirectory)) self.r.blueprints = blueprints.Blueprints.load(y) self.r.blueprints._prepConstruction(self.cs) ``` -------------------------------- ### Get Block Index from Z-Index Source: https://terrapower.github.io/armi/_modules/armi/reactor/assemblies.html Placeholder for a method to get the block index from a z-index. ```python def getBIndexFromZIndex(self, zIndex): """ ``` -------------------------------- ### Test Start and Stop Counting Source: https://terrapower.github.io/armi/_modules/armi/utils/tests/test_codeTiming.html Tests the manual start() and stop() methods of a timer, including edge cases like multiple consecutive starts or stops, and verifies the overStart count. Also demonstrates using timers as context managers. ```python # test the start() and stop() methods, and their side effects master = codeTiming.MasterTimer.getMasterTimer() timer = master.startTimer("bananananana") t0 = timer.stop() self.assertEqual(timer.overStart, 0) # run start a few times in a row, to trip the overstart for i in range(5): time.sleep(0.01) t1 = timer.start() self.assertGreater(t1, t0) t0 = t1 self.assertEqual(timer.overStart, i) # run stop a few times in a row, which is allowed for race conditions for i in range(5): time.sleep(0.01) t2 = timer.stop() self.assertGreater(t2, t1) t1 = t2 self.assertEqual(timer.overStart, 3 - i if 3 - i > 0 else 0) # start will always work from a stopped state time.sleep(0.01) t6 = timer.start() self.assertGreater(t6, t2) self.assertEqual(timer.overStart, 0) # start a second timer to show two can run at once time.sleep(0.01) timer2 = master.endTimer("wazzlewazllewazzzle") t7 = timer2.start() self.assertGreater(t7, t6) self.assertEqual(timer2.overStart, 0) # use the timers as context managers with timer2: with timer: pass # There should be one start/stop each, leaving the over start count the same self.assertEqual(timer.overStart, 0) self.assertEqual(timer2.overStart, 0) ``` -------------------------------- ### ExcoreCollection Initialization and Usage Source: https://terrapower.github.io/armi/_modules/armi/reactor/excoreStructure.html Demonstrates how to create an `ExcoreCollection` and add `ExcoreStructure` objects to it, allowing access via both dictionary keys and class attributes. ```python class ExcoreCollection(dict): """ A collection that allows ex-core structures to be accessed like a dict, or class attributes. Examples -------- Build some sample data:: >>> sfp = ExcoreStructure("sfp") >>> ivs = ExcoreStructure("ivs") Build THIS collection:: >>> excore = ExcoreCollection() Now you can add data to this collection like it were a dictionary, and access freely:: >>> excore["sfp"] = sfp >>> excore["sfp"] >>> excore.sfp Or you can add data as if it were a class attribute, and still have dual access:: >>> excore.ivs = ivs >>> excore.ivs >>> excore["ivs"] """ def __getattr__(self, key): """Override the class attribute getter. First check if the class attribute exists. If not, check if the key is in the dictionary. """ try: # try to get a real class attribute return self.__dict__[key] except KeyError: try: # if it's not a class attribute, maybe it is a dictionary key? return self.__getitem__(key) except Exception: pass # it is neither, just raise the usual error raise def __setattr__(self, key, value): """Override the class attribute setting. If the value has an ExcoreStructure type, assume we want to store this in the dictionary. """ if type(value) is ExcoreStructure: self.__setitem__(key, value) else: self.__dict__[key] = value def __getstate__(self): """Needed to support pickling and unpickling the Reactor.""" return self.__dict__.copy() def __setstate__(self, state): """Needed to support pickling and unpickling the Reactor.""" self.__dict__.update(state) def __deepcopy__(self, memo): """Needed to support pickling and unpickling the Reactor.""" memo[id(self)] = newE = self.__class__.__new__(self.__class__) newE.__setstate__(copy.deepcopy(self.__getstate__(), memo)) return newE def __repr__(self): return "<{}: {} id:{}>".format(self.__class__.__name__, self.name, id(self)) ``` -------------------------------- ### Initialize ExcoreStructure Source: https://terrapower.github.io/armi/_modules/armi/reactor/excoreStructure.html Initializes an ex-core structure with a name and an optional parent. It also sets up a placeholder for a spatial grid. ```python class ExcoreStructure(Composite): """This is meant as the simplest baseclass needed to represent an ex-core reactor thing. An ex-core structure is expected to: - be a child of the Reactor, - have a grid associated with it, - contain a hierarchical set of ArmiObjects. """ def __init__(self, name, parent=None): Composite.__init__(self, name) self.parent = parent self.spatialGrid = None ``` -------------------------------- ### Verify ARMI Installation (Module Execution) Source: https://terrapower.github.io/armi/user/user_install.html An alternative command to verify the ARMI installation by executing it as a Python module. ```bash (armi-venv) $ python -m armi ``` -------------------------------- ### Setup Reactor for Construction Test Source: https://terrapower.github.io/armi/_modules/armi/reactor/blueprints/tests/test_reactorBlueprints.html Creates temporary YAML files for system and grid designs, loads blueprints, and constructs reactor components. Cleans up temporary files afterward. ```python fnames = [self._testMethodName + n for n in ["geometry.yaml", "sfp-geom.yaml"]] for fn in fnames: with open(fn, "w") as f: f.write(SMALL_YAML) cs = settings.Settings() bp = blueprints.Blueprints.load(test_customIsotopics.TestCustomIsotopics.yamlString) bp.systemDesigns = self.systemDesigns bp.gridDesigns = self.gridDesigns reactor = reactors.Reactor(cs.caseTitle, bp) core = bp.systemDesigns["core"].construct(cs, bp, reactor) sfp = bp.systemDesigns["sfp"].construct(cs, bp, reactor) evst = bp.systemDesigns["evst"].construct(cs, bp, reactor) for fn in fnames: os.remove(fn) return core, sfp, evst ``` -------------------------------- ### Burn Chain YAML Example Source: https://terrapower.github.io/armi/_modules/armi/nucDirectory/transmutations.html This example illustrates the structure of a burn-chain.yaml file, defining transmutations and decays for a nuclide. ```yaml U238: - nuSF: 2.0000 - transmutation: branch: 1.0 products: - NP237 type: n2n - transmutation: branch: 1.0 products: - LFP38 type: fission - transmutation: branch: 1.0 products: - NP239 - PU239 type: nGamma - decay: branch: 5.45000e-07 halfLifeInSeconds: 1.4099935680e+17 products: - LFP38 type: sf ``` -------------------------------- ### Initialize and Apply B4C Material Parameters Source: https://terrapower.github.io/armi/_modules/armi/materials/tests/test_b4c.html Demonstrates the initialization of B4C material objects and the application of specific input parameters like theoretical density and its fraction. This is useful for setting up material instances with custom properties for testing. ```python from armi.materials.b4c import B4C self.mat = B4C() self.B4C_theoretical_density = B4C() self.B4C_theoretical_density.applyInputParams(theoretical_density=0.5) self.B4C_TD_frac = B4C() self.B4C_TD_frac.applyInputParams(TD_frac=0.4) self.B4C_both = B4C() self.B4C_both.applyInputParams(theoretical_density=0.5, TD_frac=0.4) ``` -------------------------------- ### Build and Verify Simulation Suite Source: https://terrapower.github.io/armi/tutorials/param_sweep.html Build the simulation suite from the defined modifiers and print its configuration. This step prepares the suite for execution. ```python suite = builder.buildSuite() suite.echoConfiguration() ``` -------------------------------- ### Install ARMI with Test Dependencies Source: https://terrapower.github.io/armi/readme.html Install ARMI along with its testing dependencies. This is necessary for running the ARMI tests locally using pytest. ```bash pip install -e ".[test]" ``` -------------------------------- ### Test EntryPoint Initialization Source: https://terrapower.github.io/armi/_modules/armi/cli/tests/test_runEntryPoint.html Tests that all subclasses of `EntryPoint` correctly initialize and add their respective command-line options. It also verifies the presence of a settings file argument where expected. ```python entryPoints = getEntireFamilyTree(EntryPoint) # Comparing to a minimum number of entry points, in case more are added. self.assertGreater(len(entryPoints), 15) for e in entryPoints: entryPoint = e() entryPoint.addOptions() settingsArg = None if entryPoint.settingsArgument is not None: for a in entryPoint.parser._actions: if "settings_file" in a.dest: settingsArg = a break self.assertIsNotNone( settingsArg, msg=( f"A settings file argument was expected for {entryPoint}, " "but does not exist. This is a error in the EntryPoint " "implementation." ), ) ``` -------------------------------- ### Clone and Install ARMI Source: https://terrapower.github.io/armi/readme.html Clone the ARMI repository and install it in editable mode. It is recommended to do this within a virtual environment to avoid dependency conflicts. ```bash git clone https://github.com/terrapower/armi cd armi pip install -e . ``` -------------------------------- ### Write and Load Settings to YAML Source: https://terrapower.github.io/armi/_modules/armi/settings/tests/test_settingsIO.html Demonstrates writing settings to a YAML file and then loading them back. Verifies that the loaded settings match the original values. ```python self.cs.writeToYamlFile(self.filepathYaml) self.cs.loadFromInputFile(self.filepathYaml) self.assertEqual(self.cs["nCycles"], 55) ``` -------------------------------- ### Setup Base Test Case for Lattice Physics Interface Source: https://terrapower.github.io/armi/_modules/armi/physics/neutronics/latticePhysics/tests/test_latticeInterface.html Sets up a base test case for LatticePhysicsInterface by creating an empty reactor core, adding a sample assembly with a fuel block, and initializing the CrossSectionGroupManager. ```python class TestLatticePhysicsInterfaceBase(unittest.TestCase): @classmethod def setUpClass(cls): # create empty reactor core cls.o = Operator(settings.Settings()) cls.o.r = Reactor("testReactor", None) cls.o.r.core = Core("testCore") # add an assembly with a single block cls.assembly = HexAssembly("testAssembly") cls.assembly.spatialGrid = grids.AxialGrid.fromNCells(1) cls.assembly.spatialGrid.armiObject = cls.assembly cls.assembly.add(buildSimpleFuelBlock()) # init and add interfaces cls.xsGroupInterface = CrossSectionGroupManager(cls.o.r, cls.o.cs) cls.o.addInterface(cls.xsGroupInterface) ``` -------------------------------- ### Test Get Parameter Without Default Raises Error Source: https://terrapower.github.io/armi/_modules/armi/reactor/tests/test_parameters.html Verifies that attempting to get a parameter without a default value raises a ParameterError. ```python class Mock(parameters.ParameterCollection): pDefs = parameters.ParameterDefinitionCollection() with pDefs.createBuilder() as pb: pb.defParam("noDefault", "units", "description", "location") mock = Mock() with self.assertRaises(parameters.ParameterError): print(mock.noDefault) ``` -------------------------------- ### Start Code Coverage Source: https://terrapower.github.io/armi/_modules/armi/cases/case.html Initializes and starts the coverage tool if enabled in the settings. It configures coverage for parallel execution if multiple MPI ranks are present. ```python def _startCoverage(self): """Helper to the Case.run: spin up the code coverage tooling, if the Settings file says to. Returns ------- coverage.Coverage Coverage object for pytest or unittest """ cov = None if self.cs["coverage"]: cov = coverage.Coverage( config_file=Case._getCoverageRcFile(userCovFile=self.cs["coverageConfigFile"], makeCopy=True), debug=["dataio"], ) if context.MPI_SIZE > 1: # interestingly, you cannot set the parallel flag in the constructor without # auto-specifying the data suffix. This should enable parallel coverage with # auto-generated data file suffixes and combinations. cov.config.parallel = True cov.start() return cov ``` -------------------------------- ### Setup for Cartesian Reactor Tests Source: https://terrapower.github.io/armi/_modules/armi/reactor/tests/test_reactors.html Sets up the operator and reactor for Cartesian grid tests. This is a base setup for tests involving Cartesian block structures. ```python [docs] class CartesianReactorTests(ReactorTests): def setUp(self): self.o = buildOperatorOfEmptyCartesianBlocks() self.r = self.o.r ``` -------------------------------- ### Initialize ARMI Settings Source: https://terrapower.github.io/armi/_modules/armi/cli/entryPoint.html Initializes settings for an entry point. Command-line arguments can update this data structure. Override this method to provide specific settings. ```python @staticmethod def _initSettings(): """ Initialize settings for this entry point. Settings given on command line will update this data structure. Override to provide specific settings in the entry point. """ return settings.Settings() ``` -------------------------------- ### Test RunEntryPoint Basics Source: https://terrapower.github.io/armi/_modules/armi/cli/tests/test_runEntryPoint.html Tests the basic initialization and argument parsing for the 'run' entry point. It verifies the command name and that the settings argument is marked as required. ```python def test_runEntryPointBasics(self): rep = RunEntryPoint() rep.addOptions() rep.parse_args([ARMI_RUN_PATH]) self.assertEqual(rep.name, "run") self.assertEqual(rep.settingsArgument, "required") ``` -------------------------------- ### Register User Plugins by Name Source: https://terrapower.github.io/armi/_modules/armi/tests/test_user_plugins.html Demonstrates registering user plugins by their Python path string using `app.registerUserPlugins()`. ```python def test_registerUserPlugins(self): app = getApp() pluginNames = [p[0] for p in app.pluginManager.list_name_plugin()] self.assertNotIn("UserPluginFlags2", pluginNames) plugins = ["armi.tests.test_user_plugins.UserPluginFlags2"] app.registerUserPlugins(plugins) pluginNames = [p[0] for p in app.pluginManager.list_name_plugin()] self.assertIn("UserPluginFlags2", pluginNames) self.assertIn("FLAG2", dir(Flags)) ``` -------------------------------- ### Get global coordinates of the centroid Source: https://terrapower.github.io/armi/_modules/armi/reactor/grids/locations.html Gets the coordinates of the centroid of this object in global 3D space. It sums local coordinates with parent global coordinates if a parent exists. ```python def getGlobalCoordinates(self, nativeCoords=False): """Get coordinates in global 3D space of the centroid of this object.""" parentLocation = self.parentLocation # to avoid evaluating property if's twice if parentLocation: return self.getLocalCoordinates(nativeCoords=nativeCoords) + parentLocation.getGlobalCoordinates( nativeCoords=nativeCoords ) return self.getLocalCoordinates(nativeCoords=nativeCoords) ``` -------------------------------- ### Test Case Profiling Start Source: https://terrapower.github.io/armi/_modules/armi/cases/tests/test_cases.html Tests the `_startProfiling` method of a Case object. It verifies that profiling is not started when 'profile' is False in settings and that a `cProfile.Profile` object is returned when 'profile' is True. ```python cs = cs.modified(newSettings={"profile": False}) case = cases.Case(cs) prof = case._startProfiling() self.assertIsNone(prof) # Test when we start coverage correctly cs = cs.modified(newSettings={"profile": True}) case = cases.Case(cs) prof = case._startProfiling() self.assertTrue(isinstance(prof, cProfile.Profile)) ``` -------------------------------- ### Initialize Git Submodules Source: https://terrapower.github.io/armi/developer/documenting.html Ensure all necessary submodules are available in your source tree before building documentation. ```bash git submodule update --init ``` -------------------------------- ### Get Block within Assembly Source: https://terrapower.github.io/armi/_modules/armi/bookkeeping/tests/test_historyTracker.html Retrieves a specific block from a fuel assembly and verifies its properties. Also tests that attempting to get a block from a shield assembly raises an AttributeError. ```python history = self.o.getInterface("history") aFuel = self.o.r.core.getFirstAssembly(Flags.FUEL) b = history._getBlockInAssembly(aFuel) self.assertGreater(b.p.height, 1.0) self.assertEqual(b.getType(), "fuel") with self.assertRaises(AttributeError): aShield = self.o.r.core.getFirstAssembly(Flags.SHIELD) history._getBlockInAssembly(aShield) ```