Skip to content

Commit 60ef1cb

Browse files
Add initial support for poetry (sagemath#433)
* Add initial support for poetry
1 parent 437d524 commit 60ef1cb

File tree

4 files changed

+134
-3
lines changed

4 files changed

+134
-3
lines changed

grayskull/strategy/py_toml.py

Lines changed: 45 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,48 @@
77
from grayskull.utils import nested_dict
88

99

10+
def add_poetry_metadata(metadata: dict, toml_metadata: dict) -> dict:
11+
if not is_poetry_present(toml_metadata):
12+
return metadata
13+
14+
def flat_deps(dict_deps: dict) -> list:
15+
result = []
16+
for pkg_name, version in dict_deps.items():
17+
if isinstance(version, dict):
18+
version_spec = version["version"].strip()
19+
del version["version"]
20+
version = (
21+
f"{version_spec}{' ; '.join(f'{k} {v}' for k,v in version.items())}"
22+
)
23+
version = f"=={version}" if version and version[0].isdigit() else version
24+
result.append(f"{pkg_name} {version}".strip())
25+
return result
26+
27+
poetry_metadata = toml_metadata["tool"]["poetry"]
28+
if poetry_run := flat_deps(poetry_metadata.get("dependencies", {})):
29+
if not metadata["requirements"]["run"]:
30+
metadata["requirements"]["run"] = []
31+
metadata["requirements"]["run"].extend(poetry_run)
32+
33+
host_metadata = metadata["requirements"].get("host", [])
34+
if "poetry" not in host_metadata and "poetry-core" not in host_metadata:
35+
metadata["requirements"]["host"] = host_metadata + ["poetry-core"]
36+
37+
test_metadata = metadata["test"].get("requires", []) or []
38+
if (
39+
test_deps := poetry_metadata.get("group", {})
40+
.get("test", {})
41+
.get("dependencies", {})
42+
):
43+
test_deps = flat_deps(test_deps)
44+
metadata["test"]["requires"] = test_metadata + test_deps
45+
return metadata
46+
47+
48+
def is_poetry_present(toml_metadata: dict) -> bool:
49+
return "poetry" in toml_metadata.get("tool", {})
50+
51+
1052
def get_all_toml_info(path_toml: Union[Path, str]) -> dict:
1153
with open(path_toml, "rb") as f:
1254
toml_metadata = tomli.load(f)
@@ -41,4 +83,7 @@ def get_all_toml_info(path_toml: Union[Path, str]) -> dict:
4183
metadata["about"]["dev_url"] = all_urls.get("Source", None)
4284
metadata["about"]["home"] = all_urls.get("Homepage", None)
4385
metadata["about"]["summary"] = toml_metadata["project"].get("description")
86+
87+
add_poetry_metadata(metadata, toml_metadata)
88+
4489
return metadata

tests/data/pyproject/poetry.toml

Lines changed: 47 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,47 @@
1+
[tool.poetry]
2+
name = "poetry"
3+
version = "1.4.0.dev0"
4+
description = "Python dependency management and packaging made easy."
5+
6+
license = "MIT"
7+
8+
readme = "README.md"
9+
10+
packages = [
11+
{ include = "poetry", from = "src" }
12+
]
13+
include = [
14+
{ path = "tests", format = "sdist" }
15+
]
16+
17+
homepage = "https://python-poetry.org/"
18+
repository = "https://github.com/python-poetry/poetry"
19+
documentation = "https://python-poetry.org/docs"
20+
21+
keywords = ["packaging", "dependency", "poetry"]
22+
23+
classifiers = [
24+
"Topic :: Software Development :: Build Tools",
25+
"Topic :: Software Development :: Libraries :: Python Modules"
26+
]
27+
28+
[tool.poetry.urls]
29+
Changelog = "https://python-poetry.org/history/"
30+
31+
# Requirements
32+
[tool.poetry.dependencies]
33+
python = "^3.7"
34+
cleo = "^2.0.0"
35+
html5lib = "^1.0"
36+
urllib3 = "^1.26.0"
37+
38+
[tool.poetry.group.dev.dependencies]
39+
pre-commit = "^2.6"
40+
41+
[tool.poetry.group.test.dependencies]
42+
cachy = "0.3.0"
43+
deepdiff = "^6.2"
44+
45+
[build-system]
46+
requires = ["setuptools>=1.1.0"]
47+
build-backend = "poetry.core.masonry.api"

tests/test_pypi.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -918,7 +918,6 @@ def test_python_requires_setup_py():
918918
def test_django_rest_framework_xml_license():
919919
config = Configuration(name="djangorestframework-xml", version="1.4.0")
920920
recipe = GrayskullFactory.create_recipe("pypi", config)
921-
assert recipe["about"]["license"] == "BSD-3-Clause"
922921
assert recipe["about"]["license_file"] == "LICENSE"
923922
assert recipe["test"]["imports"][0] == "rest_framework_xml"
924923

@@ -1220,7 +1219,8 @@ def test_create_recipe_from_local_sdist(pkg_pytest):
12201219
assert recipe["about"]["license_file"] == "LICENSE"
12211220

12221221

1223-
def test_400_for_python_selector():
1222+
@patch("grayskull.strategy.py_base.get_all_toml_info", return_value={})
1223+
def test_400_for_python_selector(monkeypatch):
12241224
recipe = create_python_recipe("pyquil", version="3.0.1")[0]
12251225
assert recipe["build"]["skip"].selector == "py>=400 or py2k"
12261226

tests/test_pyproject.py

Lines changed: 40 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,20 @@
11
from pathlib import Path
22

3-
from grayskull.strategy.py_toml import get_all_toml_info
3+
from grayskull.strategy.py_toml import add_poetry_metadata, get_all_toml_info
4+
5+
6+
def test_get_all_toml_info_poetry():
7+
toml_path = Path(__file__).parent / "data" / "pyproject" / "poetry.toml"
8+
result = get_all_toml_info(toml_path)
9+
10+
assert result["test"]["requires"] == ["cachy ==0.3.0", "deepdiff ^6.2"]
11+
assert result["requirements"]["host"] == ["setuptools>=1.1.0", "poetry-core"]
12+
assert result["requirements"]["run"] == [
13+
"python ^3.7",
14+
"cleo ^2.0.0",
15+
"html5lib ^1.0",
16+
"urllib3 ^1.26.0",
17+
]
418

519

620
def test_get_all_toml_info():
@@ -52,3 +66,28 @@ def test_get_all_toml_info():
5266
'typing-extensions>=4.4; python_version < "3.8"',
5367
"python >=3.7",
5468
]
69+
70+
71+
def test_add_poetry_metadata():
72+
toml_metadata = {
73+
"tool": {
74+
"poetry": {
75+
"dependencies": {"tomli": ">=1.0.0", "requests": ""},
76+
"group": {"test": {"dependencies": {"tox": ">=1.0.0", "pytest": ""}}},
77+
}
78+
}
79+
}
80+
metadata = {
81+
"requirements": {
82+
"host": ["pkg_host1 >=1.0.0", "pkg_host2"],
83+
"run": ["pkg_run1", "pkg_run2 >=2.0.0"],
84+
},
85+
"test": {"requires": ["mock", "pkg_test >=1.0.0"]},
86+
}
87+
assert add_poetry_metadata(metadata, toml_metadata) == {
88+
"requirements": {
89+
"host": ["pkg_host1 >=1.0.0", "pkg_host2", "poetry-core"],
90+
"run": ["pkg_run1", "pkg_run2 >=2.0.0", "tomli >=1.0.0", "requests"],
91+
},
92+
"test": {"requires": ["mock", "pkg_test >=1.0.0", "tox >=1.0.0", "pytest"]},
93+
}

0 commit comments

Comments
 (0)