Commit 58e3676c by Sébastien Eustace

Improve installation of directory and git dependencies

parent 179c4d2a
......@@ -23,6 +23,16 @@ class PipInstaller(BaseInstaller):
self._io = io
def install(self, package, update=False):
if package.source_type == "directory":
self.install_directory(package, update=update)
return
if package.source_type == "git":
self.install_git(package)
return
args = ["install", "--no-deps"]
if package.source_type == "legacy" and package.source_url:
......@@ -129,3 +139,72 @@ class PipInstaller(BaseInstaller):
os.close(fd)
return name
def install_directory(self, package, update=False):
from poetry.io import NullIO
from poetry.masonry.builder import SdistBuilder
from poetry.poetry import Poetry
from poetry.utils._compat import decode
from poetry.utils.env import NullEnv
from poetry.utils.toml_file import TomlFile
if package.root_dir:
req = os.path.join(package.root_dir, package.source_url)
else:
req = os.path.realpath(package.source_url)
args = ["install", "--no-deps", "-U"]
pyproject = TomlFile(os.path.join(req, "pyproject.toml"))
has_poetry = False
if pyproject.exists():
pyproject_content = pyproject.read()
has_poetry = (
"tool" in pyproject_content and "poetry" in pyproject_content["tool"]
)
has_build_system = "build-system" in pyproject_content
setup = os.path.join(req, "setup.py")
has_setup = os.path.exists(setup)
if not has_setup and has_poetry and (package.develop or not has_build_system):
# We actually need to rely on creating a temporary setup.py
# file since pip, as of this comment, does not support
# build-system for editable packages
# We also need it for non-PEP-517 packages
builder = SdistBuilder(Poetry.create(pyproject.parent), NullEnv(), NullIO())
with open(setup, "w") as f:
f.write(decode(builder.build_setup()))
if package.develop:
args.append("-e")
args.append(req)
try:
return self.run(*args)
finally:
if not has_setup and os.path.exists(setup):
os.remove(setup)
def install_git(self, package):
from poetry.packages import Package
from poetry.utils._compat import Path
from poetry.utils.helpers import temporary_directory
from poetry.vcs import Git
with temporary_directory() as tmp_dir:
tmp_dir = Path(tmp_dir)
git = Git()
git.clone(package.source_url, tmp_dir)
git.checkout(package.source_reference, tmp_dir)
# Now we just need to install from the temporary directory
pkg = Package(package.name, package.version)
pkg.source_type = "directory"
pkg.source_url = str(tmp_dir)
pkg.develop = False
self.install_directory(pkg)
......@@ -9,7 +9,6 @@ from poetry.utils._compat import Path
from poetry.utils._compat import decode
from poetry.utils.helpers import parse_requires
from poetry.utils.toml_file import TomlFile
from poetry.utils.env import NullEnv
from poetry.utils.env import Env
from .dependency import Dependency
......@@ -27,7 +26,7 @@ class DirectoryDependency(Dependency):
category="main", # type: str
optional=False, # type: bool
base=None, # type: Path
develop=False, # type: bool
develop=True, # type: bool
):
from . import dependency_from_pep_508
from .package import Package
......@@ -36,6 +35,7 @@ class DirectoryDependency(Dependency):
self._base = base
self._full_path = path
self._develop = develop
self._supports_poetry = False
if self._base and not self._path.is_absolute():
self._full_path = self._base / self._path
......@@ -49,29 +49,23 @@ class DirectoryDependency(Dependency):
# Checking content to dertermine actions
setup = self._full_path / "setup.py"
pyproject = TomlFile(self._full_path / "pyproject.toml")
has_poetry = False
if pyproject.exists():
pyproject_content = pyproject.read()
has_poetry = (
self._supports_poetry = (
"tool" in pyproject_content and "poetry" in pyproject_content["tool"]
)
if not setup.exists() and not has_poetry:
if not setup.exists() and not self._supports_poetry:
raise ValueError(
"Directory {} does not seem to be a Python package".format(
self._full_path
)
)
if has_poetry:
from poetry.masonry.builders import SdistBuilder
if self._supports_poetry:
from poetry.poetry import Poetry
poetry = Poetry.create(self._full_path)
builder = SdistBuilder(poetry, NullEnv(), NullIO())
with setup.open("w") as f:
f.write(decode(builder.build_setup()))
package = poetry.package
self._package = Package(package.pretty_name, package.version)
......@@ -148,5 +142,8 @@ class DirectoryDependency(Dependency):
def develop(self):
return self._develop
def supports_poetry(self):
return self._supports_poetry
def is_directory(self):
return True
......@@ -75,7 +75,7 @@ class Package(object):
self.root_dir = None
self.develop = False
self.develop = True
@property
def name(self):
......@@ -106,6 +106,9 @@ class Package(object):
@property
def full_pretty_version(self):
if self.source_type in ["file", "directory"]:
return "{} {}".format(self._pretty_version, self.source_url)
if self.source_type not in ["hg", "git"]:
return self._pretty_version
......@@ -266,7 +269,7 @@ class Package(object):
category=category,
optional=optional,
base=self.root_dir,
develop=constraint.get("develop", False),
develop=constraint.get("develop", True),
)
else:
version = constraint["version"]
......
......@@ -197,7 +197,7 @@ Package operations: 2 installs, 0 updates, 0 removals
Writing lock file
- Installing pendulum (1.4.4)
- Installing demo (0.1.0)
- Installing demo (0.1.0 ../distributions/demo-0.1.0-py2.py3-none-any.whl)
"""
assert tester.get_display(True) == expected
......@@ -237,7 +237,7 @@ Package operations: 2 installs, 0 updates, 0 removals
Writing lock file
- Installing pendulum (1.4.4)
- Installing demo (0.1.0)
- Installing demo (0.1.0 ../distributions/demo-0.1.0.tar.gz)
"""
assert tester.get_display(True) == expected
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment