def create_poetry( self, cwd=None, io=None): # type: (Optional[Path], Optional[IO]) -> Poetry if io is None: io = NullIO() base_poetry = super(Factory, self).create_poetry(cwd) locker = Locker(base_poetry.file.parent / "poetry.lock", base_poetry.local_config) # Loading global configuration config = self.create_config(io) # Loading local configuration local_config_file = TomlFile(base_poetry.file.parent / "poetry.toml") if local_config_file.exists(): if io.is_debug(): io.write_line("Loading configuration file {}".format( local_config_file.path)) config.merge(local_config_file.read()) poetry = Poetry( base_poetry.file.path, base_poetry.local_config, base_poetry.package, locker, config, ) # Configuring sources for source in poetry.local_config.get("source", []): repository = self.create_legacy_repository(source, config) is_default = source.get("default", False) is_secondary = source.get("secondary", False) if io.is_debug(): message = "Adding repository {} ({})".format( repository.name, repository.url) if is_default: message += " and setting it as the default one" elif is_secondary: message += " and setting it as secondary" io.write_line(message) poetry.pool.add_repository(repository, is_default, secondary=is_secondary) # Always put PyPI last to prefer private repositories # but only if we have no other default source if not poetry.pool.has_default(): poetry.pool.add_repository(PyPiRepository(), True) else: if io.is_debug(): io.write_line("Deactivating the PyPI repository") return poetry
def temporary_project_directory( path, toml_patch=None ): # type: (Path, Optional[Dict[str, Any]]) -> ContextManager[str] """ Context manager that takes a project source directory, copies content to a temporary directory, patches the `pyproject.toml` using the provided patch, or using the default patch if one is not given. The default path replaces `build-system` section in order to use the working copy of poetry-core as the backend. Once the context, exists, the temporary directory is cleaned up. :param path: Source project root directory to copy from. :param toml_patch: Patch to use for the pyproject.toml, defaults to build system patching. :return: A temporary copy """ assert (path / "pyproject.toml").exists() with tempfile.TemporaryDirectory(prefix="poetry-core-pep517") as tmp: dst = Path(tmp) / path.name shutil.copytree(str(path), dst) toml = TomlFile(str(dst / "pyproject.toml")) data = toml.read() data.update(toml_patch or __toml_build_backend_patch__) toml.write(data) yield str(dst)
def test_old_pyproject_toml_file_deprecation( pyproject_toml, build_system_section, poetry_section ): with pytest.warns(DeprecationWarning): file = TomlFile(pyproject_toml) data = file.read() assert data == PyProjectTOMLFile(pyproject_toml).read()
def test_old_pyproject_toml_file_deprecation( pyproject_toml: Path, build_system_section: str, poetry_section: str ) -> None: from poetry.core.utils.toml_file import TomlFile with pytest.warns(DeprecationWarning): file = TomlFile(pyproject_toml) data = file.read() assert data == TOMLFile(pyproject_toml).read()
def test_validate_fails(): complete = TomlFile(fixtures_dir / "complete.toml") content = complete.read()["tool"]["poetry"] content["this key is not in the schema"] = "" if PY2: expected = ("Additional properties are not allowed " "(u'this key is not in the schema' was unexpected)") else: expected = ("Additional properties are not allowed " "('this key is not in the schema' was unexpected)") assert Factory.validate(content) == {"errors": [expected], "warnings": []}
def create_config(cls, io=None): # type: (Optional[IO]) -> Config if io is None: io = NullIO() config = Config() # Load global config config_file = TomlFile(Path(CONFIG_DIR) / "config.toml") if config_file.exists(): if io.is_debug(): io.write_line( "<debug>Loading configuration file {}</debug>".format( config_file.path)) config.merge(config_file.read()) config.set_config_source(FileConfigSource(config_file)) # Load global auth config auth_config_file = TomlFile(Path(CONFIG_DIR) / "auth.toml") if auth_config_file.exists(): if io.is_debug(): io.write_line( "<debug>Loading configuration file {}</debug>".format( auth_config_file.path)) config.merge(auth_config_file.read()) config.set_auth_config_source(FileConfigSource(auth_config_file)) return config
def __init__( self, name, path, # type: Path category="main", # type: str optional=False, # type: bool base=None, # type: Path develop=True, # type: bool ): self._path = path 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 if not self._full_path.exists(): raise ValueError("Directory {} does not exist".format(self._path)) if self._full_path.is_file(): raise ValueError("{} is a file, expected a directory".format( self._path)) # Checking content to determine actions setup = self._full_path / "setup.py" pyproject = TomlFile(self._full_path / "pyproject.toml") if pyproject.exists(): pyproject_content = pyproject.read() self._supports_poetry = ("tool" in pyproject_content and "poetry" in pyproject_content["tool"]) if not setup.exists() and not self._supports_poetry: raise ValueError( "Directory {} does not seem to be a Python package".format( self._full_path)) super(DirectoryDependency, self).__init__(name, "*", category=category, optional=optional, allows_prereleases=True)
def test_validate(): complete = TomlFile(fixtures_dir / "complete.toml") content = complete.read()["tool"]["poetry"] assert Factory.validate(content) == {"errors": [], "warnings": []}