Repository: tox-dev/tox

Issue:
Tox passenv by default only passes HTTP_PROXY but not http_proxy
According to the docs, tox passenv is [case insensitive](https://tox.wiki/en/latest/config.html#conf-passenv). Apparently this is not the case for variables passed through by default. This means that e.g. `HTTP_PROXY` will be forwarded by default, but not `http_proxy`. This is a problem because some linux programs look for the upper-case version (e.g. `pip`) and some for the lower-case version (e.g. `apt` and `git`).

This problem can be worked around by explicitly setting `passenv = HTTP_PROXY HTTPS_PROXY`, because then tox will also include the lower-case pendants, but this feels a bit counter-intuitive.

I'd propose to either include the lower-cased proxy variables into the list of default variables (and clarify in the docs that case-insensitivity doesn't apply for default variables) or treat all default variables as case insensitive. I can also prepare a PR for any of the two solutions if desired.

Discussion:

Patch:
diff --git a/CONTRIBUTORS b/CONTRIBUTORS
index ca325a32..f3fc3407 100644
--- a/CONTRIBUTORS
+++ b/CONTRIBUTORS
@@ -35,6 +35,7 @@ David Diaz
 Ederag
 Eli Collins
 Eugene Yunak
+Fabian Poggenhans
 Felix Hildén
 Fernando L. Pereira
 Florian Bruhin
diff --git a/docs/changelog/2372.feature.rst b/docs/changelog/2372.feature.rst
new file mode 100644
index 00000000..470dbc5f
--- /dev/null
+++ b/docs/changelog/2372.feature.rst
@@ -0,0 +1,1 @@
+Add default environment variables (such as http_proxy) regardless of their case to passenv on UNIX -- by :user:`poggenhans`.
diff --git a/docs/config.rst b/docs/config.rst
index 8f277ffe..c579733e 100644
--- a/docs/config.rst
+++ b/docs/config.rst
@@ -460,7 +460,8 @@ Complete list of settings that you can put into ``testenv*`` sections:
     ``A`` will pass both ``A`` and ``a``.
 
     Some variables are always passed through to ensure the basic functionality
-    of standard library functions or tooling like pip:
+    of standard library functions or tooling like pip.
+    This is also not case sensitive on all platforms except Windows:
 
     * passed through on all platforms: ``CURL_CA_BUNDLE``, ``PATH``,
       ``LANG``, ``LANGUAGE``,
diff --git a/src/tox/config/__init__.py b/src/tox/config/__init__.py
index 10acbe12..b155fd1c 100644
--- a/src/tox/config/__init__.py
+++ b/src/tox/config/__init__.py
@@ -809,6 +809,10 @@ def tox_addoption(parser):
             passenv.add("MSYSTEM")  # fixes #429
         else:
             passenv.add("TMPDIR")
+
+            # add non-uppercased variables to passenv if present (only necessary for UNIX)
+            passenv.update(name for name in os.environ if name.upper() in passenv)
+
         for spec in value:
             for name in os.environ:
                 if fnmatchcase(name.upper(), spec.upper()):


Test patch:
diff --git a/tests/unit/config/test_config.py b/tests/unit/config/test_config.py
index d6ff0aba..6949bf93 100644
--- a/tests/unit/config/test_config.py
+++ b/tests/unit/config/test_config.py
@@ -1494,6 +1494,8 @@ class TestConfigTestEnv:
         monkeypatch.setenv("A123A", "a")
         monkeypatch.setenv("A123B", "b")
         monkeypatch.setenv("BX23", "0")
+        if plat == "linux2":
+            monkeypatch.setenv("http_proxy", "c")
         config = newconfig(
             """
             [testenv]
@@ -1518,6 +1520,9 @@ class TestConfigTestEnv:
             assert "MSYSTEM" in envconfig.passenv
         else:
             assert "TMPDIR" in envconfig.passenv
+            if sys.platform != "win32":
+                # this cannot be emulated on win - it doesn't support lowercase env vars
+                assert "http_proxy" in envconfig.passenv
         assert "CURL_CA_BUNDLE" in envconfig.passenv
         assert "PATH" in envconfig.passenv
         assert "PIP_INDEX_URL" in envconfig.passenv
@@ -3575,7 +3580,7 @@ def test_config_via_pyproject_legacy(initproj):
     initproj(
         "config_via_pyproject_legacy-0.5",
         filedefs={
-            "pyproject.toml": u'''
+            "pyproject.toml": '''
                 [project]
                 description = "Factory ⸻ A code generator 🏭"
                 authors = [{name = "Łukasz Langa"}]