diff --git a/backend/src/hatchling/version/source/env.py b/backend/src/hatchling/version/source/env.py index b46389437..efdbc92e3 100644 --- a/backend/src/hatchling/version/source/env.py +++ b/backend/src/hatchling/version/source/env.py @@ -10,6 +10,8 @@ class EnvSource(VersionSourceInterface): def get_version_data(self) -> dict: variable = self.config.get('variable', '') + default_value = self.config.get('default-value', '') + if not variable: message = 'option `variable` must be specified' raise ValueError(message) @@ -18,11 +20,15 @@ def get_version_data(self) -> dict: message = 'option `variable` must be a string' raise TypeError(message) - if variable not in os.environ: + if default_value and not isinstance(default_value, str): + message = 'option `default-value` must be a string' + raise TypeError(message) + + if variable not in os.environ and not default_value: message = f'environment variable `{variable}` is not set' raise RuntimeError(message) - return {'version': os.environ[variable]} + return {'version': os.getenv(variable, default_value)} def set_version(self, version: str, version_data: dict) -> None: # noqa: ARG002, PLR6301 message = 'Cannot set environment variables' diff --git a/docs/plugins/version-source/env.md b/docs/plugins/version-source/env.md index 125b23104..d6c27c08d 100644 --- a/docs/plugins/version-source/env.md +++ b/docs/plugins/version-source/env.md @@ -22,3 +22,4 @@ source = "env" | Option | Description | | --- | --- | | `variable` (required) | The name of the environment variable | +| `default-value` | The value to use if the environment variable is not set | \ No newline at end of file diff --git a/tests/backend/version/source/test_env.py b/tests/backend/version/source/test_env.py index 3e8d74847..3eab34460 100644 --- a/tests/backend/version/source/test_env.py +++ b/tests/backend/version/source/test_env.py @@ -18,6 +18,13 @@ def test_variable_not_string(isolation): source.get_version_data() +def test_default_value_not_string(isolation): + source = EnvSource(str(isolation), {'variable': 'ENV_VERSION', 'default-value': 1}) + + with pytest.raises(TypeError, match='option `default-value` must be a string'): + source.get_version_data() + + def test_variable_not_available(isolation): source = EnvSource(str(isolation), {'variable': 'ENV_VERSION'}) @@ -27,6 +34,13 @@ def test_variable_not_available(isolation): source.get_version_data() +def test_variable_not_available_with_default_value(isolation): + source = EnvSource(str(isolation), {'variable': 'ENV_VERSION', 'default-value': '0.0.1'}) + + with EnvVars(exclude=['ENV_VERSION']): + assert source.get_version_data()['version'] == '0.0.1' + + def test_variable_contains_version(isolation): source = EnvSource(str(isolation), {'variable': 'ENV_VERSION'})