From f2460ece7a8818ecd994aecf4858d6b8926dfb3d Mon Sep 17 00:00:00 2001 From: lmoresi Date: Wed, 24 Jun 2026 11:05:58 +1000 Subject: [PATCH] fix(params): apply -uw_* CLI overrides regardless of platform (#111) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit uw.Params reads overrides from the PETSc options database, but petsc4py only auto-populates that DB from sys.argv on some platforms (e.g. macOS) and not others (e.g. Gadi). On Gadi, Params(...) therefore silently fell back to its defaults even when the CLI argument was present — a hard-to-debug, environment-dependent failure with no warning. Params.__init__ now calls uw.parse_cmd_line_options() (idempotent) before reading the options DB, so a '-uw_ ' override is applied consistently. Regression: tests/test_0821_params_cli_override.py. Closes #111. Underworld development team with AI support from Claude Code --- src/underworld3/utilities/_params.py | 8 ++++ tests/test_0821_params_cli_override.py | 53 ++++++++++++++++++++++++++ 2 files changed, 61 insertions(+) create mode 100644 tests/test_0821_params_cli_override.py diff --git a/src/underworld3/utilities/_params.py b/src/underworld3/utilities/_params.py index 950c8eb1..e5e81f23 100644 --- a/src/underworld3/utilities/_params.py +++ b/src/underworld3/utilities/_params.py @@ -156,6 +156,14 @@ def __init__(self, **defaults): object.__setattr__(self, '_values', {}) object.__setattr__(self, '_sources', {}) + # Ensure command-line options (-uw_*) are loaded into the PETSc options + # database BEFORE we read overrides. petsc4py populates this DB from + # sys.argv automatically on some platforms but NOT others (e.g. Gadi), + # where Params previously fell back silently to the defaults even though + # the CLI args were present (issue #111). parse_cmd_line_options() is + # idempotent, so this is safe to call on every Params construction. + uw.parse_cmd_line_options() + # Use the module-level options object opts = uw.options diff --git a/tests/test_0821_params_cli_override.py b/tests/test_0821_params_cli_override.py new file mode 100644 index 00000000..7f46e2a1 --- /dev/null +++ b/tests/test_0821_params_cli_override.py @@ -0,0 +1,53 @@ +#!/usr/bin/env python3 +"""Regression: uw.Params picks up -uw_* command-line overrides (#111). + +On some platforms (e.g. Gadi) petsc4py does NOT auto-populate the PETSc options +database from sys.argv, so uw.Params silently fell back to its defaults even +when the CLI argument was present. Params now calls parse_cmd_line_options() +during construction, so a `-uw_ ` override is applied regardless of +platform. +""" +import sys + +import pytest + +import underworld3 as uw + +pytestmark = [pytest.mark.level_1, pytest.mark.tier_a] + + +def _clear(name): + from petsc4py import PETSc + + opts = PETSc.Options() + if opts.hasName(name): + opts.delValue(name) + + +def test_params_applies_cli_override(): + """A -uw_* CLI argument overrides the Params default even when the options + DB was not pre-populated (the Gadi failure mode in #111).""" + saved = sys.argv + try: + # Simulate Gadi: CLI arg present, options DB not yet populated. + _clear("uw_cellsize") + sys.argv = ["prog", "-uw_cellsize", "1/16"] + params = uw.Params(uw_cellsize=uw.Param("1/8", type=uw.ParamType.STRING)) + assert params.uw_cellsize == "1/16", ( + f"CLI override not applied: got {params.uw_cellsize!r}, expected '1/16'" + ) + finally: + sys.argv = saved + _clear("uw_cellsize") + + +def test_params_uses_default_without_cli(): + """With no CLI override, Params returns its default.""" + saved = sys.argv + try: + _clear("uw_testparam_111") + sys.argv = ["prog"] + params = uw.Params(uw_testparam_111=uw.Param("default_value", type=uw.ParamType.STRING)) + assert params.uw_testparam_111 == "default_value" + finally: + sys.argv = saved