11from __future__ import annotations
22
33from pathlib import Path
4- from typing import TYPE_CHECKING , Any
4+ from typing import TYPE_CHECKING , Any , Literal
55from unittest .mock import ANY
66
77import pytest
@@ -51,19 +51,30 @@ def test_set_env_bad_line() -> None:
5151 SetEnv ("A" , "py" , "py" , Path ())
5252
5353
54+ ConfigFileFormat = Literal ["ini" , "toml" ]
55+
56+
5457class EvalSetEnv (Protocol ):
5558 def __call__ (
5659 self ,
57- tox_ini : str ,
60+ config : str ,
61+ * ,
62+ of_type : ConfigFileFormat = "ini" ,
5863 extra_files : dict [str , Any ] | None = ...,
5964 from_cwd : Path | None = ...,
6065 ) -> SetEnv : ...
6166
6267
6368@pytest .fixture
6469def eval_set_env (tox_project : ToxProjectCreator ) -> EvalSetEnv :
65- def func (tox_ini : str , extra_files : dict [str , Any ] | None = None , from_cwd : Path | None = None ) -> SetEnv :
66- prj = tox_project ({"tox.ini" : tox_ini , ** (extra_files or {})})
70+ def func (
71+ config : str ,
72+ * ,
73+ of_type : ConfigFileFormat = "ini" ,
74+ extra_files : dict [str , Any ] | None = None ,
75+ from_cwd : Path | None = None ,
76+ ) -> SetEnv :
77+ prj = tox_project ({f"tox.{ of_type } " : config , ** (extra_files or {})})
6778 result = prj .run ("c" , "-k" , "set_env" , "-e" , "py" , from_cwd = None if from_cwd is None else prj .path / from_cwd )
6879 result .assert_success ()
6980 set_env : SetEnv = result .env_conf ("py" )["set_env" ]
@@ -149,7 +160,20 @@ def test_set_env_honor_override(eval_set_env: EvalSetEnv) -> None:
149160 assert set_env .load ("PIP_DISABLE_PIP_VERSION_CHECK" ) == "0"
150161
151162
152- def test_set_env_environment_file (eval_set_env : EvalSetEnv ) -> None :
163+ @pytest .mark .parametrize (
164+ ("of_type" , "config" ),
165+ [
166+ pytest .param ("ini" , "[testenv]\n package=skip\n set_env=file|A{/}a.txt\n change_dir=C" , id = "ini" ),
167+ pytest .param ("toml" , '[env_run_base]\n package="skip"\n set_env={file="A{/}a.txt"}\n change_dir="C"' , id = "toml" ),
168+ pytest .param ("ini" , "[testenv]\n package=skip\n set_env=file|{env:env_file}\n change_dir=C" , id = "ini-env" ),
169+ pytest .param (
170+ "toml" , '[env_run_base]\n package="skip"\n set_env={file="{env:env_file}"}\n change_dir="C"' , id = "toml-env"
171+ ),
172+ ],
173+ )
174+ def test_set_env_environment_file (
175+ of_type : ConfigFileFormat , config : str , eval_set_env : EvalSetEnv , monkeypatch : MonkeyPatch
176+ ) -> None :
153177 env_file = """
154178 A=1
155179 B= 2
@@ -158,9 +182,10 @@ def test_set_env_environment_file(eval_set_env: EvalSetEnv) -> None:
158182 E = "1"
159183 F =
160184 """
185+ monkeypatch .setenv ("env_file" , "A{/}a.txt" )
186+
161187 extra = {"A" : {"a.txt" : env_file }, "B" : None , "C" : None }
162- ini = "[testenv]\n package=skip\n set_env=file|A{/}a.txt\n change_dir=C"
163- set_env = eval_set_env (ini , extra_files = extra , from_cwd = Path ("B" ))
188+ set_env = eval_set_env (config , of_type = of_type , extra_files = extra , from_cwd = Path ("B" ))
164189 content = {k : set_env .load (k ) for k in set_env }
165190 assert content == {
166191 "PIP_DISABLE_PIP_VERSION_CHECK" : "1" ,
@@ -174,6 +199,42 @@ def test_set_env_environment_file(eval_set_env: EvalSetEnv) -> None:
174199 }
175200
176201
202+ @pytest .mark .parametrize (
203+ ("of_type" , "config" ),
204+ [
205+ pytest .param ("ini" , "[testenv]\n package=skip\n set_env=file|A{/}a.txt\n X=y\n change_dir=C" , id = "ini" ),
206+ pytest .param (
207+ "toml" , '[env_run_base]\n package="skip"\n set_env={file="A{/}a.txt", X="y"}\n change_dir="C"' , id = "toml"
208+ ),
209+ pytest .param ("ini" , "[testenv]\n package=skip\n set_env=file|{env:env_file}\n X=y\n change_dir=C" , id = "ini-env" ),
210+ pytest .param (
211+ "toml" ,
212+ '[env_run_base]\n package="skip"\n set_env={file="{env:env_file}", X="y"}\n change_dir="C"' ,
213+ id = "toml-env" ,
214+ ),
215+ ],
216+ )
217+ def test_set_env_environment_file_combined_with_normal_setting (
218+ of_type : ConfigFileFormat , config : str , eval_set_env : EvalSetEnv , monkeypatch : MonkeyPatch
219+ ) -> None :
220+ env_file = """
221+ A=1
222+ """
223+ # Monkeypatch only used for some of the parameters
224+ monkeypatch .setenv ("env_file" , "A{/}a.txt" )
225+
226+ extra = {"A" : {"a.txt" : env_file }, "B" : None , "C" : None }
227+ set_env = eval_set_env (config , of_type = of_type , extra_files = extra , from_cwd = Path ("B" ))
228+ content = {k : set_env .load (k ) for k in set_env }
229+ assert content == {
230+ "PIP_DISABLE_PIP_VERSION_CHECK" : "1" ,
231+ "PYTHONHASHSEED" : ANY ,
232+ "A" : "1" ,
233+ "X" : "y" ,
234+ "PYTHONIOENCODING" : "utf-8" ,
235+ }
236+
237+
177238def test_set_env_environment_file_missing (tox_project : ToxProjectCreator ) -> None :
178239 project = tox_project ({"tox.ini" : "[testenv]\n package=skip\n set_env=file|magic.txt" })
179240 result = project .run ("r" )
0 commit comments