feat: v2.0.0 -- confirmed working, scaffolding removed
Confirmed in game. The radiator's thermal-ammo and hold signals both arrive, VentAllowed goes false, and the radiator idles with its manual switch still on -- heat banked for the launchers instead of vented. The self-test probes did their job: ThresholdToggle was fine, and a mod-defined category carries a value perfectly well. The EMP probe was simply a bad probe -- it read thermal_load_dissipation, which an idled radiator broadcasts as zero, so it was correctly reporting a real zero. Routing in v1.3.0 was the actual cure. Remove the probes and the diagnostic indicators. The repointed power indicator is the one cue a player needs: it now shows on a radiator the mod has idled. Add test_override_values_name_real_components, which catches an Overrides value naming a component that does not exist -- a fourth way to produce a mod that loads clean and does nothing, and one this very commit introduced while stripping the scaffolding. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_011oLWY1G6S8U35bi2FxVWni
This commit is contained in:
@@ -532,6 +532,54 @@ def test_network_components_are_routed():
|
||||
)
|
||||
|
||||
|
||||
# ---------------------------------------------------------------------------
|
||||
# 6d. An Overrides value that names a component must name one that exists.
|
||||
#
|
||||
# The whole point of the Overrides actions is to repoint vanilla components
|
||||
# at components this mod adds. If such a value names something that is not
|
||||
# there -- deleted, renamed, or never written -- the mod still loads and the
|
||||
# gate silently reverts to doing nothing.
|
||||
# ---------------------------------------------------------------------------
|
||||
|
||||
def test_override_values_name_real_components():
|
||||
mod = rules_parser.parse_file(os.path.join(MOD_ROOT, "mod.rules"))
|
||||
|
||||
# What each part offers: its vanilla components plus what the mod adds.
|
||||
available = {}
|
||||
for mod_file, part_path in addbase_targets():
|
||||
added = rules_parser.parse_file(mod_file)
|
||||
vanilla_components = resolve(f"<{part_path}>/Part/Components")
|
||||
names = set(added.order)
|
||||
if vanilla_components is not None:
|
||||
names |= set(vanilla_components.order)
|
||||
available.setdefault(part_path, set()).update(names)
|
||||
|
||||
for action in iter_actions(mod):
|
||||
kind = action.get("Action")
|
||||
target = action.get("OverrideIn")
|
||||
if not kind or kind.value != "Overrides" or target is None:
|
||||
continue
|
||||
part_path, _inner = split_target(target.value)
|
||||
known = available.get(part_path)
|
||||
if not known:
|
||||
continue
|
||||
overrides = action.get("Overrides")
|
||||
if overrides is None:
|
||||
continue
|
||||
for field in overrides.order:
|
||||
value = overrides.children[field]
|
||||
if value.kind != "scalar":
|
||||
continue
|
||||
ref = value.value.strip()
|
||||
if not re.match(r"^[A-Za-z_][A-Za-z0-9_]*$", ref):
|
||||
continue
|
||||
check(
|
||||
ref in known,
|
||||
f"Overrides sets {field} = '{ref}' on {os.path.basename(part_path)}, "
|
||||
f"but no such component exists on that part",
|
||||
)
|
||||
|
||||
|
||||
# ---------------------------------------------------------------------------
|
||||
# 7. Added indicators must bind to a real toggle and a real atlas sprite.
|
||||
# ---------------------------------------------------------------------------
|
||||
|
||||
Reference in New Issue
Block a user