Viewing files at commit 2310099b696dCommit detailsView latest

Browse files
tests/test_environment.py 84 lines · 3.7 KB · python
1
from __future__ import annotations
2
3
import os
4
import shutil
5
import subprocess
6
import sys
7
import tempfile
8
import unittest
9
from pathlib import Path
10
from unittest import mock
11
12
sys.path.insert(0, str(Path(__file__).resolve().parents[1] / "scripts"))
13
14
from oakbench.environment import ENV_ISOLATION_VERSION, base_env  # noqa: E402
15
16
17
class EnvironmentPolicyTest(unittest.TestCase):
18
    def test_inherited_git_plumbing_cannot_redirect_any_lane(self):
19
        poison = {"GIT_DIR": "/wrong", "GIT_WORK_TREE": "/wrong", "GIT_INDEX_FILE": "/wrong",
20
                  "GIT_OBJECT_DIRECTORY": "/wrong", "GIT_CONFIG_COUNT": "1",
21
                  "GIT_CONFIG_KEY_0": "core.hooksPath", "GIT_CONFIG_VALUE_0": "/wrong",
22
                  "GIT_CONFIG_GLOBAL": "/wrong", "GIT_NO_REPLACE_OBJECTS": "0"}
23
        with mock.patch.dict(os.environ, poison):
24
            env = base_env()
25
        for key in poison.keys() - {"GIT_CONFIG_GLOBAL", "GIT_NO_REPLACE_OBJECTS"}:
26
            self.assertFalse(key in env, key)
27
        self.assertEqual(env["GIT_CONFIG_GLOBAL"], os.devnull)
28
        self.assertEqual(env["GIT_NO_REPLACE_OBJECTS"], "1")
29
30
    @unittest.skipUnless(shutil.which("git"), "Git required")
31
    def test_real_git_initializes_requested_checkout_with_poisoned_host_environment(self):
32
        with tempfile.TemporaryDirectory() as tmp:
33
            target, poison = Path(tmp) / "target", Path(tmp) / "poison"
34
            target.mkdir(); poison.mkdir()
35
            with mock.patch.dict(os.environ, {"GIT_DIR": str(poison / ".git"), "GIT_WORK_TREE": str(poison)}):
36
                process = subprocess.run([shutil.which("git"), "init", "-q"], cwd=target,
37
                                         env=base_env(), capture_output=True, timeout=20)
38
            self.assertEqual(process.returncode, 0, process.stderr)
39
            self.assertTrue((target / ".git").is_dir())
40
            self.assertFalse((poison / ".git").exists())
41
42
    def test_base_env_isolates_host_home_git_config_and_locale(self) -> None:
43
        env = base_env()
44
        bench_home = Path(env["HOME"])
45
46
        self.assertNotEqual(bench_home, Path.home())
47
        self.assertTrue(bench_home.is_dir())
48
        self.assertEqual(env["XDG_CONFIG_HOME"], str(bench_home / ".config"))
49
        self.assertEqual(env["XDG_CACHE_HOME"], str(bench_home / ".cache"))
50
        self.assertEqual(env["ZDOTDIR"], str(bench_home))
51
        self.assertEqual(env["BASH_ENV"], os.devnull)
52
        self.assertEqual(env["ENV"], os.devnull)
53
        self.assertEqual(env["GIT_CONFIG_GLOBAL"], os.devnull)
54
        self.assertEqual(env["GIT_CONFIG_NOSYSTEM"], "1")
55
        self.assertEqual(env["LC_ALL"], "C")
56
        self.assertEqual(env["LANG"], "C")
57
        self.assertEqual(env["TZ"], "UTC")
58
        self.assertEqual(env["OAK_BENCH_ENV_ISOLATION_VERSION"], ENV_ISOLATION_VERSION)
59
60
    def test_base_env_accepts_explicit_stable_home(self) -> None:
61
        with tempfile.TemporaryDirectory() as tmp:
62
            home = Path(tmp) / "bench-home"
63
            first = base_env(home=home)
64
            second = base_env(home=home)
65
        self.assertEqual(first["HOME"], second["HOME"])
66
        self.assertEqual(first["XDG_CONFIG_HOME"], str(home / ".config"))
67
68
    def test_base_env_preserves_existing_path_and_explicit_tokens(self) -> None:
69
        old_token = os.environ.get("OAK_API_KEY")
70
        try:
71
            os.environ["OAK_API_KEY"] = "test-token"
72
            env = base_env()
73
        finally:
74
            if old_token is None:
75
                os.environ.pop("OAK_API_KEY", None)
76
            else:
77
                os.environ["OAK_API_KEY"] = old_token
78
79
        self.assertEqual(env.get("PATH"), os.environ.get("PATH"))
80
        self.assertEqual(env["OAK_API_KEY"], "test-token")
81
82
83
if __name__ == "__main__":
84
    unittest.main()