summaryrefslogtreecommitdiff
path: root/src/setuptools_scm/_integration/setuptools.py
diff options
context:
space:
mode:
Diffstat (limited to 'src/setuptools_scm/_integration/setuptools.py')
-rw-r--r--src/setuptools_scm/_integration/setuptools.py105
1 files changed, 105 insertions, 0 deletions
diff --git a/src/setuptools_scm/_integration/setuptools.py b/src/setuptools_scm/_integration/setuptools.py
index 6e04148..94981d7 100644
--- a/src/setuptools_scm/_integration/setuptools.py
+++ b/src/setuptools_scm/_integration/setuptools.py
@@ -1,6 +1,17 @@
from __future__ import annotations
+import logging
import os
+import warnings
+from typing import Any
+from typing import Callable
+
+import setuptools
+
+from .. import _config
+from .._version_cls import _validate_version_cls
+
+log = logging.getLogger(__name__)
def read_dist_name_from_setup_cfg(
@@ -13,3 +24,97 @@ def read_dist_name_from_setup_cfg(
parser.read([input], encoding="utf-8")
dist_name = parser.get("metadata", "name", fallback=None)
return dist_name
+
+
+def _warn_on_old_setuptools(_version: str = setuptools.__version__) -> None:
+ if int(_version.split(".")[0]) < 61:
+ warnings.warn(
+ RuntimeWarning(
+ f"""
+ERROR: setuptools=={_version} is used in combination with setuptools_scm>=8.x
+
+Your build configuration is incomplete and previously worked by accident!
+setuptools_scm requires setuptools>=61
+
+Suggested workaround if applicable:
+ - migrating from the deprecated setup_requires mechanism to pep517/518
+ and using a pyproject.toml to declare build dependencies
+ which are reliably pre-installed before running the build tools
+"""
+ )
+ )
+
+
+def _assign_version(
+ dist: setuptools.Distribution, config: _config.Configuration
+) -> None:
+ from .. import _get_version, _version_missing
+
+ maybe_version = _get_version(config)
+
+ if maybe_version is None:
+ _version_missing(config)
+ else:
+ assert dist.metadata.version is None
+ dist.metadata.version = maybe_version
+
+
+_warn_on_old_setuptools()
+
+
+def version_keyword(
+ dist: setuptools.Distribution,
+ keyword: str,
+ value: bool | dict[str, Any] | Callable[[], dict[str, Any]],
+) -> None:
+ if not value:
+ return
+ elif value is True:
+ value = {}
+ elif callable(value):
+ value = value()
+ assert (
+ "dist_name" not in value
+ ), "dist_name may not be specified in the setup keyword "
+ dist_name: str | None = dist.metadata.name
+ if dist.metadata.version is not None:
+ warnings.warn(f"version of {dist_name} already set")
+ return
+ log.debug(
+ "version keyword %r",
+ vars(dist.metadata),
+ )
+ log.debug("dist %s %s", id(dist), id(dist.metadata))
+
+ if dist_name is None:
+ dist_name = read_dist_name_from_setup_cfg()
+ version_cls = value.pop("version_cls", None)
+ normalize = value.pop("normalize", True)
+ final_version = _validate_version_cls(version_cls, normalize)
+ config = _config.Configuration(
+ dist_name=dist_name, version_cls=final_version, **value
+ )
+ _assign_version(dist, config)
+
+
+def infer_version(dist: setuptools.Distribution) -> None:
+ log.debug(
+ "finalize hook %r",
+ vars(dist.metadata),
+ )
+ log.debug("dist %s %s", id(dist), id(dist.metadata))
+ if dist.metadata.version is not None:
+ return # metadata already added by hook
+ dist_name = dist.metadata.name
+ if dist_name is None:
+ dist_name = read_dist_name_from_setup_cfg()
+ if not os.path.isfile("pyproject.toml"):
+ return
+ if dist_name == "setuptools_scm":
+ return
+ try:
+ config = _config.Configuration.from_file(dist_name=dist_name)
+ except LookupError as e:
+ log.exception(e)
+ else:
+ _assign_version(dist, config)