55332db67a
CI / Lint (ruff check) (push) Successful in 31s
CI / Format (ruff format) (push) Successful in 32s
CI / Sync project version with tag (push) Has been skipped
CI / Lint (ruff check) (pull_request) Successful in 26s
CI / Type check (ty) (push) Successful in 29s
CI / Format (ruff format) (pull_request) Successful in 33s
CI / Sync project version with tag (pull_request) Has been skipped
CI / Type check (ty) (pull_request) Successful in 35s
CI / Tests (pull_request) Successful in 3m47s
CI / Tests (push) Successful in 3m55s
Rejoins lines that only wrapped because they exceeded the old 88-char limit; ruff check and the full test suite (725 passed) are unaffected.
102 lines
3.6 KiB
Python
102 lines
3.6 KiB
Python
import numpy as np
|
|
import pytest
|
|
|
|
from giant.materials import (
|
|
MaterialProperties,
|
|
MaterialPropertiesNotFilledError,
|
|
UnknownMaterialError,
|
|
get_material_properties,
|
|
material_properties_array,
|
|
)
|
|
|
|
|
|
def test_get_material_properties_unknown_name_raises():
|
|
with pytest.raises(UnknownMaterialError):
|
|
get_material_properties("G4_Unobtainium")
|
|
|
|
|
|
def test_get_material_properties_unfilled_entry_raises():
|
|
"""G4_LYSO is not a stock Geant4 NIST material (confirmed against the
|
|
vendored Geant4 11.4.1 build) and is the one entry still shipped unfilled."""
|
|
with pytest.raises(MaterialPropertiesNotFilledError):
|
|
get_material_properties("G4_LYSO")
|
|
|
|
|
|
def test_get_material_properties_returns_filled_entry_from_injected_table():
|
|
table = {"G4_Pb": MaterialProperties(z_eff=82.0, a_eff=207.2, density=11.35, x0=0.5612, lambda_int=17.59)}
|
|
props = get_material_properties("G4_Pb", table)
|
|
assert props.z_eff == 82.0
|
|
assert props.a_eff == 207.2
|
|
assert props.density == 11.35
|
|
assert props.x0 == 0.5612
|
|
assert props.lambda_int == 17.59
|
|
|
|
|
|
def test_material_properties_array_shape_and_values():
|
|
table = {
|
|
"G4_Pb": MaterialProperties(82.0, 207.2, 11.35, 0.5612, 17.59),
|
|
"G4_W": MaterialProperties(74.0, 183.84, 19.3, 0.3504, 9.95),
|
|
}
|
|
names = np.array(["G4_Pb", "G4_W", "G4_Pb"], dtype=object)
|
|
arr = material_properties_array(names, table)
|
|
assert arr.shape == (3, 5)
|
|
assert arr.dtype == np.float32
|
|
np.testing.assert_allclose(arr[0], [82.0, 207.2, 11.35, 0.5612, 17.59], rtol=1e-5)
|
|
np.testing.assert_allclose(arr[1], [74.0, 183.84, 19.3, 0.3504, 9.95], rtol=1e-5)
|
|
|
|
|
|
def test_all_known_materials_present_in_stub_table():
|
|
"""Every material referenced elsewhere in the repo must at least have a
|
|
stub entry (even if unfilled) -- an unknown name should never be the
|
|
failure mode a physicist hits when populating the table."""
|
|
from giant.materials import MATERIAL_PROPERTIES
|
|
|
|
expected = {
|
|
"G4_PbWO4",
|
|
"G4_CESIUM_IODIDE",
|
|
"G4_Pb",
|
|
"G4_W",
|
|
"G4_Cu",
|
|
"G4_Fe",
|
|
"G4_BRASS",
|
|
"G4_POLYSTYRENE",
|
|
"G4_PLASTIC_SC_VINYLTOLUENE",
|
|
"G4_BGO",
|
|
"G4_LYSO",
|
|
"G4_AIR",
|
|
"G4_lAr",
|
|
}
|
|
assert expected <= set(MATERIAL_PROPERTIES.keys())
|
|
|
|
|
|
def test_all_materials_filled_except_lyso():
|
|
"""G4_LYSO is the sole intentionally-unfilled entry (not a stock Geant4
|
|
NIST material); every other known material has real Geant4-derived
|
|
values -- see the module docstring for provenance."""
|
|
from giant.materials import MATERIAL_PROPERTIES
|
|
|
|
for name, props in MATERIAL_PROPERTIES.items():
|
|
if name == "G4_LYSO":
|
|
assert all(v is None for v in props)
|
|
else:
|
|
assert all(v is not None for v in props), f"{name} unexpectedly unfilled"
|
|
|
|
|
|
def test_elemental_material_z_eff_matches_atomic_number():
|
|
"""Single-element materials' z_eff must equal the element's real Z."""
|
|
pb = get_material_properties("G4_Pb")
|
|
assert pb.z_eff == pytest.approx(82.0)
|
|
w = get_material_properties("G4_W")
|
|
assert w.z_eff == pytest.approx(74.0)
|
|
fe = get_material_properties("G4_Fe")
|
|
assert fe.z_eff == pytest.approx(26.0)
|
|
|
|
|
|
def test_pbwo4_values_match_known_cms_ecal_reference():
|
|
"""PbWO4 (CMS ECAL crystal) has well-known reference values: X0~0.89cm,
|
|
density 8.28 g/cm^3 -- sanity check the Geant4-derived numbers land there."""
|
|
pbwo4 = get_material_properties("G4_PbWO4")
|
|
assert pbwo4.density == pytest.approx(8.28)
|
|
assert pbwo4.x0 == pytest.approx(0.89, abs=0.01)
|
|
assert pbwo4.z_eff == pytest.approx(31.33, abs=0.01)
|