Files
AnyPS5/tools/tests/test_env_reference.py
xXPBSXxandClaude Sonnet 5.5 f33e4158c0 fix(tools): reject a scan root that is not a directory in env_reference
A mistyped --root (or running from another directory) was skipped silently,
so --check reported every documented name as stale.

Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
2026-10-21 07:44:52 +02:00

136 lines
6.8 KiB
Python

import contextlib
import io
import sys
import tempfile
import unittest
from pathlib import Path
sys.path.insert(0, str(Path(__file__).resolve().parents[1]))
import env_reference
BOTH = ("APS5_", "ANYPS5_")
CODE = """static bool a = std::getenv("APS5_PROFILE_DRAW") != nullptr;
static bool b = IsEnvironmentSet("APS5_TRACE_GPU");
static unsigned long c = kibSetting("APS5_HOST_IMPORT_MIB", 6144);
static unsigned long d = MaskFromEnvironment("APS5_WORKER_AFFINITY_MASK");
static const char* e = std::getenv("ANYPS5_GPU");
static const char* f = std::getenv("PATH");
static const char* g = std::getenv("TZ");
static int h = EnvInt("APS5_THREAD_NICE", -10);
static int i = GetEnvironmentVariableA("APS5_CRASH_INDIRECT_MEMORY", nullptr, 0);
static unsigned long j = configured("APS5_PIPELINE_JOURNAL_MAX_MIB", 1024u) << 20u;
static unsigned long k = PipelineSwitch("APS5_PIPELINE_STORE_ENTRIES", 1024u);
static unsigned long l = configured("APS5_PIPELINE_JOURNAL_THREADS", std::max(1u, hardware / 2u));
static std::size_t m = environmentCount("APS5_PM4_RING", 16, MaximumCapacity, "APS5_PM4_RING must be a number");
static int n = GetEnvironmentVariableW(L"ANYPS5_LOADEXEC_ARGV_SKIP", skip, 2);
static const auto* o = addWideString(u"ANYPS5_LOADEXEC_PARENT");
static unsigned long p = reconfigured("APS5_NOT_A_READ", 1);
static bool q = _wgetenv(L"APS5_WIDE_PRESENT") != nullptr;
static int r = _wtoi(_wgetenv(L"APS5_WIDE_INT"));
static const wchar_t* s = _wgetenv(L"ANYPS5_WIDE_CONFIG");
static const char* t = std::getenv("NOT_AN_ENV");
"""
class EnvReferenceTests(unittest.TestCase):
def fixture(self):
directory = tempfile.TemporaryDirectory()
self.addCleanup(directory.cleanup)
root = Path(directory.name)
(root / "core").mkdir()
(root / "core" / "Sample.cpp").write_text(CODE, encoding="utf-8")
return root
def test_reads_find_every_reader_form_and_ignore_other_names(self):
root = self.fixture()
found = env_reference.reads([root / "core"], BOTH)
self.assertEqual(
set(found),
{"APS5_PROFILE_DRAW", "APS5_TRACE_GPU", "APS5_HOST_IMPORT_MIB",
"APS5_WORKER_AFFINITY_MASK", "ANYPS5_GPU", "APS5_THREAD_NICE",
"APS5_CRASH_INDIRECT_MEMORY", "APS5_PIPELINE_JOURNAL_MAX_MIB",
"APS5_PIPELINE_STORE_ENTRIES", "APS5_PIPELINE_JOURNAL_THREADS", "APS5_PM4_RING",
"ANYPS5_LOADEXEC_ARGV_SKIP", "ANYPS5_LOADEXEC_PARENT",
"ANYPS5_WIDE_CONFIG", "APS5_WIDE_PRESENT", "APS5_WIDE_INT"})
self.assertEqual(found["APS5_PROFILE_DRAW"][0][1], 1)
self.assertEqual(found["APS5_THREAD_NICE"][0][2:], ("integer", "-10"))
self.assertEqual(found["APS5_HOST_IMPORT_MIB"][0][2:], ("integer", "6144"))
self.assertEqual(found["APS5_PIPELINE_JOURNAL_MAX_MIB"][0][2:], ("integer", "1024"))
self.assertEqual(found["APS5_PIPELINE_STORE_ENTRIES"][0][2:], ("integer", "1024"))
self.assertEqual(found["APS5_PIPELINE_JOURNAL_THREADS"][0][2:], ("integer", ""))
self.assertEqual(found["APS5_PM4_RING"][0][2:], ("integer", "16"))
self.assertEqual(found["ANYPS5_LOADEXEC_ARGV_SKIP"][0][2:], ("string", ""))
self.assertEqual(found["ANYPS5_LOADEXEC_PARENT"][0][2:], ("string", ""))
self.assertEqual(found["ANYPS5_WIDE_CONFIG"][0][2:], ("string", ""))
self.assertEqual(found["APS5_WIDE_PRESENT"][0][2:], ("presence", ""))
self.assertEqual(found["APS5_WIDE_INT"][0][2:], ("integer", ""))
def test_the_default_prefixes_cover_both(self):
root = self.fixture()
found = env_reference.reads([root / "core"])
self.assertTrue(found)
self.assertTrue([name for name in found if name.startswith("APS5_")])
self.assertTrue([name for name in found if name.startswith("ANYPS5_")])
def test_check_passes_when_every_read_name_has_a_row(self):
root = self.fixture()
found = env_reference.reads([root / "core"])
doc = root / "ENVIRONMENT.md"
doc.write_text("\n".join("| `%s` |" % name for name in found), encoding="utf-8")
out = io.StringIO()
self.assertEqual(env_reference.check(found, doc, env_reference.PREFIXES, out), 0)
def test_check_reports_a_read_name_without_a_row(self):
root = self.fixture()
found = env_reference.reads([root / "core"])
doc = root / "ENVIRONMENT.md"
doc.write_text("| `APS5_PROFILE_DRAW` |", encoding="utf-8")
out = io.StringIO()
self.assertEqual(env_reference.check(found, doc, env_reference.PREFIXES, out), 1)
self.assertIn("APS5_TRACE_GPU", out.getvalue())
self.assertIn("has no row", out.getvalue())
def test_check_reports_a_row_the_code_no_longer_reads(self):
root = self.fixture()
found = env_reference.reads([root / "core"])
doc = root / "ENVIRONMENT.md"
names = ["| `%s` |" % name for name in found] + ["| `APS5_REMOVED` |"]
doc.write_text("\n".join(names), encoding="utf-8")
out = io.StringIO()
self.assertEqual(env_reference.check(found, doc, env_reference.PREFIXES, out), 1)
self.assertIn("APS5_REMOVED", out.getvalue())
self.assertIn("no longer reads", out.getvalue())
def test_check_fails_when_the_document_is_missing(self):
root = self.fixture()
found = env_reference.reads([root / "core"])
out = io.StringIO()
self.assertEqual(
env_reference.check(found, root / "missing.md", env_reference.PREFIXES, out), 1)
self.assertIn("cannot read", out.getvalue())
def test_ancestor_directory_named_in_skip_does_not_suppress_root_scan(self):
directory = tempfile.TemporaryDirectory()
self.addCleanup(directory.cleanup)
core = Path(directory.name) / "build" / "checkout" / "core"
(core / "3rdparty").mkdir(parents=True)
(core / "Sample.cpp").write_text('static bool a = IsEnvironmentSet("APS5_TRACE_GPU");\n', encoding="utf-8")
(core / "3rdparty" / "Ignored.cpp").write_text('static bool b = IsEnvironmentSet("APS5_IGNORED");\n', encoding="utf-8")
self.assertEqual(set(env_reference.reads([core], BOTH)), {"APS5_TRACE_GPU"})
def test_main_rejects_a_scan_root_that_is_not_a_directory(self):
root = self.fixture()
for name in ("missing", "core/Sample.cpp"):
for flags in (["--check"], ["--table"], []):
err = io.StringIO()
with contextlib.redirect_stdout(io.StringIO()) as out, contextlib.redirect_stderr(err):
code = env_reference.main(flags + ["--doc", str(root / "ENVIRONMENT.md"), "--root", str(root / name)])
self.assertEqual(code, 1, (name, flags))
self.assertIn("is not a directory", err.getvalue())
self.assertNotIn("no longer reads", out.getvalue())
if __name__ == "__main__":
unittest.main()