From a5e2389dfa85b95d825f6397a8fe88cb4481ad35 Mon Sep 17 00:00:00 2001 From: Chang Y Date: Sat, 28 Mar 2020 14:59:01 +0800 Subject: [PATCH 01/80] fix typo in examples fix typo in examples --- docs/cmd-deps-convert.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/docs/cmd-deps-convert.md b/docs/cmd-deps-convert.md index 4c2ede46..b48c1c2b 100644 --- a/docs/cmd-deps-convert.md +++ b/docs/cmd-deps-convert.md @@ -85,9 +85,9 @@ You can convert anything to anything: 1. Lock Pipfile: `dephell deps convert --from=Pipfile --to=Pipfile.lock` 1. Lock poetry: `dephell deps convert --from=pyproject.toml --to=poetry.lock` 1. Migrate from setup.py to poetry: `dephell deps convert --from=setup.py --to=pyproject.toml` -1. Migrate from pipenv to poetry: `dephell deps convert --from=Pipenv --to=pyproject.toml` +1. Migrate from pipenv to poetry: `dephell deps convert --from=Pipfile --to=pyproject.toml` 1. Generate setup.py for poetry (to make project backward compatible with setuptools): `dephell deps convert --from=pyproject.toml --to=setup.py` -1. Generate requirements.txt from Pipfile to work on a pipenv-based project without pipenv: `dephell deps convert --from=Pipenv --to=requirements.txt` +1. Generate requirements.txt from Pipfile to work on a pipenv-based project without pipenv: `dephell deps convert --from=Pipfile --to=requirements.txt` 1. Generate requirements.txt from poetry to work on a poetry-based project without poetry: `dephell deps convert --from=pyproject.toml --to=requirements.txt` 1. Pipe poetry requirements into pip for installation in a custom environment: `pip install -r <(dephell deps convert --to-path stdout --to-format pip)` From 33563f785fe6a689b6045ba0c26f56c06e21c3b0 Mon Sep 17 00:00:00 2001 From: Gram Date: Fri, 3 Apr 2020 14:03:39 +0200 Subject: [PATCH 02/80] stable egg-info parsing --- dephell/converters/egginfo.py | 14 ++++++++++++-- 1 file changed, 12 insertions(+), 2 deletions(-) diff --git a/dephell/converters/egginfo.py b/dephell/converters/egginfo.py index 1fe3f8e4..2cb72624 100644 --- a/dephell/converters/egginfo.py +++ b/dephell/converters/egginfo.py @@ -2,6 +2,7 @@ from collections import defaultdict from email.parser import Parser from itertools import chain +from logging import getLogger from pathlib import Path from typing import Dict, Optional @@ -9,7 +10,7 @@ from dephell_discover import Root as PackageRoot from dephell_links import parse_link from dephell_markers import Markers -from packaging.requirements import Requirement as PackagingRequirement +from packaging.requirements import Requirement as PackagingRequirement, InvalidRequirement # app from ..constants import DOWNLOAD_FIELD, HOMEPAGE_FIELD @@ -20,6 +21,7 @@ class _Reader: + logger = getLogger('dephell.converters.egginfo') def can_parse(self, path: Path, content: Optional[str] = None) -> bool: if isinstance(path, str): @@ -151,7 +153,15 @@ def parse_info(cls, content: str, root=None, urls: Dict[str, str] = None) -> Roo # dependencies deps = [] for req in cls._get_list(info, 'Requires-Dist'): - req = PackagingRequirement(req) + try: + req = PackagingRequirement(req) + except InvalidRequirement: + cls.logger.warning('invalid requirement', extra=dict( + requirement=req, + package_name=root.name, + package_version=root.version, + )) + continue deps.extend(DependencyMaker.from_requirement( source=root, req=req, From 6ce1541443d2c82b28453b29bb0788122c3fee47 Mon Sep 17 00:00:00 2001 From: Gram Date: Fri, 3 Apr 2020 14:03:58 +0200 Subject: [PATCH 03/80] fix wrong extras dumping --- dephell/models/dependency.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/dephell/models/dependency.py b/dephell/models/dependency.py index bc0b3b7a..94e7bfbc 100644 --- a/dephell/models/dependency.py +++ b/dephell/models/dependency.py @@ -193,7 +193,7 @@ def __str__(self) -> str: marker = Markers(str(self.marker)) if self.envs - {'main'}: - extra_markers = {'extra == "{}"'.format(env) for env in self.envs - {'main'}} + extra_markers = {'extra == {!r}'.format(env) for env in self.envs - {'main'}} marker &= Markers(' or '.join(extra_markers)) if marker: result += '; ' + str(marker) From cc52341e6d159c9fdba02df03b22a77b05758c73 Mon Sep 17 00:00:00 2001 From: Gram Date: Fri, 3 Apr 2020 14:04:10 +0200 Subject: [PATCH 04/80] fix simple warehouse caching --- dephell/repositories/_warehouse/_simple.py | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/dephell/repositories/_warehouse/_simple.py b/dephell/repositories/_warehouse/_simple.py index 51dea3b0..4dcbee08 100644 --- a/dephell/repositories/_warehouse/_simple.py +++ b/dephell/repositories/_warehouse/_simple.py @@ -147,6 +147,7 @@ def _get_links(self, name: str) -> List[Dict[str, str]]: dep_url = posixpath.join(self.url, quote(name)) + '/' with requests_session() as session: + logger.debug('getting dep info from simple repo', extra=dict(url=dep_url)) response = session.get(dep_url, auth=self.auth) if response.status_code == 404: raise PackageNotFoundError(package=name, url=dep_url) @@ -164,12 +165,14 @@ def _get_links(self, name: str) -> List[Dict[str, str]]: python = tag.get('data-requires-python') fragment = parse_qs(parsed.fragment) - yield dict( + link = dict( url=urljoin(dep_url, link), name=parsed.path.strip('/').split('/')[-1], python=html.unescape(python) if python else '*', digest=fragment['sha256'][0] if 'sha256' in fragment else None, ) + links.append(link) + yield link cache.dump(links) return links From 5b7b1af81573dc13a8e8d9426590598ffe5690c3 Mon Sep 17 00:00:00 2001 From: Gram Date: Fri, 3 Apr 2020 14:18:33 +0200 Subject: [PATCH 05/80] fix simple repo cache reading --- dephell/repositories/_warehouse/_simple.py | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/dephell/repositories/_warehouse/_simple.py b/dephell/repositories/_warehouse/_simple.py index 4dcbee08..0ed63af4 100644 --- a/dephell/repositories/_warehouse/_simple.py +++ b/dephell/repositories/_warehouse/_simple.py @@ -143,7 +143,8 @@ def _get_links(self, name: str) -> List[Dict[str, str]]: ) links = cache.load() if links: - return links + yield from links + return dep_url = posixpath.join(self.url, quote(name)) + '/' with requests_session() as session: From 4c59857250fce445303617474c72250b53284876 Mon Sep 17 00:00:00 2001 From: Gram Date: Fri, 3 Apr 2020 14:18:51 +0200 Subject: [PATCH 06/80] fix simple repo files validation for extras --- dephell/repositories/_warehouse/_simple.py | 12 +++++++++++- 1 file changed, 11 insertions(+), 1 deletion(-) diff --git a/dephell/repositories/_warehouse/_simple.py b/dephell/repositories/_warehouse/_simple.py index 0ed63af4..6cd6fad7 100644 --- a/dephell/repositories/_warehouse/_simple.py +++ b/dephell/repositories/_warehouse/_simple.py @@ -53,9 +53,19 @@ def get_releases(self, dep) -> tuple: releases_info = dict() for link in links: name, version = self._parse_name(link['name']) - if canonicalize_name(name) != dep.name: + if canonicalize_name(name) != canonicalize_name(dep.base_name): + logger.warning('bad dist name', extra=dict( + dist_name=link['name'], + package_name=dep.base_name, + reason='package name does not match', + )) continue if not version: + logger.warning('bad dist name', extra=dict( + dist_name=link['name'], + package_name=dep.base_name, + reason='no version specified', + )) continue if version not in releases_info: From b2485b3b59abab21738f25779ddcf91504212e77 Mon Sep 17 00:00:00 2001 From: Gram Date: Fri, 3 Apr 2020 14:37:07 +0200 Subject: [PATCH 07/80] fix simple repo get deps --- dephell/repositories/_warehouse/_simple.py | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/dephell/repositories/_warehouse/_simple.py b/dephell/repositories/_warehouse/_simple.py index 6cd6fad7..5b612927 100644 --- a/dephell/repositories/_warehouse/_simple.py +++ b/dephell/repositories/_warehouse/_simple.py @@ -188,7 +188,7 @@ def _get_links(self, name: str) -> List[Dict[str, str]]: cache.dump(links) return links - async def _get_deps_from_links(self, name, version): + async def _get_deps_from_links(self, name: str, version): from ...converters import SDistConverter, WheelConverter links = self._get_links(name=name) @@ -197,7 +197,7 @@ async def _get_deps_from_links(self, name, version): link_name, link_version = self._parse_name(link['name']) if canonicalize_name(link_name) != name: continue - if link_version != version: + if link_version != str(version): continue good_links.append(link) @@ -211,6 +211,9 @@ async def _get_deps_from_links(self, name, version): (sdist, '.zip'), ) + if name == 'celery': + import pdb; pdb.set_trace() + for converter, ext in rules: for link in good_links: if not link['name'].endswith(ext): From 11868bab02234bdd0f090ce4cbeb6f63d6e484ad Mon Sep 17 00:00:00 2001 From: Gram Date: Fri, 3 Apr 2020 15:44:10 +0200 Subject: [PATCH 08/80] backoff aiohttp for simple repo --- dephell/networking.py | 25 +++++++++++++++++++++- dephell/repositories/_warehouse/_base.py | 3 ++- dephell/repositories/_warehouse/_simple.py | 3 --- 3 files changed, 26 insertions(+), 5 deletions(-) diff --git a/dephell/networking.py b/dephell/networking.py index 9f862be7..64cd0837 100644 --- a/dephell/networking.py +++ b/dephell/networking.py @@ -1,16 +1,20 @@ # built-in +from functools import partial, update_wrapper +from logging import getLogger +from time import sleep from ssl import create_default_context # external import certifi import requests -from aiohttp import ClientSession, TCPConnector +from aiohttp import ClientSession, TCPConnector, ClientPayloadError # app from . import __version__ USER_AGENT = 'DepHell/{version}'.format(version=__version__) +logger = getLogger('dephell.networking') def aiohttp_session(*, auth=None, **kwargs): @@ -36,3 +40,22 @@ def requests_session(*, auth=None, headers=None, **kwargs): if kwargs: session.__dict__.update(kwargs) return session + + +def aiohttp_repeat(func=None, *, count: int = 3): + if func is None: + return partial(func, count=count) + + async def wrapper(*args, **kwargs): + for pause in range(1, count + 1): + try: + return await func(*args, **kwargs) + except ClientPayloadError: + if pause == count: + raise + logger.debug('aiohttp payload error, repeating...', exc_info=True) + sleep(pause) + raise RuntimeError('unreachable') + + wrapper = update_wrapper(wrapper=wrapper, wrapped=func) + return wrapper diff --git a/dephell/repositories/_warehouse/_base.py b/dephell/repositories/_warehouse/_base.py index 97588f42..512a330a 100644 --- a/dephell/repositories/_warehouse/_base.py +++ b/dephell/repositories/_warehouse/_base.py @@ -13,7 +13,7 @@ # app from ...cached_property import cached_property from ...constants import WAREHOUSE_DOMAINS -from ...networking import aiohttp_session +from ...networking import aiohttp_session, aiohttp_repeat from ..base import Interface @@ -136,6 +136,7 @@ async def _download_and_parse(self, *, url: str, converter) -> Tuple[str, ...]: deps.append(str(dep)) return tuple(deps) + @aiohttp_repeat async def _download(self, *, url: str, path: Path) -> None: async with aiohttp_session(auth=self.auth) as session: async with session.get(url) as response: diff --git a/dephell/repositories/_warehouse/_simple.py b/dephell/repositories/_warehouse/_simple.py index 5b612927..b5f4b9d2 100644 --- a/dephell/repositories/_warehouse/_simple.py +++ b/dephell/repositories/_warehouse/_simple.py @@ -211,9 +211,6 @@ async def _get_deps_from_links(self, name: str, version): (sdist, '.zip'), ) - if name == 'celery': - import pdb; pdb.set_trace() - for converter, ext in rules: for link in good_links: if not link['name'].endswith(ext): From 1d724eaf8ba1d0dbc2f9f97d129e7ddcc602df73 Mon Sep 17 00:00:00 2001 From: Gram Date: Fri, 3 Apr 2020 16:06:20 +0200 Subject: [PATCH 09/80] fix cache name --- dephell/cache.py | 2 +- dephell/networking.py | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/dephell/cache.py b/dephell/cache.py index 6fda56e9..2d5f69dd 100644 --- a/dephell/cache.py +++ b/dephell/cache.py @@ -16,7 +16,7 @@ class BaseCache: def __init__(self, *keys, ttl: int = -1): self.path = Path(config['cache']['path'], *keys) if self.ext: - self.path = self.path.with_suffix(self.ext) + self.path = self.path.with_name(self.path.name + self.ext) self.ttl = ttl self._check_ttl() diff --git a/dephell/networking.py b/dephell/networking.py index 64cd0837..5eaa27ae 100644 --- a/dephell/networking.py +++ b/dephell/networking.py @@ -42,7 +42,7 @@ def requests_session(*, auth=None, headers=None, **kwargs): return session -def aiohttp_repeat(func=None, *, count: int = 3): +def aiohttp_repeat(func=None, *, count: int = 4): if func is None: return partial(func, count=count) From f3430f8e7ca2de838347866f8fc45ad0ff4fa568 Mon Sep 17 00:00:00 2001 From: Gram Date: Fri, 3 Apr 2020 17:26:08 +0200 Subject: [PATCH 10/80] catch more general errors --- dephell/networking.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/dephell/networking.py b/dephell/networking.py index 5eaa27ae..9882d302 100644 --- a/dephell/networking.py +++ b/dephell/networking.py @@ -7,7 +7,7 @@ # external import certifi import requests -from aiohttp import ClientSession, TCPConnector, ClientPayloadError +from aiohttp import ClientSession, TCPConnector, ClientError # app from . import __version__ @@ -50,7 +50,7 @@ async def wrapper(*args, **kwargs): for pause in range(1, count + 1): try: return await func(*args, **kwargs) - except ClientPayloadError: + except ClientError: if pause == count: raise logger.debug('aiohttp payload error, repeating...', exc_info=True) From 392fbcf360f1b82b6020c63cafd21792f138ae87 Mon Sep 17 00:00:00 2001 From: Gram Date: Fri, 3 Apr 2020 17:26:26 +0200 Subject: [PATCH 11/80] fix caching for zero-dep pkgs --- dephell/repositories/_warehouse/_simple.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/dephell/repositories/_warehouse/_simple.py b/dephell/repositories/_warehouse/_simple.py index b5f4b9d2..8b656cdb 100644 --- a/dephell/repositories/_warehouse/_simple.py +++ b/dephell/repositories/_warehouse/_simple.py @@ -152,7 +152,7 @@ def _get_links(self, name: str) -> List[Dict[str, str]]: ttl=config['cache']['ttl'], ) links = cache.load() - if links: + if links is not None: yield from links return From d79d56ef7c70911ba3ccdc9176621f2845ec1e7f Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 13 Apr 2020 13:44:48 +0200 Subject: [PATCH 12/80] fix extras detecting for warehouse --- dephell/repositories/_warehouse/_base.py | 15 ++++++++------- 1 file changed, 8 insertions(+), 7 deletions(-) diff --git a/dephell/repositories/_warehouse/_base.py b/dephell/repositories/_warehouse/_base.py index 512a330a..64e3c264 100644 --- a/dephell/repositories/_warehouse/_base.py +++ b/dephell/repositories/_warehouse/_base.py @@ -99,22 +99,23 @@ def _convert_deps(*, deps, name, version, extra): )) try: - dep_extra = req.marker and Markers(req.marker).extra + dep_extras = req.marker and Markers(req.marker).get_strings('extra') except ValueError: # unsupported operation for version marker python_version: in - dep_extra = None + dep_extras = set() # it's not extra and we want not extra too - if dep_extra is None and extra is None: + if not dep_extras and extra is None: result.append(req) continue # it's extra, but we want not the extra # or it's not the extra, but we want extra. - if dep_extra is None or extra is None: + if not dep_extras or extra is None: continue # it's extra and we want this extra - elif dep_extra == extra: - result.append(req) - continue + for dep_extra in dep_extras: + if dep_extra == extra: + result.append(req) + break return tuple(result) From a5b5cbf448f46535608cbff397f0df5df6a1b329 Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 13 Apr 2020 13:54:09 +0200 Subject: [PATCH 13/80] simplify deps tree output --- dephell/commands/deps_tree.py | 12 +++++++++--- 1 file changed, 9 insertions(+), 3 deletions(-) diff --git a/dephell/commands/deps_tree.py b/dephell/commands/deps_tree.py index 2e24ad7a..5beb0982 100644 --- a/dephell/commands/deps_tree.py +++ b/dephell/commands/deps_tree.py @@ -63,12 +63,18 @@ def __call__(self) -> bool: @classmethod def _make_tree(cls, dep, *, level: int = 0) -> List[str]: - lines = ['{level}- {name} [required: {constraint}, locked: {best}, latest: {latest}]'.format( + best = dep.group.best_release.version + latest = dep.group.best_release.version + if best == latest: + template = '{level}- {name} [required: {constraint}, latest: {latest}]' + else: + template = '{level}- {name} [required: {constraint}, locked: {best}, latest: {latest}]' + lines = [template.format( level=' ' * level, name=dep.name, constraint=str(dep.constraint) or '*', - best=str(dep.group.best_release.version), - latest=str(dep.groups.releases[0].version), + best=str(best), + latest=str(latest), )] deps = {dep.name: dep for dep in dep.dependencies}.values() # drop duplicates for subdep in sorted(deps): From 36cb1c9c23272d3da580846e8066368a615ee73f Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 13 Apr 2020 14:01:41 +0200 Subject: [PATCH 14/80] actualize safety test --- tests/test_controllers/test_safety.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/test_controllers/test_safety.py b/tests/test_controllers/test_safety.py index 1464abb0..d7da2a96 100644 --- a/tests/test_controllers/test_safety.py +++ b/tests/test_controllers/test_safety.py @@ -9,5 +9,5 @@ def test_safety(): safety = Safety() vulns = safety.get('django', '1.11.0') - assert len(vulns) == 5 + assert len(vulns) == 13 assert {vuln.name for vuln in vulns} == {'django'} From 97eb5ff9bfd84a0cb54d1273b70c280a779c44e8 Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 13 Apr 2020 14:03:52 +0200 Subject: [PATCH 15/80] register pytest markers --- setup.cfg | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/setup.cfg b/setup.cfg index 9b37ff71..b59285e8 100644 --- a/setup.cfg +++ b/setup.cfg @@ -11,3 +11,8 @@ exclude= .pytest_cache build setup.py + +[tool:pytest] +addopts = --strict-markers +markers = + allow_hosts: allow network requests to specified hostnames. From 216b7fd1021e5b573cb689e2f37bd9b5eb5a5c33 Mon Sep 17 00:00:00 2001 From: orsinium Date: Mon, 13 Apr 2020 14:18:17 +0200 Subject: [PATCH 16/80] sort imports --- dephell/converters/egginfo.py | 2 +- dephell/networking.py | 4 ++-- dephell/repositories/_warehouse/_base.py | 2 +- 3 files changed, 4 insertions(+), 4 deletions(-) diff --git a/dephell/converters/egginfo.py b/dephell/converters/egginfo.py index 2cb72624..cf2bcd08 100644 --- a/dephell/converters/egginfo.py +++ b/dephell/converters/egginfo.py @@ -10,7 +10,7 @@ from dephell_discover import Root as PackageRoot from dephell_links import parse_link from dephell_markers import Markers -from packaging.requirements import Requirement as PackagingRequirement, InvalidRequirement +from packaging.requirements import InvalidRequirement, Requirement as PackagingRequirement # app from ..constants import DOWNLOAD_FIELD, HOMEPAGE_FIELD diff --git a/dephell/networking.py b/dephell/networking.py index 9882d302..cdafbaa7 100644 --- a/dephell/networking.py +++ b/dephell/networking.py @@ -1,13 +1,13 @@ # built-in from functools import partial, update_wrapper from logging import getLogger -from time import sleep from ssl import create_default_context +from time import sleep # external import certifi import requests -from aiohttp import ClientSession, TCPConnector, ClientError +from aiohttp import ClientError, ClientSession, TCPConnector # app from . import __version__ diff --git a/dephell/repositories/_warehouse/_base.py b/dephell/repositories/_warehouse/_base.py index 64e3c264..6520fbdf 100644 --- a/dephell/repositories/_warehouse/_base.py +++ b/dephell/repositories/_warehouse/_base.py @@ -13,7 +13,7 @@ # app from ...cached_property import cached_property from ...constants import WAREHOUSE_DOMAINS -from ...networking import aiohttp_session, aiohttp_repeat +from ...networking import aiohttp_repeat, aiohttp_session from ..base import Interface From 598ead46a1ddee1e4f005df3f0d17bda3caebdb6 Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 13 Apr 2020 14:55:06 +0200 Subject: [PATCH 17/80] fix recommonmark registration for sphinx 3.0.0 --- docs/conf.py | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/docs/conf.py b/docs/conf.py index f1dad500..84782e17 100644 --- a/docs/conf.py +++ b/docs/conf.py @@ -7,7 +7,6 @@ # external import alabaster -from recommonmark.parser import CommonMarkParser from recommonmark.transform import AutoStructify @@ -20,12 +19,10 @@ 'sphinx.ext.coverage', 'sphinx.ext.viewcode', 'sphinx.ext.githubpages', + 'recommonmark', ] templates_path = ['_templates'] -source_parsers = { - '.md': CommonMarkParser, -} source_suffix = ['.rst', '.md'] master_doc = 'index' From 0765ee8cc874200e10da2adc06652ac3eeffcbbb Mon Sep 17 00:00:00 2001 From: Anton Ilyushenkov Date: Wed, 22 Apr 2020 12:00:00 +0300 Subject: [PATCH 18/80] Fix default value for *Converter.lock --- dephell/__main__.py | 1 - dephell/actions/__init__.py | 1 - dephell/actions/_autocomplete.py | 1 - dephell/actions/_contributing.py | 1 - dephell/actions/_converting.py | 1 - dephell/actions/_downloads.py | 1 - dephell/actions/_entrypoints.py | 1 - dephell/actions/_git.py | 1 - dephell/actions/_json.py | 1 - dephell/actions/_python.py | 1 - dephell/actions/_transform.py | 1 - dephell/actions/_travis.py | 1 - dephell/cacher.py | 6 ++---- dephell/cli.py | 1 - dephell/commands/__init__.py | 1 - dephell/commands/base.py | 1 - dephell/commands/discover.py | 1 - dephell/commands/inspect_gadget.py | 1 - dephell/commands/package_changelog.py | 1 - dephell/commands/package_show.py | 3 ++- dephell/commands/package_verify.py | 1 - dephell/commands/project_build.py | 1 - dephell/commands/project_bump.py | 1 - dephell/commands/vendor_import.py | 1 - dephell/config/__init__.py | 1 - dephell/config/app_dirs.py | 1 - dephell/config/builders.py | 4 ++-- dephell/config/defaults.py | 1 - dephell/config/manager.py | 4 ++-- dephell/config/scheme.py | 4 ++-- dephell/controllers/__init__.py | 1 - dephell/controllers/_conflict.py | 1 - dephell/controllers/_dependency.py | 1 - dephell/controllers/_docker.py | 1 - dephell/controllers/_graph.py | 1 - dephell/controllers/_mutator.py | 1 - dephell/controllers/_readme.py | 1 - dephell/controllers/_repos.py | 3 ++- dephell/controllers/_resolver.py | 1 - dephell/controllers/_safety.py | 1 - dephell/controllers/_snyk.py | 1 - dephell/controllers/_uploader.py | 1 - dephell/converters/__init__.py | 1 - dephell/converters/conda.py | 2 ++ dephell/converters/egginfo.py | 7 +++++-- dephell/converters/flit.py | 4 +++- dephell/converters/imports.py | 5 +++-- dephell/converters/installed.py | 4 +++- dephell/converters/pip.py | 6 ++++-- dephell/converters/pipfile.py | 6 ++++-- dephell/converters/pipfilelock.py | 5 +++-- dephell/converters/poetry.py | 5 ++++- dephell/converters/poetrylock.py | 5 ++++- dephell/converters/pyproject.py | 4 +++- dephell/converters/sdist.py | 2 +- dephell/converters/setuppy.py | 5 +++-- dephell/converters/wheel.py | 4 +++- dephell/imports.py | 1 - dephell/logging_helpers.py | 1 - dephell/models/__init__.py | 1 - dephell/models/author.py | 1 - dephell/models/groups.py | 1 - dephell/networking.py | 1 - dephell/package_manager.py | 1 - dephell/pip_cleaner.py | 1 - dephell/repositories/__init__.py | 4 ++-- dephell/repositories/_conda/__init__.py | 1 - dephell/repositories/_conda/_base.py | 1 - dephell/repositories/_conda/_cloud.py | 1 - dephell/repositories/_conda/_git.py | 1 - dephell/repositories/_getter.py | 1 - dephell/repositories/_git/bitbucket.py | 1 - dephell/repositories/_git/git.py | 1 - dephell/repositories/_git/github.py | 1 - dephell/repositories/_git/gitlab.py | 1 - dephell/repositories/_warehouse/__init__.py | 1 - dephell/repositories/_warehouse/_api.py | 1 - dephell/repositories/_warehouse/_base.py | 1 - dephell/repositories/_warehouse/_local.py | 1 - dephell/repositories/_warehouse/_simple.py | 1 - dephell/repositories/base.py | 1 - dephell/yaml.py | 1 - docs/conf.py | 1 - install.py | 5 +++-- setup.py | 1 - tests/conftest.py | 1 - tests/helpers.py | 9 ++++----- tests/requirements/setup.py | 1 - tests/test_actions/test_dotenv.py | 1 - tests/test_actions/test_entrypoints.py | 1 - tests/test_actions/test_json.py | 1 - tests/test_actions/test_transform.py | 1 - tests/test_commands/test_deps_audit.py | 3 +-- tests/test_commands/test_deps_install.py | 3 +-- tests/test_commands/test_deps_licenses.py | 1 - tests/test_commands/test_deps_outdated.py | 3 +-- tests/test_commands/test_deps_tree.py | 1 - tests/test_commands/test_generate_config.py | 1 - tests/test_commands/test_generate_license.py | 1 - tests/test_commands/test_inspect_venv.py | 5 ++--- tests/test_commands/test_jail_install.py | 3 +-- tests/test_commands/test_package_bug.py | 1 - tests/test_commands/test_package_downloads.py | 1 - tests/test_commands/test_package_install.py | 3 +-- tests/test_commands/test_package_search.py | 1 - tests/test_commands/test_package_show.py | 1 - tests/test_commands/test_project_bump.py | 1 - tests/test_commands/test_vendor_import.py | 3 +-- tests/test_commands/test_venv_create.py | 5 ++--- tests/test_commands/test_venv_destroy.py | 5 ++--- tests/test_config.py | 1 - tests/test_controllers/test_safety.py | 1 - tests/test_controllers/test_snyk.py | 1 - tests/test_converters/test_all.py | 2 -- tests/test_converters/test_egginfo.py | 5 ++--- tests/test_converters/test_imports.py | 1 - tests/test_converters/test_pip.py | 5 ++--- tests/test_converters/test_pipfile.py | 3 +-- tests/test_converters/test_pipfilelock.py | 3 +-- tests/test_converters/test_poetry.py | 1 - tests/test_converters/test_poetrylock.py | 1 - tests/test_converters/test_setuppy.py | 5 ++--- tests/test_models/test_author.py | 1 - tests/test_models/test_models_dependency.py | 3 +-- tests/test_models/test_release.py | 5 ++--- tests/test_models/test_requirement.py | 1 - tests/test_repositories/test_conda.py | 1 - tests/test_repositories/test_git_git.py | 4 +--- tests/test_repositories/test_local.py | 1 - tests/test_repositories/test_warehouse_api.py | 2 -- tests/test_repositories/test_warehouse_local.py | 1 - tests/test_repositories/test_warehouse_simple.py | 2 -- tests/test_resolving/test_git_resolving.py | 5 ++--- tests/test_resolving/test_python_compat.py | 3 +-- tests/test_resolving/test_smoke.py | 4 +--- 135 files changed, 94 insertions(+), 185 deletions(-) diff --git a/dephell/__main__.py b/dephell/__main__.py index c27de3a5..88054802 100644 --- a/dephell/__main__.py +++ b/dephell/__main__.py @@ -1,5 +1,4 @@ # app from .cli import entrypoint - entrypoint() diff --git a/dephell/actions/__init__.py b/dephell/actions/__init__.py index 075e62d5..2ebde495 100644 --- a/dephell/actions/__init__.py +++ b/dephell/actions/__init__.py @@ -20,7 +20,6 @@ from ._travis import make_travis from ._venv import get_venv - __all__ = [ 'attach_deps', 'format_size', diff --git a/dephell/actions/_autocomplete.py b/dephell/actions/_autocomplete.py index d930c499..d94c6c0d 100644 --- a/dephell/actions/_autocomplete.py +++ b/dephell/actions/_autocomplete.py @@ -4,7 +4,6 @@ # external from jinja2 import Environment, PackageLoader - templates = Environment( loader=PackageLoader('dephell', 'templates'), ) diff --git a/dephell/actions/_contributing.py b/dephell/actions/_contributing.py index baddb5ba..945b988a 100644 --- a/dephell/actions/_contributing.py +++ b/dephell/actions/_contributing.py @@ -5,7 +5,6 @@ # external from jinja2 import Environment, PackageLoader - env = Environment(loader=PackageLoader('dephell', 'templates')) KNOWN_SECTIONS = ( ('test', 'tests'), diff --git a/dephell/actions/_converting.py b/dephell/actions/_converting.py index 7b51fd22..722b0d16 100644 --- a/dephell/actions/_converting.py +++ b/dephell/actions/_converting.py @@ -6,7 +6,6 @@ from ..config import Config from ..converters import CONVERTERS - logger = getLogger('dephell.actions') diff --git a/dephell/actions/_downloads.py b/dephell/actions/_downloads.py index d21cd14f..af05c36f 100644 --- a/dephell/actions/_downloads.py +++ b/dephell/actions/_downloads.py @@ -10,7 +10,6 @@ # app from ..networking import requests_session - RECENT_URL = 'https://pypistats.org/api/packages/{}/recent' CATEGORIES_URLS = dict( pythons='https://pypistats.org/api/packages/{}/python_minor', diff --git a/dephell/actions/_entrypoints.py b/dephell/actions/_entrypoints.py index ec1bea23..e0fe4d49 100644 --- a/dephell/actions/_entrypoints.py +++ b/dephell/actions/_entrypoints.py @@ -11,7 +11,6 @@ from ..converters import EggInfoConverter from ..models import EntryPoint - logger = getLogger('dephell.actions') diff --git a/dephell/actions/_git.py b/dephell/actions/_git.py index 1f0b6f0a..ac5943da 100644 --- a/dephell/actions/_git.py +++ b/dephell/actions/_git.py @@ -4,7 +4,6 @@ from pathlib import Path from typing import Iterable, Tuple - logger = getLogger('dephell.actions.git') diff --git a/dephell/actions/_json.py b/dephell/actions/_json.py index 65a765f8..c94c610f 100644 --- a/dephell/actions/_json.py +++ b/dephell/actions/_json.py @@ -7,7 +7,6 @@ # app from ..imports import lazy_import - pygments = lazy_import('pygments') pygments_lexers = lazy_import('pygments.lexers') pygments_formatters = lazy_import('pygments.formatters') diff --git a/dephell/actions/_python.py b/dephell/actions/_python.py index 9ba0724a..17379a29 100644 --- a/dephell/actions/_python.py +++ b/dephell/actions/_python.py @@ -11,7 +11,6 @@ from ..converters import CONVERTERS from ._venv import get_venv - # https://docs.python.org/3/library/site.html PTHS = ('easy-install.pth', 'setuptools.pth', None) DIRS = ('site-packages', 'dist-packages') diff --git a/dephell/actions/_transform.py b/dephell/actions/_transform.py index 4e9f127d..b280e7ec 100644 --- a/dephell/actions/_transform.py +++ b/dephell/actions/_transform.py @@ -4,7 +4,6 @@ # app from ..imports import lazy_import - bowler_helpers = lazy_import('bowler.helpers') fissix_pytree = lazy_import('fissix.pytree') fixer_util = lazy_import('fissix.fixer_util') diff --git a/dephell/actions/_travis.py b/dephell/actions/_travis.py index 357ffb58..55a1122d 100644 --- a/dephell/actions/_travis.py +++ b/dephell/actions/_travis.py @@ -1,7 +1,6 @@ # built-in from typing import Any, Dict, Optional - HEADER = """ # Config for Travis CI, tests powered by DepHell. # https://travis-ci.org/ diff --git a/dephell/cacher.py b/dephell/cacher.py index d067424b..936da28f 100644 --- a/dephell/cacher.py +++ b/dephell/cacher.py @@ -10,16 +10,14 @@ import asyncio from itertools import islice -# external -from packaging.requirements import Requirement - # project from dephell.constants import DEFAULT_WAREHOUSE from dephell.controllers import DependencyMaker from dephell.models import RootDependency from dephell.networking import requests_session from dephell.repositories import WarehouseAPIRepo - +# external +from packaging.requirements import Requirement loop = asyncio.get_event_loop() URL = 'https://hugovk.github.io/top-pypi-packages/top-pypi-packages-30-days.min.json' diff --git a/dephell/cli.py b/dephell/cli.py index 84e65416..8bfe8fad 100644 --- a/dephell/cli.py +++ b/dephell/cli.py @@ -12,7 +12,6 @@ from .constants import ReturnCodes from .exceptions import ExtraException - logger = getLogger('dephell.cli') parser = Parser( description='Manage dependencies, projects, virtual environments.', diff --git a/dephell/commands/__init__.py b/dephell/commands/__init__.py index d28591f6..67581d8e 100644 --- a/dephell/commands/__init__.py +++ b/dephell/commands/__init__.py @@ -1,7 +1,6 @@ # app from .discover import COMMANDS - __all__ = ['COMMANDS'] # allow to import commands diff --git a/dephell/commands/base.py b/dephell/commands/base.py index d16afce8..859cda59 100644 --- a/dephell/commands/base.py +++ b/dephell/commands/base.py @@ -18,7 +18,6 @@ from ..controllers import analyze_conflict from ..converters import CONVERTERS, InstalledConverter - REX_WORD = re.compile(r'([a-z\d])([A-Z])') diff --git a/dephell/commands/discover.py b/dephell/commands/discover.py index 78071c20..b647b1c9 100644 --- a/dephell/commands/discover.py +++ b/dephell/commands/discover.py @@ -1,7 +1,6 @@ # built-in from importlib import import_module - # keep sorted _NAMES = ( 'deps add', diff --git a/dephell/commands/inspect_gadget.py b/dephell/commands/inspect_gadget.py index 535ebb5a..0dc06fe5 100644 --- a/dephell/commands/inspect_gadget.py +++ b/dephell/commands/inspect_gadget.py @@ -5,7 +5,6 @@ from ..config import builders from .base import BaseCommand - # Source: https://www.asciiart.eu/cartoons/inspector-gadget # Author: https://en.wikipedia.org/wiki/Joan_Stark GADGET = r""" diff --git a/dephell/commands/package_changelog.py b/dephell/commands/package_changelog.py index f2ca8dea..ad9237bb 100644 --- a/dephell/commands/package_changelog.py +++ b/dephell/commands/package_changelog.py @@ -10,7 +10,6 @@ from ..config import builders from .base import BaseCommand - DEFAULT_WIDTH = int(os.environ.get('COLUMNS', 90)) diff --git a/dephell/commands/package_show.py b/dephell/commands/package_show.py index cf2bb31f..6d08286c 100644 --- a/dephell/commands/package_show.py +++ b/dephell/commands/package_show.py @@ -2,7 +2,8 @@ from argparse import ArgumentParser # app -from ..actions import format_size, get_package, get_path_size, get_python_env, make_json +from ..actions import (format_size, get_package, get_path_size, get_python_env, + make_json) from ..config import builders from ..converters import InstalledConverter from .base import BaseCommand diff --git a/dephell/commands/package_verify.py b/dephell/commands/package_verify.py index 7964765b..910f620f 100644 --- a/dephell/commands/package_verify.py +++ b/dephell/commands/package_verify.py @@ -10,7 +10,6 @@ from ..networking import requests_session from .base import BaseCommand - gnupg = lazy_import('gnupg', package='python-gnupg') DEFAULT_KEYSERVER = 'pgp.mit.edu' diff --git a/dephell/commands/project_build.py b/dephell/commands/project_build.py index 8e94b176..7744b12f 100644 --- a/dephell/commands/project_build.py +++ b/dephell/commands/project_build.py @@ -10,7 +10,6 @@ from ..models import Requirement from .base import BaseCommand - DUMPERS = ( ('setuppy', 'setup.py'), ('egginfo', '.'), diff --git a/dephell/commands/project_bump.py b/dephell/commands/project_bump.py index eca13d7e..28436c92 100644 --- a/dephell/commands/project_bump.py +++ b/dephell/commands/project_bump.py @@ -15,7 +15,6 @@ from ..models import Requirement from .base import BaseCommand - FILE_NAMES = ( # dunder '__init__.py', diff --git a/dephell/commands/vendor_import.py b/dephell/commands/vendor_import.py index 7cf683b2..61ed6e03 100644 --- a/dephell/commands/vendor_import.py +++ b/dephell/commands/vendor_import.py @@ -9,7 +9,6 @@ from ..imports import lazy_import from .base import BaseCommand - bowler = lazy_import('bowler') if TYPE_CHECKING: diff --git a/dephell/config/__init__.py b/dephell/config/__init__.py index cce9f584..44ddc7ea 100644 --- a/dephell/config/__init__.py +++ b/dephell/config/__init__.py @@ -2,7 +2,6 @@ from .app_dirs import get_cache_dir, get_data_dir from .manager import Config - config = Config() diff --git a/dephell/config/app_dirs.py b/dephell/config/app_dirs.py index a22354c5..970419c1 100644 --- a/dephell/config/app_dirs.py +++ b/dephell/config/app_dirs.py @@ -6,7 +6,6 @@ # app from ..imports import lazy_import - appdirs = lazy_import('appdirs') diff --git a/dephell/config/builders.py b/dephell/config/builders.py index 1339eec9..12cc4468 100644 --- a/dephell/config/builders.py +++ b/dephell/config/builders.py @@ -3,8 +3,8 @@ from dephell_versioning import get_schemes # app -from ..constants import FORMATS, LOG_FORMATTERS, LOG_LEVELS, REPOSITORIES, STRATEGIES - +from ..constants import (FORMATS, LOG_FORMATTERS, LOG_LEVELS, REPOSITORIES, + STRATEGIES) env_help = ( 'Pipenv has 2 envs in same file: main and dev. ' diff --git a/dephell/config/defaults.py b/dephell/config/defaults.py index 86dedd92..e195b35d 100644 --- a/dephell/config/defaults.py +++ b/dephell/config/defaults.py @@ -5,7 +5,6 @@ from ..constants import DEFAULT_UPLOAD, DEFAULT_WAREHOUSE from .app_dirs import get_cache_dir, get_data_dir - DEFAULT = dict( tests=['tests'], sdist=dict( diff --git a/dephell/config/manager.py b/dephell/config/manager.py index 9ee1a89f..30e8ca60 100644 --- a/dephell/config/manager.py +++ b/dephell/config/manager.py @@ -16,12 +16,12 @@ from tomlkit.exceptions import TOMLKitError # app -from ..constants import ARCHIVE_EXTENSIONS, ENV_VAR_TEMPLATE, NON_PATH_FORMATS, SUFFIXES +from ..constants import (ARCHIVE_EXTENSIONS, ENV_VAR_TEMPLATE, + NON_PATH_FORMATS, SUFFIXES) from .defaults import DEFAULT from .logging_config import LOGGING from .scheme import SCHEME - ENV_VAR_REX = re.compile(ENV_VAR_TEMPLATE.format('(.+)')) diff --git a/dephell/config/scheme.py b/dephell/config/scheme.py index acfb0946..72056d61 100644 --- a/dephell/config/scheme.py +++ b/dephell/config/scheme.py @@ -3,8 +3,8 @@ from dephell_versioning import get_schemes # app -from ..constants import FORMATS, LOG_FORMATTERS, LOG_LEVELS, REPOSITORIES, STRATEGIES - +from ..constants import (FORMATS, LOG_FORMATTERS, LOG_LEVELS, REPOSITORIES, + STRATEGIES) _TARGET = dict( type='dict', diff --git a/dephell/controllers/__init__.py b/dephell/controllers/__init__.py index 6367fee0..6600c6e0 100644 --- a/dephell/controllers/__init__.py +++ b/dephell/controllers/__init__.py @@ -11,7 +11,6 @@ from ._snyk import Snyk, SnykVulnInfo from ._uploader import Uploader - __all__ = [ 'analyze_conflict', 'DependencyMaker', diff --git a/dephell/controllers/_conflict.py b/dephell/controllers/_conflict.py index b98a149b..91255a42 100644 --- a/dephell/controllers/_conflict.py +++ b/dephell/controllers/_conflict.py @@ -5,7 +5,6 @@ # external from jinja2 import Environment, PackageLoader - logger = getLogger('dephell') env = Environment( loader=PackageLoader('dephell', 'templates'), diff --git a/dephell/controllers/_dependency.py b/dephell/controllers/_dependency.py index be38f97a..2e3c0922 100644 --- a/dephell/controllers/_dependency.py +++ b/dephell/controllers/_dependency.py @@ -17,7 +17,6 @@ from ..models.marker_tracker import MarkerTracker from ..repositories import get_repo - logger = getLogger('dephell.controllers') # regex for names generated by pipenv rex_hash = re.compile(r'[a-f0-9]{7}') diff --git a/dephell/controllers/_docker.py b/dephell/controllers/_docker.py index b36636fa..3214d22c 100644 --- a/dephell/controllers/_docker.py +++ b/dephell/controllers/_docker.py @@ -12,7 +12,6 @@ from ..imports import lazy_import from ..networking import requests_session - docker = lazy_import('docker') dockerpty = lazy_import('dockerpty') diff --git a/dephell/controllers/_graph.py b/dephell/controllers/_graph.py index 322e2cee..faceaf64 100644 --- a/dephell/controllers/_graph.py +++ b/dephell/controllers/_graph.py @@ -8,7 +8,6 @@ from ..models.dependency import Dependency from ..models.root import RootDependency - graphviz = lazy_import('graphviz') graphviz_backend = lazy_import('graphviz.backend') diff --git a/dephell/controllers/_mutator.py b/dephell/controllers/_mutator.py index 221ef0bf..3242e105 100644 --- a/dephell/controllers/_mutator.py +++ b/dephell/controllers/_mutator.py @@ -12,7 +12,6 @@ from ._dependency import DependencyMaker from ._graph import Graph - logger = getLogger('dephell.controllers') diff --git a/dephell/controllers/_readme.py b/dephell/controllers/_readme.py index 18803e2f..259f73eb 100644 --- a/dephell/controllers/_readme.py +++ b/dephell/controllers/_readme.py @@ -12,7 +12,6 @@ from ..cached_property import cached_property from ..constants import EXTENSIONS - CODE = """ import os.path diff --git a/dephell/controllers/_repos.py b/dephell/controllers/_repos.py index b59b078e..d9d0eac4 100644 --- a/dephell/controllers/_repos.py +++ b/dephell/controllers/_repos.py @@ -14,7 +14,8 @@ from ..constants import WAREHOUSE_DOMAINS from ..exceptions import PackageNotFoundError from ..models import Auth -from ..repositories import WarehouseAPIRepo, WarehouseBaseRepo, WarehouseLocalRepo, WarehouseSimpleRepo +from ..repositories import (WarehouseAPIRepo, WarehouseBaseRepo, + WarehouseLocalRepo, WarehouseSimpleRepo) @lru_cache(maxsize=16) diff --git a/dephell/controllers/_resolver.py b/dephell/controllers/_resolver.py index 0bb21240..733011d3 100644 --- a/dephell/controllers/_resolver.py +++ b/dephell/controllers/_resolver.py @@ -12,7 +12,6 @@ from ..models import RootDependency from ._conflict import analyze_conflict - logger = getLogger('dephell.resolver') REX_BASE_VERSION = re.compile(r'[0-9\.]+') diff --git a/dephell/controllers/_safety.py b/dephell/controllers/_safety.py index a3aa6c2d..b63bec84 100644 --- a/dephell/controllers/_safety.py +++ b/dephell/controllers/_safety.py @@ -12,7 +12,6 @@ from ..cached_property import cached_property from ..networking import requests_session - DUMP_URL = 'https://github.com/pyupio/safety-db/raw/master/data/insecure_full.json' REX_LINK = re.compile(r'https?\:\/\/[a-z]+[^\s\"]+') diff --git a/dephell/controllers/_snyk.py b/dephell/controllers/_snyk.py index ecd37b1d..b94e1e40 100644 --- a/dephell/controllers/_snyk.py +++ b/dephell/controllers/_snyk.py @@ -13,7 +13,6 @@ from ..cached_property import cached_property from ..networking import requests_session - RSS_URL = 'https://snyk.io/vuln/feed.xml?type=pip' REX_VERSION = re.compile(VERSION_PATTERN, re.VERBOSE | re.IGNORECASE) REX_TAG = re.compile(r'<\/?[a-z]+.*?>') diff --git a/dephell/controllers/_uploader.py b/dephell/controllers/_uploader.py index f990190f..a407aa89 100644 --- a/dephell/controllers/_uploader.py +++ b/dephell/controllers/_uploader.py @@ -14,7 +14,6 @@ from ..constants import DEFAULT_UPLOAD, TEST_UPLOAD from ..networking import requests_session - BOUNDARY = '--------------GHSKFJDLGDS7543FJKLFHRE75642756743254' diff --git a/dephell/converters/__init__.py b/dephell/converters/__init__.py index 75ff6127..bbb23550 100644 --- a/dephell/converters/__init__.py +++ b/dephell/converters/__init__.py @@ -18,7 +18,6 @@ from .setuppy import SetupPyConverter from .wheel import WheelConverter - __all__ = [ 'CONVERTERS', diff --git a/dephell/converters/conda.py b/dephell/converters/conda.py index ac57d3dd..be62e191 100644 --- a/dephell/converters/conda.py +++ b/dephell/converters/conda.py @@ -3,6 +3,7 @@ from pathlib import Path from typing import Optional +import attr # external from dephell_discover import Root as PackageRoot from dephell_specifier import RangeSpecifier @@ -16,6 +17,7 @@ from .base import BaseConverter +@attr.s() class CondaConverter(BaseConverter): def can_parse(self, path: Path, content: Optional[str] = None) -> bool: if isinstance(path, str): diff --git a/dephell/converters/egginfo.py b/dephell/converters/egginfo.py index cf2bcd08..419d0375 100644 --- a/dephell/converters/egginfo.py +++ b/dephell/converters/egginfo.py @@ -6,11 +6,13 @@ from pathlib import Path from typing import Dict, Optional +import attr # external from dephell_discover import Root as PackageRoot from dephell_links import parse_link from dephell_markers import Markers -from packaging.requirements import InvalidRequirement, Requirement as PackagingRequirement +from packaging.requirements import InvalidRequirement +from packaging.requirements import Requirement as PackagingRequirement # app from ..constants import DOWNLOAD_FIELD, HOMEPAGE_FIELD @@ -401,9 +403,10 @@ def _format_req(req, with_envs: bool) -> str: return line +@attr.s() class EggInfoConverter(_Reader, _Writer, BaseConverter): """ PEP-314, PEP-345, PEP-566 https://packaging.python.org/specifications/core-metadata/ """ - lock = False + lock = attr.ib(type=bool, default=False) diff --git a/dephell/converters/flit.py b/dephell/converters/flit.py index 0df6147e..85083633 100644 --- a/dephell/converters/flit.py +++ b/dephell/converters/flit.py @@ -3,6 +3,7 @@ from pathlib import Path from typing import Optional +import attr # external import tomlkit from dephell_discover import Root as PackageRoot @@ -17,8 +18,9 @@ from .egginfo import EggInfoConverter +@attr.s() class FlitConverter(BaseConverter): - lock = False + lock = attr.ib(type=bool, default=False) def can_parse(self, path: Path, content: Optional[str] = None) -> bool: if not content: diff --git a/dephell/converters/imports.py b/dephell/converters/imports.py index 465565c1..3e555590 100644 --- a/dephell/converters/imports.py +++ b/dephell/converters/imports.py @@ -3,6 +3,7 @@ from pathlib import Path from typing import Dict, List, Set +import attr # external from dephell_discover import Root as PackageRoot @@ -14,7 +15,6 @@ from ..networking import requests_session from .base import BaseConverter - MAPPING_URLS = ( 'https://raw.githubusercontent.com/bndr/pipreqs/master/pipreqs/mapping', 'https://raw.githubusercontent.com/JetBrains/intellij-community/master/python/helpers/tools/packages', @@ -23,8 +23,9 @@ CACHE_TTL = 3600 * 24 * 30 # 30 days +@attr.s() class ImportsConverter(BaseConverter): - lock = True + lock = attr.ib(type=bool, default=True) def can_parse(self, path: Path, content: str = None) -> bool: if isinstance(path, str): diff --git a/dephell/converters/installed.py b/dephell/converters/installed.py index 6c125e78..63fb3155 100644 --- a/dephell/converters/installed.py +++ b/dephell/converters/installed.py @@ -3,6 +3,7 @@ from pathlib import Path from typing import Iterable, Union +import attr # external from dephell_discover import Root as PackageRoot from packaging.utils import canonicalize_name @@ -15,8 +16,9 @@ from .wheel import WheelConverter +@attr.s() class InstalledConverter(BaseConverter): - lock = True + lock = attr.ib(type=bool, default=True) _blacklist = { 'pkg-resources', # https://bugs.launchpad.net/ubuntu/+source/python-pip/+bug/1635463 diff --git a/dephell/converters/pip.py b/dephell/converters/pip.py index d31ca921..1411b1f7 100644 --- a/dephell/converters/pip.py +++ b/dephell/converters/pip.py @@ -4,10 +4,12 @@ from types import SimpleNamespace from typing import Optional +from pip._internal.req import parse_requirements + +import attr # external from dephell_discover import Root as PackageRoot from dephell_links import DirLink, FileLink -from pip._internal.req import parse_requirements # app from ..context_tools import chdir @@ -16,7 +18,6 @@ from ..repositories import WarehouseBaseRepo, WarehouseLocalRepo from .base import BaseConverter - try: # pip<20.0.1 from pip._internal.index import PackageFinder @@ -33,6 +34,7 @@ from pip._internal.network.session import PipSession +@attr.s() class PIPConverter(BaseConverter): sep = ' \\\n ' diff --git a/dephell/converters/pipfile.py b/dephell/converters/pipfile.py index 841b446b..4306ad12 100644 --- a/dephell/converters/pipfile.py +++ b/dephell/converters/pipfile.py @@ -2,6 +2,7 @@ from pathlib import Path from typing import List, Optional +import attr # external import tomlkit from dephell_discover import Root as PackageRoot @@ -15,12 +16,13 @@ from ..repositories import WarehouseBaseRepo, WarehouseLocalRepo, get_repo from .base import BaseConverter - VCS_LIST = ('git', 'svn', 'hg', 'bzr') +@attr.s() class PIPFileConverter(BaseConverter): - lock = False + lock = attr.ib(type=bool, default=False) + fields = ( 'version', 'editable', 'extras', 'markers', 'ref', 'vcs', 'index', 'hashes', diff --git a/dephell/converters/pipfilelock.py b/dephell/converters/pipfilelock.py index 0feef518..1ef7d9c6 100644 --- a/dephell/converters/pipfilelock.py +++ b/dephell/converters/pipfilelock.py @@ -5,6 +5,7 @@ from pathlib import Path from typing import Optional +import attr # external from dephell_discover import Root as PackageRoot from dephell_pythons import Pythons @@ -16,14 +17,14 @@ from ..repositories import WarehouseBaseRepo, WarehouseLocalRepo from .pipfile import PIPFileConverter - # https://stackoverflow.com/a/23820416 # https://github.com/pypa/pipfile/blob/master/examples/Pipfile.lock # https://github.com/pypa/pipfile/blob/master/pipfile/api.py +@attr.s() class PIPFileLockConverter(PIPFileConverter): - lock = True + lock = attr.ib(type=bool, default=True) def can_parse(self, path: Path, content: Optional[str] = None) -> bool: if isinstance(path, str): diff --git a/dephell/converters/poetry.py b/dephell/converters/poetry.py index 7b5d5573..7c276574 100644 --- a/dephell/converters/poetry.py +++ b/dephell/converters/poetry.py @@ -3,6 +3,7 @@ from pathlib import Path from typing import List, Optional +import attr # external import tomlkit from dephell_discover import Root as PackageRoot @@ -16,8 +17,10 @@ from .base import BaseConverter +@attr.s() class PoetryConverter(BaseConverter): - lock = False + lock = attr.ib(type=bool, default=False) + fields = ( 'version', 'python', 'platform', 'allows-prereleases', 'optional', 'extras', 'develop', diff --git a/dephell/converters/poetrylock.py b/dephell/converters/poetrylock.py index fd4d47a3..e94e2f01 100644 --- a/dephell/converters/poetrylock.py +++ b/dephell/converters/poetrylock.py @@ -3,6 +3,7 @@ from pathlib import Path from typing import List, Optional +import attr # external import tomlkit from dephell_discover import Root as PackageRoot @@ -16,8 +17,10 @@ from .base import BaseConverter +@attr.s() class PoetryLockConverter(BaseConverter): - lock = True + lock = attr.ib(type=bool, default=True) + fields = ( 'category', 'description', 'name', 'marker', 'optional', 'python-versions', 'version', 'dependencies', diff --git a/dephell/converters/pyproject.py b/dephell/converters/pyproject.py index a22293c4..5e144751 100644 --- a/dephell/converters/pyproject.py +++ b/dephell/converters/pyproject.py @@ -2,6 +2,7 @@ from pathlib import Path from typing import Optional +import attr # external from dephell_discover import Root as PackageRoot from packaging.requirements import Requirement @@ -13,8 +14,9 @@ from .base import BaseConverter +@attr.s() class PyProjectConverter(BaseConverter): - lock = False + lock = attr.ib(type=bool, default=False) def can_parse(self, path: Path, content: Optional[str] = None) -> bool: if isinstance(path, str): diff --git a/dephell/converters/sdist.py b/dephell/converters/sdist.py index 32deef8c..eaadbe29 100644 --- a/dephell/converters/sdist.py +++ b/dephell/converters/sdist.py @@ -25,7 +25,7 @@ class SDistConverter(BaseConverter): # ratio of tests and project size after which tests will be excluded from sdist ratio = attr.ib(type=Optional[float], default=None) - lock = False + lock = attr.ib(type=bool, default=False) def can_parse(self, path: Path, content: Optional[str] = None) -> bool: if content is not None: diff --git a/dephell/converters/setuppy.py b/dephell/converters/setuppy.py index 945b6466..e6fcfdb0 100644 --- a/dephell/converters/setuppy.py +++ b/dephell/converters/setuppy.py @@ -5,6 +5,7 @@ from pathlib import Path from typing import Optional +import attr # external from dephell_discover import Root as PackageRoot from dephell_links import DirLink, FileLink, URLLink, VCSLink, parse_link @@ -18,7 +19,6 @@ from ..models import Author, EntryPoint, RootDependency from .base import BaseConverter - try: from yapf.yapflib.style import CreateGoogleStyle from yapf.yapflib.yapf_api import FormatCode @@ -54,8 +54,9 @@ """ +@attr.s() class SetupPyConverter(BaseConverter): - lock = False + lock = attr.ib(type=bool, default=False) def can_parse(self, path: Path, content: Optional[str] = None) -> bool: if isinstance(path, str): diff --git a/dephell/converters/wheel.py b/dephell/converters/wheel.py index 01a7965d..8ada2148 100644 --- a/dephell/converters/wheel.py +++ b/dephell/converters/wheel.py @@ -7,6 +7,7 @@ from typing import Optional from zipfile import ZIP_DEFLATED, ZipFile, ZipInfo +import attr # external from dephell_archive import ArchivePath from dephell_discover import Root as PackageRoot @@ -207,9 +208,10 @@ def make_records(self, path: str) -> str: return content + ('\n{},,'.format(path)) +@attr.s() class WheelConverter(_Reader, _Writer, BaseConverter): """ PEP-0427 https://www.python.org/dev/peps/pep-0427/ """ - lock = False + lock = attr.ib(type=bool, default=False) diff --git a/dephell/imports.py b/dephell/imports.py index bce60138..0eff26ca 100644 --- a/dephell/imports.py +++ b/dephell/imports.py @@ -4,7 +4,6 @@ from logging import getLogger from pathlib import Path - logger = getLogger(__name__) diff --git a/dephell/logging_helpers.py b/dephell/logging_helpers.py index d6d08dad..ed824410 100644 --- a/dephell/logging_helpers.py +++ b/dephell/logging_helpers.py @@ -2,7 +2,6 @@ import logging import os - __all__ = ['ColoredFormatter', 'LevelFilter'] diff --git a/dephell/models/__init__.py b/dephell/models/__init__.py index 29f2f30c..483359fc 100644 --- a/dephell/models/__init__.py +++ b/dephell/models/__init__.py @@ -14,7 +14,6 @@ from .root import RootDependency from .simple_dependency import SimpleDependency - __all__ = [ 'Auth', 'Author', diff --git a/dephell/models/author.py b/dephell/models/author.py index ad25bb05..822f5b7a 100644 --- a/dephell/models/author.py +++ b/dephell/models/author.py @@ -5,7 +5,6 @@ # external import attr - REX_AUTHOR = re.compile(r'^\s*(?P.+?) \<(?P.+?)\>\s*$') diff --git a/dephell/models/groups.py b/dephell/models/groups.py index f69182d0..92e12e9a 100644 --- a/dephell/models/groups.py +++ b/dephell/models/groups.py @@ -10,7 +10,6 @@ from ..config import config from .group import Group - loop = asyncio.get_event_loop() diff --git a/dephell/networking.py b/dephell/networking.py index cdafbaa7..9cd2b537 100644 --- a/dephell/networking.py +++ b/dephell/networking.py @@ -12,7 +12,6 @@ # app from . import __version__ - USER_AGENT = 'DepHell/{version}'.format(version=__version__) logger = getLogger('dephell.networking') diff --git a/dephell/package_manager.py b/dephell/package_manager.py index e7dfeba4..5e15f611 100644 --- a/dephell/package_manager.py +++ b/dephell/package_manager.py @@ -14,7 +14,6 @@ from .converters import PIPConverter from .models import Requirement - logger = getLogger('dephell') diff --git a/dephell/pip_cleaner.py b/dephell/pip_cleaner.py index 1a81fa67..505adfdf 100644 --- a/dephell/pip_cleaner.py +++ b/dephell/pip_cleaner.py @@ -1,7 +1,6 @@ # built-in import sys - whitelist = { 'Collecting ', 'Installing collected packages: ', diff --git a/dephell/repositories/__init__.py b/dephell/repositories/__init__.py index 8456692f..96cf0493 100644 --- a/dephell/repositories/__init__.py +++ b/dephell/repositories/__init__.py @@ -4,8 +4,8 @@ from ._git.git import GitRepo from ._local import LocalRepo from ._release import ReleaseRepo -from ._warehouse import WarehouseAPIRepo, WarehouseBaseRepo, WarehouseLocalRepo, WarehouseSimpleRepo - +from ._warehouse import (WarehouseAPIRepo, WarehouseBaseRepo, + WarehouseLocalRepo, WarehouseSimpleRepo) __all__ = [ 'CondaCloudRepo', diff --git a/dephell/repositories/_conda/__init__.py b/dephell/repositories/_conda/__init__.py index e550d9fe..90cf2985 100644 --- a/dephell/repositories/_conda/__init__.py +++ b/dephell/repositories/_conda/__init__.py @@ -3,7 +3,6 @@ from ._composite import CondaRepo from ._git import CondaGitRepo - __all__ = [ 'CondaCloudRepo', 'CondaGitRepo', diff --git a/dephell/repositories/_conda/_base.py b/dephell/repositories/_conda/_base.py index 528ed703..70da0811 100644 --- a/dephell/repositories/_conda/_base.py +++ b/dephell/repositories/_conda/_base.py @@ -8,7 +8,6 @@ # app from ..base import Interface - # idk how this regex works # source: conda/models/match_spec.py REX_VERSION_BUILD = re.compile(r'((?:.+?)[^>~])(?:[ =])([^-=,|<>~]+?))?$') diff --git a/dephell/repositories/_conda/_cloud.py b/dephell/repositories/_conda/_cloud.py index 795057b7..7b8ebc6a 100644 --- a/dephell/repositories/_conda/_cloud.py +++ b/dephell/repositories/_conda/_cloud.py @@ -24,7 +24,6 @@ from ...networking import requests_session from ._base import CondaBaseRepo - # https://conda.anaconda.org/conda-forge/linux-64 # https://conda.anaconda.org/conda-forge/noarch # https://repo.anaconda.com/pkgs/main/linux-64 diff --git a/dephell/repositories/_conda/_git.py b/dephell/repositories/_conda/_git.py index c9b8da93..868f1008 100644 --- a/dephell/repositories/_conda/_git.py +++ b/dephell/repositories/_conda/_git.py @@ -26,7 +26,6 @@ from ...yaml import yaml_load from ._base import CondaBaseRepo - # source: conda-build/metadata.py # Selectors must be either: # - at end of the line diff --git a/dephell/repositories/_getter.py b/dephell/repositories/_getter.py index 13a288a4..2afcfaa1 100644 --- a/dephell/repositories/_getter.py +++ b/dephell/repositories/_getter.py @@ -9,7 +9,6 @@ from ._release import ReleaseRepo from ._warehouse import WarehouseAPIRepo - _repos = dict( conda_cloud=CondaCloudRepo(), conda_git=CondaGitRepo(), diff --git a/dephell/repositories/_git/bitbucket.py b/dephell/repositories/_git/bitbucket.py index 9be27791..4a6347b3 100644 --- a/dephell/repositories/_git/bitbucket.py +++ b/dephell/repositories/_git/bitbucket.py @@ -7,7 +7,6 @@ from ...networking import requests_session from .base import BaseRepo - rex_author = re.compile(r'bitbucket\.com[/:]([a-zA-Z_-])') diff --git a/dephell/repositories/_git/git.py b/dephell/repositories/_git/git.py index 0a6b9820..c97cc40d 100644 --- a/dephell/repositories/_git/git.py +++ b/dephell/repositories/_git/git.py @@ -17,7 +17,6 @@ from .._local import LocalRepo from ..base import Interface - logger = getLogger(__name__) rex_version = re.compile(r'(?:refs/tags/)?v?\.?\s*(.+)') diff --git a/dephell/repositories/_git/github.py b/dephell/repositories/_git/github.py index e7346ab0..34dd2de4 100644 --- a/dephell/repositories/_git/github.py +++ b/dephell/repositories/_git/github.py @@ -6,7 +6,6 @@ from ..cached_property import cached_property from .base import BaseRepo - rex_author = re.compile(r'github\.com[/:]([a-zA-Z_-])') diff --git a/dephell/repositories/_git/gitlab.py b/dephell/repositories/_git/gitlab.py index 5d0e43da..d587711b 100644 --- a/dephell/repositories/_git/gitlab.py +++ b/dephell/repositories/_git/gitlab.py @@ -7,7 +7,6 @@ from ..cached_property import cached_property from .base import BaseRepo - rex_author = re.compile(r'gitlab\.com[/:]([a-zA-Z_-])') diff --git a/dephell/repositories/_warehouse/__init__.py b/dephell/repositories/_warehouse/__init__.py index c79676b6..144643ba 100644 --- a/dephell/repositories/_warehouse/__init__.py +++ b/dephell/repositories/_warehouse/__init__.py @@ -4,7 +4,6 @@ from ._local import WarehouseLocalRepo from ._simple import WarehouseSimpleRepo - __all__ = [ 'WarehouseAPIRepo', 'WarehouseBaseRepo', diff --git a/dephell/repositories/_warehouse/_api.py b/dephell/repositories/_warehouse/_api.py index 5b68d597..5c599985 100644 --- a/dephell/repositories/_warehouse/_api.py +++ b/dephell/repositories/_warehouse/_api.py @@ -21,7 +21,6 @@ from ...networking import aiohttp_session, requests_session from ._base import WarehouseBaseRepo - logger = getLogger('dephell.repositories') _fields = { 'author_email', diff --git a/dephell/repositories/_warehouse/_base.py b/dephell/repositories/_warehouse/_base.py index 6520fbdf..09816727 100644 --- a/dephell/repositories/_warehouse/_base.py +++ b/dephell/repositories/_warehouse/_base.py @@ -16,7 +16,6 @@ from ...networking import aiohttp_repeat, aiohttp_session from ..base import Interface - try: import aiofiles except ImportError: diff --git a/dephell/repositories/_warehouse/_local.py b/dephell/repositories/_warehouse/_local.py index 70dbc7d2..cb7e5f57 100644 --- a/dephell/repositories/_warehouse/_local.py +++ b/dephell/repositories/_warehouse/_local.py @@ -18,7 +18,6 @@ from ...models.release import Release from ._base import WarehouseBaseRepo - logger = getLogger('dephell.repositories.warehouse.simple') REX_WORD = re.compile('[a-zA-Z]+') diff --git a/dephell/repositories/_warehouse/_simple.py b/dephell/repositories/_warehouse/_simple.py index 8b656cdb..78556d78 100644 --- a/dephell/repositories/_warehouse/_simple.py +++ b/dephell/repositories/_warehouse/_simple.py @@ -24,7 +24,6 @@ from ...networking import requests_session from ._base import WarehouseBaseRepo - html5lib = lazy_import('html5lib') logger = getLogger('dephell.repositories.warehouse.simple') diff --git a/dephell/repositories/base.py b/dephell/repositories/base.py index d4be6e47..e8a73109 100644 --- a/dephell/repositories/base.py +++ b/dephell/repositories/base.py @@ -3,7 +3,6 @@ import re from typing import Dict, Iterable, List, Optional - REX_TOKEN = re.compile(r'^((?P[a-z_]+)\:)?(?P.+)$') diff --git a/dephell/yaml.py b/dephell/yaml.py index a0dfa76e..b8c49c3d 100644 --- a/dephell/yaml.py +++ b/dephell/yaml.py @@ -1,7 +1,6 @@ # app from .imports import lazy_import - ruamel_yaml = lazy_import('ruamel.yaml', package='ruamel.yaml') py_yaml = lazy_import('yaml', package='PyYAML') diff --git a/docs/conf.py b/docs/conf.py index 84782e17..85e10130 100644 --- a/docs/conf.py +++ b/docs/conf.py @@ -9,7 +9,6 @@ import alabaster from recommonmark.transform import AutoStructify - sys.path.append(os.path.abspath('../')) extensions = [ 'alabaster', diff --git a/install.py b/install.py index a5afea9e..ef02eacb 100644 --- a/install.py +++ b/install.py @@ -2,12 +2,13 @@ import subprocess import sys from argparse import ArgumentParser -from os import environ, name as os_name, pathsep +from os import environ +from os import name as os_name +from os import pathsep from pathlib import Path from shutil import rmtree from venv import create - POST_MESSAGE = """DepHell is installed now. Great! DepHell was added in your PATH. Please, restart your shell. diff --git a/setup.py b/setup.py index f7904a7b..19ede75d 100644 --- a/setup.py +++ b/setup.py @@ -12,7 +12,6 @@ # built-in import os.path - readme = '' here = os.path.abspath(os.path.dirname(__file__)) readme_path = os.path.join(here, 'README.rst') diff --git a/tests/conftest.py b/tests/conftest.py index 3e38a1e6..f242a8fd 100644 --- a/tests/conftest.py +++ b/tests/conftest.py @@ -7,7 +7,6 @@ import pytest from aioresponses import aioresponses - true_socket = socket.socket true_connect = socket.socket.connect diff --git a/tests/helpers.py b/tests/helpers.py index 4365cf70..fd01a969 100644 --- a/tests/helpers.py +++ b/tests/helpers.py @@ -3,14 +3,13 @@ from datetime import datetime from unittest.mock import patch -# external -from packaging.requirements import Requirement as PackagingRequirement - # project -from dephell.controllers import DependencyMaker, Graph, Mutator, Resolver, analyze_conflict +from dephell.controllers import (DependencyMaker, Graph, Mutator, Resolver, + analyze_conflict) from dephell.models import Release, Requirement, RootDependency from dephell.repositories import ReleaseRepo - +# external +from packaging.requirements import Requirement as PackagingRequirement DEFAULT_TIME = datetime(1970, 1, 1, 0, 0) diff --git a/tests/requirements/setup.py b/tests/requirements/setup.py index 005ee5fb..f0e84b20 100644 --- a/tests/requirements/setup.py +++ b/tests/requirements/setup.py @@ -5,7 +5,6 @@ # external from setuptools import setup - here = path.abspath(path.dirname(__file__)) root = path.dirname(path.dirname(here)) with open(path.join(root, 'README.md'), encoding='utf-8') as f: diff --git a/tests/test_actions/test_dotenv.py b/tests/test_actions/test_dotenv.py index 103599d0..3d8d131c 100644 --- a/tests/test_actions/test_dotenv.py +++ b/tests/test_actions/test_dotenv.py @@ -1,6 +1,5 @@ # external import pytest - # project from dephell.actions import read_dotenv diff --git a/tests/test_actions/test_entrypoints.py b/tests/test_actions/test_entrypoints.py index 0bef4490..1269ce77 100644 --- a/tests/test_actions/test_entrypoints.py +++ b/tests/test_actions/test_entrypoints.py @@ -3,7 +3,6 @@ # external import pytest - # project from dephell.actions._entrypoints import _get_matching_path, get_entrypoints diff --git a/tests/test_actions/test_json.py b/tests/test_actions/test_json.py index 1b163460..f4776619 100644 --- a/tests/test_actions/test_json.py +++ b/tests/test_actions/test_json.py @@ -1,6 +1,5 @@ # external import pytest - # project from dephell.actions._json import _flatdict diff --git a/tests/test_actions/test_transform.py b/tests/test_actions/test_transform.py index 9dcbb778..0c2d262c 100644 --- a/tests/test_actions/test_transform.py +++ b/tests/test_actions/test_transform.py @@ -3,7 +3,6 @@ # external import pytest - # project from dephell.actions import transform_imports from dephell.constants import IS_WINDOWS diff --git a/tests/test_commands/test_deps_audit.py b/tests/test_commands/test_deps_audit.py index 7cfc40ee..9d0d7c11 100644 --- a/tests/test_commands/test_deps_audit.py +++ b/tests/test_commands/test_deps_audit.py @@ -5,11 +5,10 @@ # external import pytest -from dephell_venvs import VEnv - # project from dephell.commands import DepsAuditCommand from dephell.config import Config +from dephell_venvs import VEnv @pytest.mark.allow_hosts() diff --git a/tests/test_commands/test_deps_install.py b/tests/test_commands/test_deps_install.py index fde39a53..eb1e0857 100644 --- a/tests/test_commands/test_deps_install.py +++ b/tests/test_commands/test_deps_install.py @@ -4,11 +4,10 @@ # external import pytest -from dephell_venvs import VEnv - # project from dephell.commands import DepsInstallCommand from dephell.config import Config +from dephell_venvs import VEnv @pytest.mark.allow_hosts() diff --git a/tests/test_commands/test_deps_licenses.py b/tests/test_commands/test_deps_licenses.py index a884d08d..3ac55709 100644 --- a/tests/test_commands/test_deps_licenses.py +++ b/tests/test_commands/test_deps_licenses.py @@ -4,7 +4,6 @@ # external import pytest - # project from dephell.commands import DepsLicensesCommand from dephell.config import Config diff --git a/tests/test_commands/test_deps_outdated.py b/tests/test_commands/test_deps_outdated.py index 2b8f5de5..1a8abf11 100644 --- a/tests/test_commands/test_deps_outdated.py +++ b/tests/test_commands/test_deps_outdated.py @@ -5,11 +5,10 @@ # external import pytest -from dephell_venvs import VEnv - # project from dephell.commands import DepsOutdatedCommand from dephell.config import Config +from dephell_venvs import VEnv @pytest.mark.allow_hosts() diff --git a/tests/test_commands/test_deps_tree.py b/tests/test_commands/test_deps_tree.py index c2039359..2e0d528d 100644 --- a/tests/test_commands/test_deps_tree.py +++ b/tests/test_commands/test_deps_tree.py @@ -4,7 +4,6 @@ # external import pytest - # project from dephell.commands import DepsTreeCommand from dephell.config import Config diff --git a/tests/test_commands/test_generate_config.py b/tests/test_commands/test_generate_config.py index 58449a9d..59231a01 100644 --- a/tests/test_commands/test_generate_config.py +++ b/tests/test_commands/test_generate_config.py @@ -3,7 +3,6 @@ # external import tomlkit - # project from dephell.commands import GenerateConfigCommand diff --git a/tests/test_commands/test_generate_license.py b/tests/test_commands/test_generate_license.py index 732581db..d3e5b752 100644 --- a/tests/test_commands/test_generate_license.py +++ b/tests/test_commands/test_generate_license.py @@ -4,7 +4,6 @@ # external import pytest - # project from dephell.commands import GenerateLicenseCommand from dephell.config import Config diff --git a/tests/test_commands/test_inspect_venv.py b/tests/test_commands/test_inspect_venv.py index 673c453f..e241cf98 100644 --- a/tests/test_commands/test_inspect_venv.py +++ b/tests/test_commands/test_inspect_venv.py @@ -3,12 +3,11 @@ import sys from pathlib import Path -# external -from dephell_venvs import VEnv - # project from dephell.commands import InspectVenvCommand from dephell.config import Config +# external +from dephell_venvs import VEnv def test_inspect_venv_command(temp_path: Path, capsys): diff --git a/tests/test_commands/test_jail_install.py b/tests/test_commands/test_jail_install.py index ddeab295..22af9ece 100644 --- a/tests/test_commands/test_jail_install.py +++ b/tests/test_commands/test_jail_install.py @@ -4,12 +4,11 @@ # external import pytest -from dephell_venvs import VEnv - # project from dephell.commands import JailInstallCommand from dephell.config import Config from dephell.constants import IS_WINDOWS +from dephell_venvs import VEnv @pytest.mark.allow_hosts() diff --git a/tests/test_commands/test_package_bug.py b/tests/test_commands/test_package_bug.py index 34c5d051..a889d941 100644 --- a/tests/test_commands/test_package_bug.py +++ b/tests/test_commands/test_package_bug.py @@ -1,6 +1,5 @@ # external import pytest - # project from dephell.commands import PackageBugCommand diff --git a/tests/test_commands/test_package_downloads.py b/tests/test_commands/test_package_downloads.py index bd26881c..2093236d 100644 --- a/tests/test_commands/test_package_downloads.py +++ b/tests/test_commands/test_package_downloads.py @@ -3,7 +3,6 @@ # external import pytest - # project from dephell.commands import PackageDownloadsCommand from dephell.config import Config diff --git a/tests/test_commands/test_package_install.py b/tests/test_commands/test_package_install.py index 4d2d24dd..9d1a5ab2 100644 --- a/tests/test_commands/test_package_install.py +++ b/tests/test_commands/test_package_install.py @@ -4,11 +4,10 @@ # external import pytest -from dephell_venvs import VEnv - # project from dephell.commands import PackageInstallCommand from dephell.config import Config +from dephell_venvs import VEnv @pytest.mark.allow_hosts() diff --git a/tests/test_commands/test_package_search.py b/tests/test_commands/test_package_search.py index e16ea987..065a449d 100644 --- a/tests/test_commands/test_package_search.py +++ b/tests/test_commands/test_package_search.py @@ -3,7 +3,6 @@ # external import pytest - # project from dephell.commands import PackageSearchCommand from dephell.config import Config diff --git a/tests/test_commands/test_package_show.py b/tests/test_commands/test_package_show.py index 8b2ac9ae..db173e7f 100644 --- a/tests/test_commands/test_package_show.py +++ b/tests/test_commands/test_package_show.py @@ -3,7 +3,6 @@ # external import pytest - # project from dephell.commands import PackageShowCommand from dephell.config import Config diff --git a/tests/test_commands/test_project_bump.py b/tests/test_commands/test_project_bump.py index 85a503ef..195df0ac 100644 --- a/tests/test_commands/test_project_bump.py +++ b/tests/test_commands/test_project_bump.py @@ -5,7 +5,6 @@ # external import pytest import tomlkit - # project from dephell.actions._git import _run from dephell.commands import ProjectBumpCommand diff --git a/tests/test_commands/test_vendor_import.py b/tests/test_commands/test_vendor_import.py index 995a9b93..7b25f964 100644 --- a/tests/test_commands/test_vendor_import.py +++ b/tests/test_commands/test_vendor_import.py @@ -3,14 +3,13 @@ # external import pytest -from dephell_discover import Root as PackageRoot - # project from dephell.commands import VendorImportCommand from dephell.config import Config from dephell.constants import IS_WINDOWS from dephell.controllers import Graph, Mutator, Resolver from dephell.models import RootDependency +from dephell_discover import Root as PackageRoot @pytest.mark.skipif(IS_WINDOWS, reason='unsupported on windows') diff --git a/tests/test_commands/test_venv_create.py b/tests/test_commands/test_venv_create.py index 2380df9f..a16f1cde 100644 --- a/tests/test_commands/test_venv_create.py +++ b/tests/test_commands/test_venv_create.py @@ -1,12 +1,11 @@ # built-in from pathlib import Path -# external -from dephell_venvs import VEnv - # project from dephell.commands import VenvCreateCommand from dephell.config import Config +# external +from dephell_venvs import VEnv def test_venv_create_command(temp_path: Path): diff --git a/tests/test_commands/test_venv_destroy.py b/tests/test_commands/test_venv_destroy.py index 2d05bd35..bf39ba86 100644 --- a/tests/test_commands/test_venv_destroy.py +++ b/tests/test_commands/test_venv_destroy.py @@ -2,12 +2,11 @@ import sys from pathlib import Path -# external -from dephell_venvs import VEnv - # project from dephell.commands import VenvDestroyCommand from dephell.config import Config +# external +from dephell_venvs import VEnv def test_venv_destroy_command(temp_path: Path): diff --git a/tests/test_config.py b/tests/test_config.py index c66dca0f..9623a2c1 100644 --- a/tests/test_config.py +++ b/tests/test_config.py @@ -3,7 +3,6 @@ # external import pytest - # project from dephell.config import Config diff --git a/tests/test_controllers/test_safety.py b/tests/test_controllers/test_safety.py index d7da2a96..0cb6d05c 100644 --- a/tests/test_controllers/test_safety.py +++ b/tests/test_controllers/test_safety.py @@ -1,6 +1,5 @@ # external import pytest - # project from dephell.controllers import Safety diff --git a/tests/test_controllers/test_snyk.py b/tests/test_controllers/test_snyk.py index bef2e481..c4653ed5 100644 --- a/tests/test_controllers/test_snyk.py +++ b/tests/test_controllers/test_snyk.py @@ -1,6 +1,5 @@ # external import pytest - # project from dephell.controllers import Snyk diff --git a/tests/test_converters/test_all.py b/tests/test_converters/test_all.py index 62f2ac30..5271b98e 100644 --- a/tests/test_converters/test_all.py +++ b/tests/test_converters/test_all.py @@ -4,13 +4,11 @@ import attr import pytest - # project from dephell import converters from dephell.controllers import DependencyMaker, Graph, RepositoriesRegistry from dephell.models import Requirement, RootDependency - root_path = Path(__file__).parent.parent / 'requirements' diff --git a/tests/test_converters/test_egginfo.py b/tests/test_converters/test_egginfo.py index 9c6837a1..b30d1244 100644 --- a/tests/test_converters/test_egginfo.py +++ b/tests/test_converters/test_egginfo.py @@ -2,12 +2,11 @@ from email.parser import Parser from pathlib import Path -# external -from dephell_links import VCSLink - # project from dephell.converters import EggInfoConverter from dephell.models import Requirement +# external +from dephell_links import VCSLink def test_load_deps(requirements_path: Path): diff --git a/tests/test_converters/test_imports.py b/tests/test_converters/test_imports.py index 29bfab0b..ac08e888 100644 --- a/tests/test_converters/test_imports.py +++ b/tests/test_converters/test_imports.py @@ -3,7 +3,6 @@ # external import pytest - # project from dephell.converters import ImportsConverter diff --git a/tests/test_converters/test_pip.py b/tests/test_converters/test_pip.py index 2abe82ec..2ec385c2 100644 --- a/tests/test_converters/test_pip.py +++ b/tests/test_converters/test_pip.py @@ -3,14 +3,13 @@ # external import pytest -from dephell_links import VCSLink -from packaging.requirements import Requirement as PackagingRequirement - # project from dephell.controllers import DependencyMaker from dephell.converters.pip import PIPConverter from dephell.models import Requirement, RootDependency from dephell.repositories import GitRepo +from dephell_links import VCSLink +from packaging.requirements import Requirement as PackagingRequirement @pytest.mark.parametrize('lock, given, expected', [ diff --git a/tests/test_converters/test_pipfile.py b/tests/test_converters/test_pipfile.py index 5fdba756..b56a79e8 100644 --- a/tests/test_converters/test_pipfile.py +++ b/tests/test_converters/test_pipfile.py @@ -3,13 +3,12 @@ # external import pytest -from dephell_links import VCSLink - # project from dephell.controllers import DependencyMaker from dephell.converters import PIPFileConverter from dephell.models import Requirement, RootDependency from dephell.repositories import GitRepo +from dephell_links import VCSLink @pytest.mark.allow_hosts() diff --git a/tests/test_converters/test_pipfilelock.py b/tests/test_converters/test_pipfilelock.py index bfd6ca46..962d5e58 100644 --- a/tests/test_converters/test_pipfilelock.py +++ b/tests/test_converters/test_pipfilelock.py @@ -4,12 +4,11 @@ # external import pytest -from dephell_links import VCSLink - # project from dephell.converters import PIPFileLockConverter from dephell.models import Requirement from dephell.repositories import GitRepo +from dephell_links import VCSLink @pytest.mark.allow_hosts() diff --git a/tests/test_converters/test_poetry.py b/tests/test_converters/test_poetry.py index b18fef14..f87c4faf 100644 --- a/tests/test_converters/test_poetry.py +++ b/tests/test_converters/test_poetry.py @@ -5,7 +5,6 @@ # external import pytest import tomlkit - # project from dephell.converters.poetry import PoetryConverter from dephell.models import Requirement diff --git a/tests/test_converters/test_poetrylock.py b/tests/test_converters/test_poetrylock.py index 27267280..c72dea97 100644 --- a/tests/test_converters/test_poetrylock.py +++ b/tests/test_converters/test_poetrylock.py @@ -3,7 +3,6 @@ # external import tomlkit - # project from dephell.converters.poetrylock import PoetryLockConverter from dephell.models import Requirement diff --git a/tests/test_converters/test_setuppy.py b/tests/test_converters/test_setuppy.py index b09a6f90..2b704f86 100644 --- a/tests/test_converters/test_setuppy.py +++ b/tests/test_converters/test_setuppy.py @@ -2,12 +2,11 @@ from pathlib import Path from textwrap import dedent -# external -from dephell_links import VCSLink - # project from dephell.converters.setuppy import SetupPyConverter from dephell.models import Requirement +# external +from dephell_links import VCSLink def test_load_deps(requirements_path: Path): diff --git a/tests/test_models/test_author.py b/tests/test_models/test_author.py index daea6273..a7cc43bd 100644 --- a/tests/test_models/test_author.py +++ b/tests/test_models/test_author.py @@ -1,6 +1,5 @@ # external import pytest - # project from dephell.models.author import Author diff --git a/tests/test_models/test_models_dependency.py b/tests/test_models/test_models_dependency.py index 43dd6965..214bcc22 100644 --- a/tests/test_models/test_models_dependency.py +++ b/tests/test_models/test_models_dependency.py @@ -1,9 +1,8 @@ # external -from packaging.requirements import Requirement - # project from dephell.controllers import DependencyMaker from dephell.models import RootDependency +from packaging.requirements import Requirement def test_from_requirement(): diff --git a/tests/test_models/test_release.py b/tests/test_models/test_release.py index f3143bb0..c5798bbd 100644 --- a/tests/test_models/test_release.py +++ b/tests/test_models/test_release.py @@ -1,11 +1,10 @@ # built-in from datetime import datetime -# external -from dephell_specifier import Specifier - # project from dephell.models.release import Release +# external +from dephell_specifier import Specifier def test_version_compare(): diff --git a/tests/test_models/test_requirement.py b/tests/test_models/test_requirement.py index 03a94ba9..0dd7c238 100644 --- a/tests/test_models/test_requirement.py +++ b/tests/test_models/test_requirement.py @@ -1,6 +1,5 @@ # external import pytest - # project from dephell.converters import PIPConverter from dephell.models import Requirement diff --git a/tests/test_repositories/test_conda.py b/tests/test_repositories/test_conda.py index 2c4fb048..97af30c1 100644 --- a/tests/test_repositories/test_conda.py +++ b/tests/test_repositories/test_conda.py @@ -3,7 +3,6 @@ # external import pytest - # project from dephell.controllers import DependencyMaker from dephell.models import RootDependency diff --git a/tests/test_repositories/test_git_git.py b/tests/test_repositories/test_git_git.py index 94c96e68..a80986f1 100644 --- a/tests/test_repositories/test_git_git.py +++ b/tests/test_repositories/test_git_git.py @@ -5,11 +5,9 @@ # external import pytest -from dephell_links import VCSLink - # project from dephell.repositories import GitRepo - +from dephell_links import VCSLink loop = asyncio.get_event_loop() git_path = Path('.git') diff --git a/tests/test_repositories/test_local.py b/tests/test_repositories/test_local.py index b01ef284..08c14fe7 100644 --- a/tests/test_repositories/test_local.py +++ b/tests/test_repositories/test_local.py @@ -5,7 +5,6 @@ # project from dephell.repositories import LocalRepo - loop = asyncio.get_event_loop() diff --git a/tests/test_repositories/test_warehouse_api.py b/tests/test_repositories/test_warehouse_api.py index ec7f9cb2..c49ac74a 100644 --- a/tests/test_repositories/test_warehouse_api.py +++ b/tests/test_repositories/test_warehouse_api.py @@ -5,14 +5,12 @@ # external import pytest - # project from dephell.constants import DEFAULT_WAREHOUSE from dephell.controllers import DependencyMaker from dephell.models import Auth, RootDependency from dephell.repositories import WarehouseAPIRepo - loop = asyncio.get_event_loop() diff --git a/tests/test_repositories/test_warehouse_local.py b/tests/test_repositories/test_warehouse_local.py index 7b34eff3..43756744 100644 --- a/tests/test_repositories/test_warehouse_local.py +++ b/tests/test_repositories/test_warehouse_local.py @@ -6,7 +6,6 @@ from dephell.models import RootDependency from dephell.repositories import WarehouseLocalRepo - loop = asyncio.get_event_loop() diff --git a/tests/test_repositories/test_warehouse_simple.py b/tests/test_repositories/test_warehouse_simple.py index 5950660a..0599fd38 100644 --- a/tests/test_repositories/test_warehouse_simple.py +++ b/tests/test_repositories/test_warehouse_simple.py @@ -6,14 +6,12 @@ # external import pytest - # project from dephell.constants import DEFAULT_WAREHOUSE from dephell.controllers import DependencyMaker from dephell.models import Auth, RootDependency from dephell.repositories import WarehouseSimpleRepo - loop = asyncio.get_event_loop() diff --git a/tests/test_resolving/test_git_resolving.py b/tests/test_resolving/test_git_resolving.py index df34a04b..383f1ac1 100644 --- a/tests/test_resolving/test_git_resolving.py +++ b/tests/test_resolving/test_git_resolving.py @@ -2,13 +2,12 @@ from collections import OrderedDict from datetime import datetime -# external -from dephell_links import VCSLink - # project from dephell.controllers import DependencyMaker from dephell.models import GitRelease, RootDependency from dephell.repositories import GitRepo +# external +from dephell_links import VCSLink class PatchedGitRepo(GitRepo): diff --git a/tests/test_resolving/test_python_compat.py b/tests/test_resolving/test_python_compat.py index 80ed2852..b2d58aaa 100644 --- a/tests/test_resolving/test_python_compat.py +++ b/tests/test_resolving/test_python_compat.py @@ -1,9 +1,8 @@ # external import pytest -from dephell_specifier import RangeSpecifier - # project from dephell.models import Dependency, Group, MarkerTracker, Release +from dephell_specifier import RangeSpecifier @pytest.mark.parametrize('pdep, prel, ok', [ diff --git a/tests/test_resolving/test_smoke.py b/tests/test_resolving/test_smoke.py index ea4450f4..eeed8f77 100644 --- a/tests/test_resolving/test_smoke.py +++ b/tests/test_resolving/test_smoke.py @@ -3,11 +3,9 @@ # external import pytest -from packaging.version import Version - # project from dephell.converters.pip import PIPConverter - +from packaging.version import Version loader = PIPConverter(lock=False) From ae20dcd19886a36b342dddf0c53f30d879edf814 Mon Sep 17 00:00:00 2001 From: Anton Ilyushenkov Date: Wed, 22 Apr 2020 12:56:12 +0300 Subject: [PATCH 19/80] isort fix --- dephell/__main__.py | 1 + dephell/actions/__init__.py | 1 + dephell/actions/_autocomplete.py | 1 + dephell/actions/_contributing.py | 1 + dephell/actions/_converting.py | 1 + dephell/actions/_downloads.py | 1 + dephell/actions/_entrypoints.py | 1 + dephell/actions/_git.py | 1 + dephell/actions/_json.py | 1 + dephell/actions/_python.py | 1 + dephell/actions/_transform.py | 1 + dephell/actions/_travis.py | 1 + dephell/cacher.py | 6 ++++-- dephell/cli.py | 1 + dephell/commands/__init__.py | 1 + dephell/commands/base.py | 1 + dephell/commands/discover.py | 1 + dephell/commands/inspect_gadget.py | 1 + dephell/commands/package_changelog.py | 1 + dephell/commands/package_show.py | 3 +-- dephell/commands/package_verify.py | 1 + dephell/commands/project_build.py | 1 + dephell/commands/project_bump.py | 1 + dephell/commands/vendor_import.py | 1 + dephell/config/__init__.py | 1 + dephell/config/app_dirs.py | 1 + dephell/config/builders.py | 4 ++-- dephell/config/defaults.py | 1 + dephell/config/manager.py | 4 ++-- dephell/config/scheme.py | 4 ++-- dephell/controllers/__init__.py | 1 + dephell/controllers/_conflict.py | 1 + dephell/controllers/_dependency.py | 1 + dephell/controllers/_docker.py | 1 + dephell/controllers/_graph.py | 1 + dephell/controllers/_mutator.py | 1 + dephell/controllers/_readme.py | 1 + dephell/controllers/_repos.py | 3 +-- dephell/controllers/_resolver.py | 1 + dephell/controllers/_safety.py | 1 + dephell/controllers/_snyk.py | 1 + dephell/controllers/_uploader.py | 1 + dephell/converters/__init__.py | 1 + dephell/converters/conda.py | 2 +- dephell/converters/egginfo.py | 5 ++--- dephell/converters/flit.py | 2 +- dephell/converters/imports.py | 3 ++- dephell/converters/installed.py | 2 +- dephell/converters/pip.py | 6 +++--- dephell/converters/pipfile.py | 3 ++- dephell/converters/pipfilelock.py | 3 ++- dephell/converters/poetry.py | 2 +- dephell/converters/poetrylock.py | 2 +- dephell/converters/pyproject.py | 2 +- dephell/converters/setuppy.py | 3 ++- dephell/converters/wheel.py | 2 +- dephell/imports.py | 1 + dephell/logging_helpers.py | 1 + dephell/models/__init__.py | 1 + dephell/models/author.py | 1 + dephell/models/groups.py | 1 + dephell/networking.py | 1 + dephell/package_manager.py | 1 + dephell/pip_cleaner.py | 1 + dephell/repositories/__init__.py | 4 ++-- dephell/repositories/_conda/__init__.py | 1 + dephell/repositories/_conda/_base.py | 1 + dephell/repositories/_conda/_cloud.py | 1 + dephell/repositories/_conda/_git.py | 1 + dephell/repositories/_getter.py | 1 + dephell/repositories/_git/bitbucket.py | 1 + dephell/repositories/_git/git.py | 1 + dephell/repositories/_git/github.py | 1 + dephell/repositories/_git/gitlab.py | 1 + dephell/repositories/_warehouse/__init__.py | 1 + dephell/repositories/_warehouse/_api.py | 1 + dephell/repositories/_warehouse/_base.py | 1 + dephell/repositories/_warehouse/_local.py | 1 + dephell/repositories/_warehouse/_simple.py | 1 + dephell/repositories/base.py | 1 + dephell/yaml.py | 1 + docs/conf.py | 1 + install.py | 5 ++--- setup.py | 1 + tests/conftest.py | 1 + tests/helpers.py | 9 +++++---- tests/test_actions/test_dotenv.py | 1 + tests/test_actions/test_entrypoints.py | 1 + tests/test_actions/test_json.py | 1 + tests/test_actions/test_transform.py | 1 + tests/test_commands/test_deps_audit.py | 3 ++- tests/test_commands/test_deps_install.py | 3 ++- tests/test_commands/test_deps_licenses.py | 1 + tests/test_commands/test_deps_outdated.py | 3 ++- tests/test_commands/test_deps_tree.py | 1 + tests/test_commands/test_generate_config.py | 1 + tests/test_commands/test_generate_license.py | 1 + tests/test_commands/test_inspect_venv.py | 5 +++-- tests/test_commands/test_jail_install.py | 3 ++- tests/test_commands/test_package_bug.py | 1 + tests/test_commands/test_package_downloads.py | 1 + tests/test_commands/test_package_install.py | 3 ++- tests/test_commands/test_package_search.py | 1 + tests/test_commands/test_package_show.py | 1 + tests/test_commands/test_project_bump.py | 1 + tests/test_commands/test_vendor_import.py | 3 ++- tests/test_commands/test_venv_create.py | 5 +++-- tests/test_commands/test_venv_destroy.py | 5 +++-- tests/test_config.py | 1 + tests/test_controllers/test_safety.py | 1 + tests/test_controllers/test_snyk.py | 1 + tests/test_converters/test_all.py | 2 ++ tests/test_converters/test_egginfo.py | 5 +++-- tests/test_converters/test_imports.py | 1 + tests/test_converters/test_pip.py | 5 +++-- tests/test_converters/test_pipfile.py | 3 ++- tests/test_converters/test_pipfilelock.py | 3 ++- tests/test_converters/test_poetry.py | 1 + tests/test_converters/test_poetrylock.py | 1 + tests/test_converters/test_setuppy.py | 5 +++-- tests/test_models/test_author.py | 1 + tests/test_models/test_models_dependency.py | 3 ++- tests/test_models/test_release.py | 5 +++-- tests/test_models/test_requirement.py | 1 + tests/test_repositories/test_conda.py | 1 + tests/test_repositories/test_git_git.py | 4 +++- tests/test_repositories/test_local.py | 1 + tests/test_repositories/test_warehouse_api.py | 2 ++ tests/test_repositories/test_warehouse_local.py | 1 + tests/test_repositories/test_warehouse_simple.py | 2 ++ tests/test_resolving/test_git_resolving.py | 5 +++-- tests/test_resolving/test_python_compat.py | 3 ++- tests/test_resolving/test_smoke.py | 4 +++- 133 files changed, 185 insertions(+), 66 deletions(-) diff --git a/dephell/__main__.py b/dephell/__main__.py index 88054802..c27de3a5 100644 --- a/dephell/__main__.py +++ b/dephell/__main__.py @@ -1,4 +1,5 @@ # app from .cli import entrypoint + entrypoint() diff --git a/dephell/actions/__init__.py b/dephell/actions/__init__.py index 2ebde495..075e62d5 100644 --- a/dephell/actions/__init__.py +++ b/dephell/actions/__init__.py @@ -20,6 +20,7 @@ from ._travis import make_travis from ._venv import get_venv + __all__ = [ 'attach_deps', 'format_size', diff --git a/dephell/actions/_autocomplete.py b/dephell/actions/_autocomplete.py index d94c6c0d..d930c499 100644 --- a/dephell/actions/_autocomplete.py +++ b/dephell/actions/_autocomplete.py @@ -4,6 +4,7 @@ # external from jinja2 import Environment, PackageLoader + templates = Environment( loader=PackageLoader('dephell', 'templates'), ) diff --git a/dephell/actions/_contributing.py b/dephell/actions/_contributing.py index 945b988a..baddb5ba 100644 --- a/dephell/actions/_contributing.py +++ b/dephell/actions/_contributing.py @@ -5,6 +5,7 @@ # external from jinja2 import Environment, PackageLoader + env = Environment(loader=PackageLoader('dephell', 'templates')) KNOWN_SECTIONS = ( ('test', 'tests'), diff --git a/dephell/actions/_converting.py b/dephell/actions/_converting.py index 722b0d16..7b51fd22 100644 --- a/dephell/actions/_converting.py +++ b/dephell/actions/_converting.py @@ -6,6 +6,7 @@ from ..config import Config from ..converters import CONVERTERS + logger = getLogger('dephell.actions') diff --git a/dephell/actions/_downloads.py b/dephell/actions/_downloads.py index af05c36f..d21cd14f 100644 --- a/dephell/actions/_downloads.py +++ b/dephell/actions/_downloads.py @@ -10,6 +10,7 @@ # app from ..networking import requests_session + RECENT_URL = 'https://pypistats.org/api/packages/{}/recent' CATEGORIES_URLS = dict( pythons='https://pypistats.org/api/packages/{}/python_minor', diff --git a/dephell/actions/_entrypoints.py b/dephell/actions/_entrypoints.py index e0fe4d49..ec1bea23 100644 --- a/dephell/actions/_entrypoints.py +++ b/dephell/actions/_entrypoints.py @@ -11,6 +11,7 @@ from ..converters import EggInfoConverter from ..models import EntryPoint + logger = getLogger('dephell.actions') diff --git a/dephell/actions/_git.py b/dephell/actions/_git.py index ac5943da..1f0b6f0a 100644 --- a/dephell/actions/_git.py +++ b/dephell/actions/_git.py @@ -4,6 +4,7 @@ from pathlib import Path from typing import Iterable, Tuple + logger = getLogger('dephell.actions.git') diff --git a/dephell/actions/_json.py b/dephell/actions/_json.py index c94c610f..65a765f8 100644 --- a/dephell/actions/_json.py +++ b/dephell/actions/_json.py @@ -7,6 +7,7 @@ # app from ..imports import lazy_import + pygments = lazy_import('pygments') pygments_lexers = lazy_import('pygments.lexers') pygments_formatters = lazy_import('pygments.formatters') diff --git a/dephell/actions/_python.py b/dephell/actions/_python.py index 17379a29..9ba0724a 100644 --- a/dephell/actions/_python.py +++ b/dephell/actions/_python.py @@ -11,6 +11,7 @@ from ..converters import CONVERTERS from ._venv import get_venv + # https://docs.python.org/3/library/site.html PTHS = ('easy-install.pth', 'setuptools.pth', None) DIRS = ('site-packages', 'dist-packages') diff --git a/dephell/actions/_transform.py b/dephell/actions/_transform.py index b280e7ec..4e9f127d 100644 --- a/dephell/actions/_transform.py +++ b/dephell/actions/_transform.py @@ -4,6 +4,7 @@ # app from ..imports import lazy_import + bowler_helpers = lazy_import('bowler.helpers') fissix_pytree = lazy_import('fissix.pytree') fixer_util = lazy_import('fissix.fixer_util') diff --git a/dephell/actions/_travis.py b/dephell/actions/_travis.py index 55a1122d..357ffb58 100644 --- a/dephell/actions/_travis.py +++ b/dephell/actions/_travis.py @@ -1,6 +1,7 @@ # built-in from typing import Any, Dict, Optional + HEADER = """ # Config for Travis CI, tests powered by DepHell. # https://travis-ci.org/ diff --git a/dephell/cacher.py b/dephell/cacher.py index 936da28f..d067424b 100644 --- a/dephell/cacher.py +++ b/dephell/cacher.py @@ -10,14 +10,16 @@ import asyncio from itertools import islice +# external +from packaging.requirements import Requirement + # project from dephell.constants import DEFAULT_WAREHOUSE from dephell.controllers import DependencyMaker from dephell.models import RootDependency from dephell.networking import requests_session from dephell.repositories import WarehouseAPIRepo -# external -from packaging.requirements import Requirement + loop = asyncio.get_event_loop() URL = 'https://hugovk.github.io/top-pypi-packages/top-pypi-packages-30-days.min.json' diff --git a/dephell/cli.py b/dephell/cli.py index 8bfe8fad..84e65416 100644 --- a/dephell/cli.py +++ b/dephell/cli.py @@ -12,6 +12,7 @@ from .constants import ReturnCodes from .exceptions import ExtraException + logger = getLogger('dephell.cli') parser = Parser( description='Manage dependencies, projects, virtual environments.', diff --git a/dephell/commands/__init__.py b/dephell/commands/__init__.py index 67581d8e..d28591f6 100644 --- a/dephell/commands/__init__.py +++ b/dephell/commands/__init__.py @@ -1,6 +1,7 @@ # app from .discover import COMMANDS + __all__ = ['COMMANDS'] # allow to import commands diff --git a/dephell/commands/base.py b/dephell/commands/base.py index 859cda59..d16afce8 100644 --- a/dephell/commands/base.py +++ b/dephell/commands/base.py @@ -18,6 +18,7 @@ from ..controllers import analyze_conflict from ..converters import CONVERTERS, InstalledConverter + REX_WORD = re.compile(r'([a-z\d])([A-Z])') diff --git a/dephell/commands/discover.py b/dephell/commands/discover.py index b647b1c9..78071c20 100644 --- a/dephell/commands/discover.py +++ b/dephell/commands/discover.py @@ -1,6 +1,7 @@ # built-in from importlib import import_module + # keep sorted _NAMES = ( 'deps add', diff --git a/dephell/commands/inspect_gadget.py b/dephell/commands/inspect_gadget.py index 0dc06fe5..535ebb5a 100644 --- a/dephell/commands/inspect_gadget.py +++ b/dephell/commands/inspect_gadget.py @@ -5,6 +5,7 @@ from ..config import builders from .base import BaseCommand + # Source: https://www.asciiart.eu/cartoons/inspector-gadget # Author: https://en.wikipedia.org/wiki/Joan_Stark GADGET = r""" diff --git a/dephell/commands/package_changelog.py b/dephell/commands/package_changelog.py index ad9237bb..f2ca8dea 100644 --- a/dephell/commands/package_changelog.py +++ b/dephell/commands/package_changelog.py @@ -10,6 +10,7 @@ from ..config import builders from .base import BaseCommand + DEFAULT_WIDTH = int(os.environ.get('COLUMNS', 90)) diff --git a/dephell/commands/package_show.py b/dephell/commands/package_show.py index 6d08286c..cf2bb31f 100644 --- a/dephell/commands/package_show.py +++ b/dephell/commands/package_show.py @@ -2,8 +2,7 @@ from argparse import ArgumentParser # app -from ..actions import (format_size, get_package, get_path_size, get_python_env, - make_json) +from ..actions import format_size, get_package, get_path_size, get_python_env, make_json from ..config import builders from ..converters import InstalledConverter from .base import BaseCommand diff --git a/dephell/commands/package_verify.py b/dephell/commands/package_verify.py index 910f620f..7964765b 100644 --- a/dephell/commands/package_verify.py +++ b/dephell/commands/package_verify.py @@ -10,6 +10,7 @@ from ..networking import requests_session from .base import BaseCommand + gnupg = lazy_import('gnupg', package='python-gnupg') DEFAULT_KEYSERVER = 'pgp.mit.edu' diff --git a/dephell/commands/project_build.py b/dephell/commands/project_build.py index 7744b12f..8e94b176 100644 --- a/dephell/commands/project_build.py +++ b/dephell/commands/project_build.py @@ -10,6 +10,7 @@ from ..models import Requirement from .base import BaseCommand + DUMPERS = ( ('setuppy', 'setup.py'), ('egginfo', '.'), diff --git a/dephell/commands/project_bump.py b/dephell/commands/project_bump.py index 28436c92..eca13d7e 100644 --- a/dephell/commands/project_bump.py +++ b/dephell/commands/project_bump.py @@ -15,6 +15,7 @@ from ..models import Requirement from .base import BaseCommand + FILE_NAMES = ( # dunder '__init__.py', diff --git a/dephell/commands/vendor_import.py b/dephell/commands/vendor_import.py index 61ed6e03..7cf683b2 100644 --- a/dephell/commands/vendor_import.py +++ b/dephell/commands/vendor_import.py @@ -9,6 +9,7 @@ from ..imports import lazy_import from .base import BaseCommand + bowler = lazy_import('bowler') if TYPE_CHECKING: diff --git a/dephell/config/__init__.py b/dephell/config/__init__.py index 44ddc7ea..cce9f584 100644 --- a/dephell/config/__init__.py +++ b/dephell/config/__init__.py @@ -2,6 +2,7 @@ from .app_dirs import get_cache_dir, get_data_dir from .manager import Config + config = Config() diff --git a/dephell/config/app_dirs.py b/dephell/config/app_dirs.py index 970419c1..a22354c5 100644 --- a/dephell/config/app_dirs.py +++ b/dephell/config/app_dirs.py @@ -6,6 +6,7 @@ # app from ..imports import lazy_import + appdirs = lazy_import('appdirs') diff --git a/dephell/config/builders.py b/dephell/config/builders.py index 12cc4468..1339eec9 100644 --- a/dephell/config/builders.py +++ b/dephell/config/builders.py @@ -3,8 +3,8 @@ from dephell_versioning import get_schemes # app -from ..constants import (FORMATS, LOG_FORMATTERS, LOG_LEVELS, REPOSITORIES, - STRATEGIES) +from ..constants import FORMATS, LOG_FORMATTERS, LOG_LEVELS, REPOSITORIES, STRATEGIES + env_help = ( 'Pipenv has 2 envs in same file: main and dev. ' diff --git a/dephell/config/defaults.py b/dephell/config/defaults.py index e195b35d..86dedd92 100644 --- a/dephell/config/defaults.py +++ b/dephell/config/defaults.py @@ -5,6 +5,7 @@ from ..constants import DEFAULT_UPLOAD, DEFAULT_WAREHOUSE from .app_dirs import get_cache_dir, get_data_dir + DEFAULT = dict( tests=['tests'], sdist=dict( diff --git a/dephell/config/manager.py b/dephell/config/manager.py index 30e8ca60..9ee1a89f 100644 --- a/dephell/config/manager.py +++ b/dephell/config/manager.py @@ -16,12 +16,12 @@ from tomlkit.exceptions import TOMLKitError # app -from ..constants import (ARCHIVE_EXTENSIONS, ENV_VAR_TEMPLATE, - NON_PATH_FORMATS, SUFFIXES) +from ..constants import ARCHIVE_EXTENSIONS, ENV_VAR_TEMPLATE, NON_PATH_FORMATS, SUFFIXES from .defaults import DEFAULT from .logging_config import LOGGING from .scheme import SCHEME + ENV_VAR_REX = re.compile(ENV_VAR_TEMPLATE.format('(.+)')) diff --git a/dephell/config/scheme.py b/dephell/config/scheme.py index 72056d61..acfb0946 100644 --- a/dephell/config/scheme.py +++ b/dephell/config/scheme.py @@ -3,8 +3,8 @@ from dephell_versioning import get_schemes # app -from ..constants import (FORMATS, LOG_FORMATTERS, LOG_LEVELS, REPOSITORIES, - STRATEGIES) +from ..constants import FORMATS, LOG_FORMATTERS, LOG_LEVELS, REPOSITORIES, STRATEGIES + _TARGET = dict( type='dict', diff --git a/dephell/controllers/__init__.py b/dephell/controllers/__init__.py index 6600c6e0..6367fee0 100644 --- a/dephell/controllers/__init__.py +++ b/dephell/controllers/__init__.py @@ -11,6 +11,7 @@ from ._snyk import Snyk, SnykVulnInfo from ._uploader import Uploader + __all__ = [ 'analyze_conflict', 'DependencyMaker', diff --git a/dephell/controllers/_conflict.py b/dephell/controllers/_conflict.py index 91255a42..b98a149b 100644 --- a/dephell/controllers/_conflict.py +++ b/dephell/controllers/_conflict.py @@ -5,6 +5,7 @@ # external from jinja2 import Environment, PackageLoader + logger = getLogger('dephell') env = Environment( loader=PackageLoader('dephell', 'templates'), diff --git a/dephell/controllers/_dependency.py b/dephell/controllers/_dependency.py index 2e3c0922..be38f97a 100644 --- a/dephell/controllers/_dependency.py +++ b/dephell/controllers/_dependency.py @@ -17,6 +17,7 @@ from ..models.marker_tracker import MarkerTracker from ..repositories import get_repo + logger = getLogger('dephell.controllers') # regex for names generated by pipenv rex_hash = re.compile(r'[a-f0-9]{7}') diff --git a/dephell/controllers/_docker.py b/dephell/controllers/_docker.py index 3214d22c..b36636fa 100644 --- a/dephell/controllers/_docker.py +++ b/dephell/controllers/_docker.py @@ -12,6 +12,7 @@ from ..imports import lazy_import from ..networking import requests_session + docker = lazy_import('docker') dockerpty = lazy_import('dockerpty') diff --git a/dephell/controllers/_graph.py b/dephell/controllers/_graph.py index faceaf64..322e2cee 100644 --- a/dephell/controllers/_graph.py +++ b/dephell/controllers/_graph.py @@ -8,6 +8,7 @@ from ..models.dependency import Dependency from ..models.root import RootDependency + graphviz = lazy_import('graphviz') graphviz_backend = lazy_import('graphviz.backend') diff --git a/dephell/controllers/_mutator.py b/dephell/controllers/_mutator.py index 3242e105..221ef0bf 100644 --- a/dephell/controllers/_mutator.py +++ b/dephell/controllers/_mutator.py @@ -12,6 +12,7 @@ from ._dependency import DependencyMaker from ._graph import Graph + logger = getLogger('dephell.controllers') diff --git a/dephell/controllers/_readme.py b/dephell/controllers/_readme.py index 259f73eb..18803e2f 100644 --- a/dephell/controllers/_readme.py +++ b/dephell/controllers/_readme.py @@ -12,6 +12,7 @@ from ..cached_property import cached_property from ..constants import EXTENSIONS + CODE = """ import os.path diff --git a/dephell/controllers/_repos.py b/dephell/controllers/_repos.py index d9d0eac4..b59b078e 100644 --- a/dephell/controllers/_repos.py +++ b/dephell/controllers/_repos.py @@ -14,8 +14,7 @@ from ..constants import WAREHOUSE_DOMAINS from ..exceptions import PackageNotFoundError from ..models import Auth -from ..repositories import (WarehouseAPIRepo, WarehouseBaseRepo, - WarehouseLocalRepo, WarehouseSimpleRepo) +from ..repositories import WarehouseAPIRepo, WarehouseBaseRepo, WarehouseLocalRepo, WarehouseSimpleRepo @lru_cache(maxsize=16) diff --git a/dephell/controllers/_resolver.py b/dephell/controllers/_resolver.py index 733011d3..0bb21240 100644 --- a/dephell/controllers/_resolver.py +++ b/dephell/controllers/_resolver.py @@ -12,6 +12,7 @@ from ..models import RootDependency from ._conflict import analyze_conflict + logger = getLogger('dephell.resolver') REX_BASE_VERSION = re.compile(r'[0-9\.]+') diff --git a/dephell/controllers/_safety.py b/dephell/controllers/_safety.py index b63bec84..a3aa6c2d 100644 --- a/dephell/controllers/_safety.py +++ b/dephell/controllers/_safety.py @@ -12,6 +12,7 @@ from ..cached_property import cached_property from ..networking import requests_session + DUMP_URL = 'https://github.com/pyupio/safety-db/raw/master/data/insecure_full.json' REX_LINK = re.compile(r'https?\:\/\/[a-z]+[^\s\"]+') diff --git a/dephell/controllers/_snyk.py b/dephell/controllers/_snyk.py index b94e1e40..ecd37b1d 100644 --- a/dephell/controllers/_snyk.py +++ b/dephell/controllers/_snyk.py @@ -13,6 +13,7 @@ from ..cached_property import cached_property from ..networking import requests_session + RSS_URL = 'https://snyk.io/vuln/feed.xml?type=pip' REX_VERSION = re.compile(VERSION_PATTERN, re.VERBOSE | re.IGNORECASE) REX_TAG = re.compile(r'<\/?[a-z]+.*?>') diff --git a/dephell/controllers/_uploader.py b/dephell/controllers/_uploader.py index a407aa89..f990190f 100644 --- a/dephell/controllers/_uploader.py +++ b/dephell/controllers/_uploader.py @@ -14,6 +14,7 @@ from ..constants import DEFAULT_UPLOAD, TEST_UPLOAD from ..networking import requests_session + BOUNDARY = '--------------GHSKFJDLGDS7543FJKLFHRE75642756743254' diff --git a/dephell/converters/__init__.py b/dephell/converters/__init__.py index bbb23550..75ff6127 100644 --- a/dephell/converters/__init__.py +++ b/dephell/converters/__init__.py @@ -18,6 +18,7 @@ from .setuppy import SetupPyConverter from .wheel import WheelConverter + __all__ = [ 'CONVERTERS', diff --git a/dephell/converters/conda.py b/dephell/converters/conda.py index be62e191..9df53667 100644 --- a/dephell/converters/conda.py +++ b/dephell/converters/conda.py @@ -3,8 +3,8 @@ from pathlib import Path from typing import Optional -import attr # external +import attr from dephell_discover import Root as PackageRoot from dephell_specifier import RangeSpecifier from packaging.utils import canonicalize_name diff --git a/dephell/converters/egginfo.py b/dephell/converters/egginfo.py index 419d0375..0640e239 100644 --- a/dephell/converters/egginfo.py +++ b/dephell/converters/egginfo.py @@ -6,13 +6,12 @@ from pathlib import Path from typing import Dict, Optional -import attr # external +import attr from dephell_discover import Root as PackageRoot from dephell_links import parse_link from dephell_markers import Markers -from packaging.requirements import InvalidRequirement -from packaging.requirements import Requirement as PackagingRequirement +from packaging.requirements import InvalidRequirement, Requirement as PackagingRequirement # app from ..constants import DOWNLOAD_FIELD, HOMEPAGE_FIELD diff --git a/dephell/converters/flit.py b/dephell/converters/flit.py index 85083633..4302f8fa 100644 --- a/dephell/converters/flit.py +++ b/dephell/converters/flit.py @@ -3,8 +3,8 @@ from pathlib import Path from typing import Optional -import attr # external +import attr import tomlkit from dephell_discover import Root as PackageRoot from dephell_specifier import RangeSpecifier diff --git a/dephell/converters/imports.py b/dephell/converters/imports.py index 3e555590..910576c1 100644 --- a/dephell/converters/imports.py +++ b/dephell/converters/imports.py @@ -3,8 +3,8 @@ from pathlib import Path from typing import Dict, List, Set -import attr # external +import attr from dephell_discover import Root as PackageRoot # app @@ -15,6 +15,7 @@ from ..networking import requests_session from .base import BaseConverter + MAPPING_URLS = ( 'https://raw.githubusercontent.com/bndr/pipreqs/master/pipreqs/mapping', 'https://raw.githubusercontent.com/JetBrains/intellij-community/master/python/helpers/tools/packages', diff --git a/dephell/converters/installed.py b/dephell/converters/installed.py index 63fb3155..67ef4303 100644 --- a/dephell/converters/installed.py +++ b/dephell/converters/installed.py @@ -3,8 +3,8 @@ from pathlib import Path from typing import Iterable, Union -import attr # external +import attr from dephell_discover import Root as PackageRoot from packaging.utils import canonicalize_name diff --git a/dephell/converters/pip.py b/dephell/converters/pip.py index 1411b1f7..a7fd93d2 100644 --- a/dephell/converters/pip.py +++ b/dephell/converters/pip.py @@ -4,12 +4,11 @@ from types import SimpleNamespace from typing import Optional -from pip._internal.req import parse_requirements - -import attr # external +import attr from dephell_discover import Root as PackageRoot from dephell_links import DirLink, FileLink +from pip._internal.req import parse_requirements # app from ..context_tools import chdir @@ -18,6 +17,7 @@ from ..repositories import WarehouseBaseRepo, WarehouseLocalRepo from .base import BaseConverter + try: # pip<20.0.1 from pip._internal.index import PackageFinder diff --git a/dephell/converters/pipfile.py b/dephell/converters/pipfile.py index 4306ad12..8ae6f0cd 100644 --- a/dephell/converters/pipfile.py +++ b/dephell/converters/pipfile.py @@ -2,8 +2,8 @@ from pathlib import Path from typing import List, Optional -import attr # external +import attr import tomlkit from dephell_discover import Root as PackageRoot from dephell_pythons import Pythons @@ -16,6 +16,7 @@ from ..repositories import WarehouseBaseRepo, WarehouseLocalRepo, get_repo from .base import BaseConverter + VCS_LIST = ('git', 'svn', 'hg', 'bzr') diff --git a/dephell/converters/pipfilelock.py b/dephell/converters/pipfilelock.py index 1ef7d9c6..ce0a7254 100644 --- a/dephell/converters/pipfilelock.py +++ b/dephell/converters/pipfilelock.py @@ -5,8 +5,8 @@ from pathlib import Path from typing import Optional -import attr # external +import attr from dephell_discover import Root as PackageRoot from dephell_pythons import Pythons from dephell_specifier import RangeSpecifier @@ -17,6 +17,7 @@ from ..repositories import WarehouseBaseRepo, WarehouseLocalRepo from .pipfile import PIPFileConverter + # https://stackoverflow.com/a/23820416 # https://github.com/pypa/pipfile/blob/master/examples/Pipfile.lock # https://github.com/pypa/pipfile/blob/master/pipfile/api.py diff --git a/dephell/converters/poetry.py b/dephell/converters/poetry.py index 7c276574..c8725686 100644 --- a/dephell/converters/poetry.py +++ b/dephell/converters/poetry.py @@ -3,8 +3,8 @@ from pathlib import Path from typing import List, Optional -import attr # external +import attr import tomlkit from dephell_discover import Root as PackageRoot from dephell_specifier import RangeSpecifier diff --git a/dephell/converters/poetrylock.py b/dephell/converters/poetrylock.py index e94e2f01..2ea66562 100644 --- a/dephell/converters/poetrylock.py +++ b/dephell/converters/poetrylock.py @@ -3,8 +3,8 @@ from pathlib import Path from typing import List, Optional -import attr # external +import attr import tomlkit from dephell_discover import Root as PackageRoot from dephell_links import DirLink diff --git a/dephell/converters/pyproject.py b/dephell/converters/pyproject.py index 5e144751..1e216c3c 100644 --- a/dephell/converters/pyproject.py +++ b/dephell/converters/pyproject.py @@ -2,8 +2,8 @@ from pathlib import Path from typing import Optional -import attr # external +import attr from dephell_discover import Root as PackageRoot from packaging.requirements import Requirement from tomlkit import document, dumps, parse diff --git a/dephell/converters/setuppy.py b/dephell/converters/setuppy.py index e6fcfdb0..8bbbdb3a 100644 --- a/dephell/converters/setuppy.py +++ b/dephell/converters/setuppy.py @@ -5,8 +5,8 @@ from pathlib import Path from typing import Optional -import attr # external +import attr from dephell_discover import Root as PackageRoot from dephell_links import DirLink, FileLink, URLLink, VCSLink, parse_link from dephell_setuptools import read_setup @@ -19,6 +19,7 @@ from ..models import Author, EntryPoint, RootDependency from .base import BaseConverter + try: from yapf.yapflib.style import CreateGoogleStyle from yapf.yapflib.yapf_api import FormatCode diff --git a/dephell/converters/wheel.py b/dephell/converters/wheel.py index 8ada2148..00f7f5d7 100644 --- a/dephell/converters/wheel.py +++ b/dephell/converters/wheel.py @@ -7,8 +7,8 @@ from typing import Optional from zipfile import ZIP_DEFLATED, ZipFile, ZipInfo -import attr # external +import attr from dephell_archive import ArchivePath from dephell_discover import Root as PackageRoot diff --git a/dephell/imports.py b/dephell/imports.py index 0eff26ca..bce60138 100644 --- a/dephell/imports.py +++ b/dephell/imports.py @@ -4,6 +4,7 @@ from logging import getLogger from pathlib import Path + logger = getLogger(__name__) diff --git a/dephell/logging_helpers.py b/dephell/logging_helpers.py index ed824410..d6d08dad 100644 --- a/dephell/logging_helpers.py +++ b/dephell/logging_helpers.py @@ -2,6 +2,7 @@ import logging import os + __all__ = ['ColoredFormatter', 'LevelFilter'] diff --git a/dephell/models/__init__.py b/dephell/models/__init__.py index 483359fc..29f2f30c 100644 --- a/dephell/models/__init__.py +++ b/dephell/models/__init__.py @@ -14,6 +14,7 @@ from .root import RootDependency from .simple_dependency import SimpleDependency + __all__ = [ 'Auth', 'Author', diff --git a/dephell/models/author.py b/dephell/models/author.py index 822f5b7a..ad25bb05 100644 --- a/dephell/models/author.py +++ b/dephell/models/author.py @@ -5,6 +5,7 @@ # external import attr + REX_AUTHOR = re.compile(r'^\s*(?P.+?) \<(?P.+?)\>\s*$') diff --git a/dephell/models/groups.py b/dephell/models/groups.py index 92e12e9a..f69182d0 100644 --- a/dephell/models/groups.py +++ b/dephell/models/groups.py @@ -10,6 +10,7 @@ from ..config import config from .group import Group + loop = asyncio.get_event_loop() diff --git a/dephell/networking.py b/dephell/networking.py index 9cd2b537..cdafbaa7 100644 --- a/dephell/networking.py +++ b/dephell/networking.py @@ -12,6 +12,7 @@ # app from . import __version__ + USER_AGENT = 'DepHell/{version}'.format(version=__version__) logger = getLogger('dephell.networking') diff --git a/dephell/package_manager.py b/dephell/package_manager.py index 5e15f611..e7dfeba4 100644 --- a/dephell/package_manager.py +++ b/dephell/package_manager.py @@ -14,6 +14,7 @@ from .converters import PIPConverter from .models import Requirement + logger = getLogger('dephell') diff --git a/dephell/pip_cleaner.py b/dephell/pip_cleaner.py index 505adfdf..1a81fa67 100644 --- a/dephell/pip_cleaner.py +++ b/dephell/pip_cleaner.py @@ -1,6 +1,7 @@ # built-in import sys + whitelist = { 'Collecting ', 'Installing collected packages: ', diff --git a/dephell/repositories/__init__.py b/dephell/repositories/__init__.py index 96cf0493..8456692f 100644 --- a/dephell/repositories/__init__.py +++ b/dephell/repositories/__init__.py @@ -4,8 +4,8 @@ from ._git.git import GitRepo from ._local import LocalRepo from ._release import ReleaseRepo -from ._warehouse import (WarehouseAPIRepo, WarehouseBaseRepo, - WarehouseLocalRepo, WarehouseSimpleRepo) +from ._warehouse import WarehouseAPIRepo, WarehouseBaseRepo, WarehouseLocalRepo, WarehouseSimpleRepo + __all__ = [ 'CondaCloudRepo', diff --git a/dephell/repositories/_conda/__init__.py b/dephell/repositories/_conda/__init__.py index 90cf2985..e550d9fe 100644 --- a/dephell/repositories/_conda/__init__.py +++ b/dephell/repositories/_conda/__init__.py @@ -3,6 +3,7 @@ from ._composite import CondaRepo from ._git import CondaGitRepo + __all__ = [ 'CondaCloudRepo', 'CondaGitRepo', diff --git a/dephell/repositories/_conda/_base.py b/dephell/repositories/_conda/_base.py index 70da0811..528ed703 100644 --- a/dephell/repositories/_conda/_base.py +++ b/dephell/repositories/_conda/_base.py @@ -8,6 +8,7 @@ # app from ..base import Interface + # idk how this regex works # source: conda/models/match_spec.py REX_VERSION_BUILD = re.compile(r'((?:.+?)[^>~])(?:[ =])([^-=,|<>~]+?))?$') diff --git a/dephell/repositories/_conda/_cloud.py b/dephell/repositories/_conda/_cloud.py index 7b8ebc6a..795057b7 100644 --- a/dephell/repositories/_conda/_cloud.py +++ b/dephell/repositories/_conda/_cloud.py @@ -24,6 +24,7 @@ from ...networking import requests_session from ._base import CondaBaseRepo + # https://conda.anaconda.org/conda-forge/linux-64 # https://conda.anaconda.org/conda-forge/noarch # https://repo.anaconda.com/pkgs/main/linux-64 diff --git a/dephell/repositories/_conda/_git.py b/dephell/repositories/_conda/_git.py index 868f1008..c9b8da93 100644 --- a/dephell/repositories/_conda/_git.py +++ b/dephell/repositories/_conda/_git.py @@ -26,6 +26,7 @@ from ...yaml import yaml_load from ._base import CondaBaseRepo + # source: conda-build/metadata.py # Selectors must be either: # - at end of the line diff --git a/dephell/repositories/_getter.py b/dephell/repositories/_getter.py index 2afcfaa1..13a288a4 100644 --- a/dephell/repositories/_getter.py +++ b/dephell/repositories/_getter.py @@ -9,6 +9,7 @@ from ._release import ReleaseRepo from ._warehouse import WarehouseAPIRepo + _repos = dict( conda_cloud=CondaCloudRepo(), conda_git=CondaGitRepo(), diff --git a/dephell/repositories/_git/bitbucket.py b/dephell/repositories/_git/bitbucket.py index 4a6347b3..9be27791 100644 --- a/dephell/repositories/_git/bitbucket.py +++ b/dephell/repositories/_git/bitbucket.py @@ -7,6 +7,7 @@ from ...networking import requests_session from .base import BaseRepo + rex_author = re.compile(r'bitbucket\.com[/:]([a-zA-Z_-])') diff --git a/dephell/repositories/_git/git.py b/dephell/repositories/_git/git.py index c97cc40d..0a6b9820 100644 --- a/dephell/repositories/_git/git.py +++ b/dephell/repositories/_git/git.py @@ -17,6 +17,7 @@ from .._local import LocalRepo from ..base import Interface + logger = getLogger(__name__) rex_version = re.compile(r'(?:refs/tags/)?v?\.?\s*(.+)') diff --git a/dephell/repositories/_git/github.py b/dephell/repositories/_git/github.py index 34dd2de4..e7346ab0 100644 --- a/dephell/repositories/_git/github.py +++ b/dephell/repositories/_git/github.py @@ -6,6 +6,7 @@ from ..cached_property import cached_property from .base import BaseRepo + rex_author = re.compile(r'github\.com[/:]([a-zA-Z_-])') diff --git a/dephell/repositories/_git/gitlab.py b/dephell/repositories/_git/gitlab.py index d587711b..5d0e43da 100644 --- a/dephell/repositories/_git/gitlab.py +++ b/dephell/repositories/_git/gitlab.py @@ -7,6 +7,7 @@ from ..cached_property import cached_property from .base import BaseRepo + rex_author = re.compile(r'gitlab\.com[/:]([a-zA-Z_-])') diff --git a/dephell/repositories/_warehouse/__init__.py b/dephell/repositories/_warehouse/__init__.py index 144643ba..c79676b6 100644 --- a/dephell/repositories/_warehouse/__init__.py +++ b/dephell/repositories/_warehouse/__init__.py @@ -4,6 +4,7 @@ from ._local import WarehouseLocalRepo from ._simple import WarehouseSimpleRepo + __all__ = [ 'WarehouseAPIRepo', 'WarehouseBaseRepo', diff --git a/dephell/repositories/_warehouse/_api.py b/dephell/repositories/_warehouse/_api.py index 5c599985..5b68d597 100644 --- a/dephell/repositories/_warehouse/_api.py +++ b/dephell/repositories/_warehouse/_api.py @@ -21,6 +21,7 @@ from ...networking import aiohttp_session, requests_session from ._base import WarehouseBaseRepo + logger = getLogger('dephell.repositories') _fields = { 'author_email', diff --git a/dephell/repositories/_warehouse/_base.py b/dephell/repositories/_warehouse/_base.py index 09816727..6520fbdf 100644 --- a/dephell/repositories/_warehouse/_base.py +++ b/dephell/repositories/_warehouse/_base.py @@ -16,6 +16,7 @@ from ...networking import aiohttp_repeat, aiohttp_session from ..base import Interface + try: import aiofiles except ImportError: diff --git a/dephell/repositories/_warehouse/_local.py b/dephell/repositories/_warehouse/_local.py index cb7e5f57..70dbc7d2 100644 --- a/dephell/repositories/_warehouse/_local.py +++ b/dephell/repositories/_warehouse/_local.py @@ -18,6 +18,7 @@ from ...models.release import Release from ._base import WarehouseBaseRepo + logger = getLogger('dephell.repositories.warehouse.simple') REX_WORD = re.compile('[a-zA-Z]+') diff --git a/dephell/repositories/_warehouse/_simple.py b/dephell/repositories/_warehouse/_simple.py index 78556d78..8b656cdb 100644 --- a/dephell/repositories/_warehouse/_simple.py +++ b/dephell/repositories/_warehouse/_simple.py @@ -24,6 +24,7 @@ from ...networking import requests_session from ._base import WarehouseBaseRepo + html5lib = lazy_import('html5lib') logger = getLogger('dephell.repositories.warehouse.simple') diff --git a/dephell/repositories/base.py b/dephell/repositories/base.py index e8a73109..d4be6e47 100644 --- a/dephell/repositories/base.py +++ b/dephell/repositories/base.py @@ -3,6 +3,7 @@ import re from typing import Dict, Iterable, List, Optional + REX_TOKEN = re.compile(r'^((?P[a-z_]+)\:)?(?P.+)$') diff --git a/dephell/yaml.py b/dephell/yaml.py index b8c49c3d..a0dfa76e 100644 --- a/dephell/yaml.py +++ b/dephell/yaml.py @@ -1,6 +1,7 @@ # app from .imports import lazy_import + ruamel_yaml = lazy_import('ruamel.yaml', package='ruamel.yaml') py_yaml = lazy_import('yaml', package='PyYAML') diff --git a/docs/conf.py b/docs/conf.py index 85e10130..84782e17 100644 --- a/docs/conf.py +++ b/docs/conf.py @@ -9,6 +9,7 @@ import alabaster from recommonmark.transform import AutoStructify + sys.path.append(os.path.abspath('../')) extensions = [ 'alabaster', diff --git a/install.py b/install.py index ef02eacb..a5afea9e 100644 --- a/install.py +++ b/install.py @@ -2,13 +2,12 @@ import subprocess import sys from argparse import ArgumentParser -from os import environ -from os import name as os_name -from os import pathsep +from os import environ, name as os_name, pathsep from pathlib import Path from shutil import rmtree from venv import create + POST_MESSAGE = """DepHell is installed now. Great! DepHell was added in your PATH. Please, restart your shell. diff --git a/setup.py b/setup.py index 19ede75d..f7904a7b 100644 --- a/setup.py +++ b/setup.py @@ -12,6 +12,7 @@ # built-in import os.path + readme = '' here = os.path.abspath(os.path.dirname(__file__)) readme_path = os.path.join(here, 'README.rst') diff --git a/tests/conftest.py b/tests/conftest.py index f242a8fd..3e38a1e6 100644 --- a/tests/conftest.py +++ b/tests/conftest.py @@ -7,6 +7,7 @@ import pytest from aioresponses import aioresponses + true_socket = socket.socket true_connect = socket.socket.connect diff --git a/tests/helpers.py b/tests/helpers.py index fd01a969..4365cf70 100644 --- a/tests/helpers.py +++ b/tests/helpers.py @@ -3,13 +3,14 @@ from datetime import datetime from unittest.mock import patch +# external +from packaging.requirements import Requirement as PackagingRequirement + # project -from dephell.controllers import (DependencyMaker, Graph, Mutator, Resolver, - analyze_conflict) +from dephell.controllers import DependencyMaker, Graph, Mutator, Resolver, analyze_conflict from dephell.models import Release, Requirement, RootDependency from dephell.repositories import ReleaseRepo -# external -from packaging.requirements import Requirement as PackagingRequirement + DEFAULT_TIME = datetime(1970, 1, 1, 0, 0) diff --git a/tests/test_actions/test_dotenv.py b/tests/test_actions/test_dotenv.py index 3d8d131c..103599d0 100644 --- a/tests/test_actions/test_dotenv.py +++ b/tests/test_actions/test_dotenv.py @@ -1,5 +1,6 @@ # external import pytest + # project from dephell.actions import read_dotenv diff --git a/tests/test_actions/test_entrypoints.py b/tests/test_actions/test_entrypoints.py index 1269ce77..0bef4490 100644 --- a/tests/test_actions/test_entrypoints.py +++ b/tests/test_actions/test_entrypoints.py @@ -3,6 +3,7 @@ # external import pytest + # project from dephell.actions._entrypoints import _get_matching_path, get_entrypoints diff --git a/tests/test_actions/test_json.py b/tests/test_actions/test_json.py index f4776619..1b163460 100644 --- a/tests/test_actions/test_json.py +++ b/tests/test_actions/test_json.py @@ -1,5 +1,6 @@ # external import pytest + # project from dephell.actions._json import _flatdict diff --git a/tests/test_actions/test_transform.py b/tests/test_actions/test_transform.py index 0c2d262c..9dcbb778 100644 --- a/tests/test_actions/test_transform.py +++ b/tests/test_actions/test_transform.py @@ -3,6 +3,7 @@ # external import pytest + # project from dephell.actions import transform_imports from dephell.constants import IS_WINDOWS diff --git a/tests/test_commands/test_deps_audit.py b/tests/test_commands/test_deps_audit.py index 9d0d7c11..7cfc40ee 100644 --- a/tests/test_commands/test_deps_audit.py +++ b/tests/test_commands/test_deps_audit.py @@ -5,10 +5,11 @@ # external import pytest +from dephell_venvs import VEnv + # project from dephell.commands import DepsAuditCommand from dephell.config import Config -from dephell_venvs import VEnv @pytest.mark.allow_hosts() diff --git a/tests/test_commands/test_deps_install.py b/tests/test_commands/test_deps_install.py index eb1e0857..fde39a53 100644 --- a/tests/test_commands/test_deps_install.py +++ b/tests/test_commands/test_deps_install.py @@ -4,10 +4,11 @@ # external import pytest +from dephell_venvs import VEnv + # project from dephell.commands import DepsInstallCommand from dephell.config import Config -from dephell_venvs import VEnv @pytest.mark.allow_hosts() diff --git a/tests/test_commands/test_deps_licenses.py b/tests/test_commands/test_deps_licenses.py index 3ac55709..a884d08d 100644 --- a/tests/test_commands/test_deps_licenses.py +++ b/tests/test_commands/test_deps_licenses.py @@ -4,6 +4,7 @@ # external import pytest + # project from dephell.commands import DepsLicensesCommand from dephell.config import Config diff --git a/tests/test_commands/test_deps_outdated.py b/tests/test_commands/test_deps_outdated.py index 1a8abf11..2b8f5de5 100644 --- a/tests/test_commands/test_deps_outdated.py +++ b/tests/test_commands/test_deps_outdated.py @@ -5,10 +5,11 @@ # external import pytest +from dephell_venvs import VEnv + # project from dephell.commands import DepsOutdatedCommand from dephell.config import Config -from dephell_venvs import VEnv @pytest.mark.allow_hosts() diff --git a/tests/test_commands/test_deps_tree.py b/tests/test_commands/test_deps_tree.py index 2e0d528d..c2039359 100644 --- a/tests/test_commands/test_deps_tree.py +++ b/tests/test_commands/test_deps_tree.py @@ -4,6 +4,7 @@ # external import pytest + # project from dephell.commands import DepsTreeCommand from dephell.config import Config diff --git a/tests/test_commands/test_generate_config.py b/tests/test_commands/test_generate_config.py index 59231a01..58449a9d 100644 --- a/tests/test_commands/test_generate_config.py +++ b/tests/test_commands/test_generate_config.py @@ -3,6 +3,7 @@ # external import tomlkit + # project from dephell.commands import GenerateConfigCommand diff --git a/tests/test_commands/test_generate_license.py b/tests/test_commands/test_generate_license.py index d3e5b752..732581db 100644 --- a/tests/test_commands/test_generate_license.py +++ b/tests/test_commands/test_generate_license.py @@ -4,6 +4,7 @@ # external import pytest + # project from dephell.commands import GenerateLicenseCommand from dephell.config import Config diff --git a/tests/test_commands/test_inspect_venv.py b/tests/test_commands/test_inspect_venv.py index e241cf98..673c453f 100644 --- a/tests/test_commands/test_inspect_venv.py +++ b/tests/test_commands/test_inspect_venv.py @@ -3,11 +3,12 @@ import sys from pathlib import Path +# external +from dephell_venvs import VEnv + # project from dephell.commands import InspectVenvCommand from dephell.config import Config -# external -from dephell_venvs import VEnv def test_inspect_venv_command(temp_path: Path, capsys): diff --git a/tests/test_commands/test_jail_install.py b/tests/test_commands/test_jail_install.py index 22af9ece..ddeab295 100644 --- a/tests/test_commands/test_jail_install.py +++ b/tests/test_commands/test_jail_install.py @@ -4,11 +4,12 @@ # external import pytest +from dephell_venvs import VEnv + # project from dephell.commands import JailInstallCommand from dephell.config import Config from dephell.constants import IS_WINDOWS -from dephell_venvs import VEnv @pytest.mark.allow_hosts() diff --git a/tests/test_commands/test_package_bug.py b/tests/test_commands/test_package_bug.py index a889d941..34c5d051 100644 --- a/tests/test_commands/test_package_bug.py +++ b/tests/test_commands/test_package_bug.py @@ -1,5 +1,6 @@ # external import pytest + # project from dephell.commands import PackageBugCommand diff --git a/tests/test_commands/test_package_downloads.py b/tests/test_commands/test_package_downloads.py index 2093236d..bd26881c 100644 --- a/tests/test_commands/test_package_downloads.py +++ b/tests/test_commands/test_package_downloads.py @@ -3,6 +3,7 @@ # external import pytest + # project from dephell.commands import PackageDownloadsCommand from dephell.config import Config diff --git a/tests/test_commands/test_package_install.py b/tests/test_commands/test_package_install.py index 9d1a5ab2..4d2d24dd 100644 --- a/tests/test_commands/test_package_install.py +++ b/tests/test_commands/test_package_install.py @@ -4,10 +4,11 @@ # external import pytest +from dephell_venvs import VEnv + # project from dephell.commands import PackageInstallCommand from dephell.config import Config -from dephell_venvs import VEnv @pytest.mark.allow_hosts() diff --git a/tests/test_commands/test_package_search.py b/tests/test_commands/test_package_search.py index 065a449d..e16ea987 100644 --- a/tests/test_commands/test_package_search.py +++ b/tests/test_commands/test_package_search.py @@ -3,6 +3,7 @@ # external import pytest + # project from dephell.commands import PackageSearchCommand from dephell.config import Config diff --git a/tests/test_commands/test_package_show.py b/tests/test_commands/test_package_show.py index db173e7f..8b2ac9ae 100644 --- a/tests/test_commands/test_package_show.py +++ b/tests/test_commands/test_package_show.py @@ -3,6 +3,7 @@ # external import pytest + # project from dephell.commands import PackageShowCommand from dephell.config import Config diff --git a/tests/test_commands/test_project_bump.py b/tests/test_commands/test_project_bump.py index 195df0ac..85a503ef 100644 --- a/tests/test_commands/test_project_bump.py +++ b/tests/test_commands/test_project_bump.py @@ -5,6 +5,7 @@ # external import pytest import tomlkit + # project from dephell.actions._git import _run from dephell.commands import ProjectBumpCommand diff --git a/tests/test_commands/test_vendor_import.py b/tests/test_commands/test_vendor_import.py index 7b25f964..995a9b93 100644 --- a/tests/test_commands/test_vendor_import.py +++ b/tests/test_commands/test_vendor_import.py @@ -3,13 +3,14 @@ # external import pytest +from dephell_discover import Root as PackageRoot + # project from dephell.commands import VendorImportCommand from dephell.config import Config from dephell.constants import IS_WINDOWS from dephell.controllers import Graph, Mutator, Resolver from dephell.models import RootDependency -from dephell_discover import Root as PackageRoot @pytest.mark.skipif(IS_WINDOWS, reason='unsupported on windows') diff --git a/tests/test_commands/test_venv_create.py b/tests/test_commands/test_venv_create.py index a16f1cde..2380df9f 100644 --- a/tests/test_commands/test_venv_create.py +++ b/tests/test_commands/test_venv_create.py @@ -1,11 +1,12 @@ # built-in from pathlib import Path +# external +from dephell_venvs import VEnv + # project from dephell.commands import VenvCreateCommand from dephell.config import Config -# external -from dephell_venvs import VEnv def test_venv_create_command(temp_path: Path): diff --git a/tests/test_commands/test_venv_destroy.py b/tests/test_commands/test_venv_destroy.py index bf39ba86..2d05bd35 100644 --- a/tests/test_commands/test_venv_destroy.py +++ b/tests/test_commands/test_venv_destroy.py @@ -2,11 +2,12 @@ import sys from pathlib import Path +# external +from dephell_venvs import VEnv + # project from dephell.commands import VenvDestroyCommand from dephell.config import Config -# external -from dephell_venvs import VEnv def test_venv_destroy_command(temp_path: Path): diff --git a/tests/test_config.py b/tests/test_config.py index 9623a2c1..c66dca0f 100644 --- a/tests/test_config.py +++ b/tests/test_config.py @@ -3,6 +3,7 @@ # external import pytest + # project from dephell.config import Config diff --git a/tests/test_controllers/test_safety.py b/tests/test_controllers/test_safety.py index 0cb6d05c..d7da2a96 100644 --- a/tests/test_controllers/test_safety.py +++ b/tests/test_controllers/test_safety.py @@ -1,5 +1,6 @@ # external import pytest + # project from dephell.controllers import Safety diff --git a/tests/test_controllers/test_snyk.py b/tests/test_controllers/test_snyk.py index c4653ed5..bef2e481 100644 --- a/tests/test_controllers/test_snyk.py +++ b/tests/test_controllers/test_snyk.py @@ -1,5 +1,6 @@ # external import pytest + # project from dephell.controllers import Snyk diff --git a/tests/test_converters/test_all.py b/tests/test_converters/test_all.py index 5271b98e..62f2ac30 100644 --- a/tests/test_converters/test_all.py +++ b/tests/test_converters/test_all.py @@ -4,11 +4,13 @@ import attr import pytest + # project from dephell import converters from dephell.controllers import DependencyMaker, Graph, RepositoriesRegistry from dephell.models import Requirement, RootDependency + root_path = Path(__file__).parent.parent / 'requirements' diff --git a/tests/test_converters/test_egginfo.py b/tests/test_converters/test_egginfo.py index b30d1244..9c6837a1 100644 --- a/tests/test_converters/test_egginfo.py +++ b/tests/test_converters/test_egginfo.py @@ -2,11 +2,12 @@ from email.parser import Parser from pathlib import Path +# external +from dephell_links import VCSLink + # project from dephell.converters import EggInfoConverter from dephell.models import Requirement -# external -from dephell_links import VCSLink def test_load_deps(requirements_path: Path): diff --git a/tests/test_converters/test_imports.py b/tests/test_converters/test_imports.py index ac08e888..29bfab0b 100644 --- a/tests/test_converters/test_imports.py +++ b/tests/test_converters/test_imports.py @@ -3,6 +3,7 @@ # external import pytest + # project from dephell.converters import ImportsConverter diff --git a/tests/test_converters/test_pip.py b/tests/test_converters/test_pip.py index 2ec385c2..2abe82ec 100644 --- a/tests/test_converters/test_pip.py +++ b/tests/test_converters/test_pip.py @@ -3,13 +3,14 @@ # external import pytest +from dephell_links import VCSLink +from packaging.requirements import Requirement as PackagingRequirement + # project from dephell.controllers import DependencyMaker from dephell.converters.pip import PIPConverter from dephell.models import Requirement, RootDependency from dephell.repositories import GitRepo -from dephell_links import VCSLink -from packaging.requirements import Requirement as PackagingRequirement @pytest.mark.parametrize('lock, given, expected', [ diff --git a/tests/test_converters/test_pipfile.py b/tests/test_converters/test_pipfile.py index b56a79e8..5fdba756 100644 --- a/tests/test_converters/test_pipfile.py +++ b/tests/test_converters/test_pipfile.py @@ -3,12 +3,13 @@ # external import pytest +from dephell_links import VCSLink + # project from dephell.controllers import DependencyMaker from dephell.converters import PIPFileConverter from dephell.models import Requirement, RootDependency from dephell.repositories import GitRepo -from dephell_links import VCSLink @pytest.mark.allow_hosts() diff --git a/tests/test_converters/test_pipfilelock.py b/tests/test_converters/test_pipfilelock.py index 962d5e58..bfd6ca46 100644 --- a/tests/test_converters/test_pipfilelock.py +++ b/tests/test_converters/test_pipfilelock.py @@ -4,11 +4,12 @@ # external import pytest +from dephell_links import VCSLink + # project from dephell.converters import PIPFileLockConverter from dephell.models import Requirement from dephell.repositories import GitRepo -from dephell_links import VCSLink @pytest.mark.allow_hosts() diff --git a/tests/test_converters/test_poetry.py b/tests/test_converters/test_poetry.py index f87c4faf..b18fef14 100644 --- a/tests/test_converters/test_poetry.py +++ b/tests/test_converters/test_poetry.py @@ -5,6 +5,7 @@ # external import pytest import tomlkit + # project from dephell.converters.poetry import PoetryConverter from dephell.models import Requirement diff --git a/tests/test_converters/test_poetrylock.py b/tests/test_converters/test_poetrylock.py index c72dea97..27267280 100644 --- a/tests/test_converters/test_poetrylock.py +++ b/tests/test_converters/test_poetrylock.py @@ -3,6 +3,7 @@ # external import tomlkit + # project from dephell.converters.poetrylock import PoetryLockConverter from dephell.models import Requirement diff --git a/tests/test_converters/test_setuppy.py b/tests/test_converters/test_setuppy.py index 2b704f86..b09a6f90 100644 --- a/tests/test_converters/test_setuppy.py +++ b/tests/test_converters/test_setuppy.py @@ -2,11 +2,12 @@ from pathlib import Path from textwrap import dedent +# external +from dephell_links import VCSLink + # project from dephell.converters.setuppy import SetupPyConverter from dephell.models import Requirement -# external -from dephell_links import VCSLink def test_load_deps(requirements_path: Path): diff --git a/tests/test_models/test_author.py b/tests/test_models/test_author.py index a7cc43bd..daea6273 100644 --- a/tests/test_models/test_author.py +++ b/tests/test_models/test_author.py @@ -1,5 +1,6 @@ # external import pytest + # project from dephell.models.author import Author diff --git a/tests/test_models/test_models_dependency.py b/tests/test_models/test_models_dependency.py index 214bcc22..43dd6965 100644 --- a/tests/test_models/test_models_dependency.py +++ b/tests/test_models/test_models_dependency.py @@ -1,8 +1,9 @@ # external +from packaging.requirements import Requirement + # project from dephell.controllers import DependencyMaker from dephell.models import RootDependency -from packaging.requirements import Requirement def test_from_requirement(): diff --git a/tests/test_models/test_release.py b/tests/test_models/test_release.py index c5798bbd..f3143bb0 100644 --- a/tests/test_models/test_release.py +++ b/tests/test_models/test_release.py @@ -1,11 +1,12 @@ # built-in from datetime import datetime -# project -from dephell.models.release import Release # external from dephell_specifier import Specifier +# project +from dephell.models.release import Release + def test_version_compare(): assert '3' in Specifier('>2') diff --git a/tests/test_models/test_requirement.py b/tests/test_models/test_requirement.py index 0dd7c238..03a94ba9 100644 --- a/tests/test_models/test_requirement.py +++ b/tests/test_models/test_requirement.py @@ -1,5 +1,6 @@ # external import pytest + # project from dephell.converters import PIPConverter from dephell.models import Requirement diff --git a/tests/test_repositories/test_conda.py b/tests/test_repositories/test_conda.py index 97af30c1..2c4fb048 100644 --- a/tests/test_repositories/test_conda.py +++ b/tests/test_repositories/test_conda.py @@ -3,6 +3,7 @@ # external import pytest + # project from dephell.controllers import DependencyMaker from dephell.models import RootDependency diff --git a/tests/test_repositories/test_git_git.py b/tests/test_repositories/test_git_git.py index a80986f1..94c96e68 100644 --- a/tests/test_repositories/test_git_git.py +++ b/tests/test_repositories/test_git_git.py @@ -5,9 +5,11 @@ # external import pytest +from dephell_links import VCSLink + # project from dephell.repositories import GitRepo -from dephell_links import VCSLink + loop = asyncio.get_event_loop() git_path = Path('.git') diff --git a/tests/test_repositories/test_local.py b/tests/test_repositories/test_local.py index 08c14fe7..b01ef284 100644 --- a/tests/test_repositories/test_local.py +++ b/tests/test_repositories/test_local.py @@ -5,6 +5,7 @@ # project from dephell.repositories import LocalRepo + loop = asyncio.get_event_loop() diff --git a/tests/test_repositories/test_warehouse_api.py b/tests/test_repositories/test_warehouse_api.py index c49ac74a..ec7f9cb2 100644 --- a/tests/test_repositories/test_warehouse_api.py +++ b/tests/test_repositories/test_warehouse_api.py @@ -5,12 +5,14 @@ # external import pytest + # project from dephell.constants import DEFAULT_WAREHOUSE from dephell.controllers import DependencyMaker from dephell.models import Auth, RootDependency from dephell.repositories import WarehouseAPIRepo + loop = asyncio.get_event_loop() diff --git a/tests/test_repositories/test_warehouse_local.py b/tests/test_repositories/test_warehouse_local.py index 43756744..7b34eff3 100644 --- a/tests/test_repositories/test_warehouse_local.py +++ b/tests/test_repositories/test_warehouse_local.py @@ -6,6 +6,7 @@ from dephell.models import RootDependency from dephell.repositories import WarehouseLocalRepo + loop = asyncio.get_event_loop() diff --git a/tests/test_repositories/test_warehouse_simple.py b/tests/test_repositories/test_warehouse_simple.py index 0599fd38..5950660a 100644 --- a/tests/test_repositories/test_warehouse_simple.py +++ b/tests/test_repositories/test_warehouse_simple.py @@ -6,12 +6,14 @@ # external import pytest + # project from dephell.constants import DEFAULT_WAREHOUSE from dephell.controllers import DependencyMaker from dephell.models import Auth, RootDependency from dephell.repositories import WarehouseSimpleRepo + loop = asyncio.get_event_loop() diff --git a/tests/test_resolving/test_git_resolving.py b/tests/test_resolving/test_git_resolving.py index 383f1ac1..df34a04b 100644 --- a/tests/test_resolving/test_git_resolving.py +++ b/tests/test_resolving/test_git_resolving.py @@ -2,12 +2,13 @@ from collections import OrderedDict from datetime import datetime +# external +from dephell_links import VCSLink + # project from dephell.controllers import DependencyMaker from dephell.models import GitRelease, RootDependency from dephell.repositories import GitRepo -# external -from dephell_links import VCSLink class PatchedGitRepo(GitRepo): diff --git a/tests/test_resolving/test_python_compat.py b/tests/test_resolving/test_python_compat.py index b2d58aaa..80ed2852 100644 --- a/tests/test_resolving/test_python_compat.py +++ b/tests/test_resolving/test_python_compat.py @@ -1,8 +1,9 @@ # external import pytest +from dephell_specifier import RangeSpecifier + # project from dephell.models import Dependency, Group, MarkerTracker, Release -from dephell_specifier import RangeSpecifier @pytest.mark.parametrize('pdep, prel, ok', [ diff --git a/tests/test_resolving/test_smoke.py b/tests/test_resolving/test_smoke.py index eeed8f77..ea4450f4 100644 --- a/tests/test_resolving/test_smoke.py +++ b/tests/test_resolving/test_smoke.py @@ -3,9 +3,11 @@ # external import pytest +from packaging.version import Version + # project from dephell.converters.pip import PIPConverter -from packaging.version import Version + loader = PIPConverter(lock=False) From a13febaa84665efce9500b6282f13c17f2a4c603 Mon Sep 17 00:00:00 2001 From: Anton Ilyushenkov Date: Wed, 22 Apr 2020 13:07:01 +0300 Subject: [PATCH 20/80] force CI From 7cc66f30ab2627f2bea40a5b59659ece4c34c4be Mon Sep 17 00:00:00 2001 From: Gram Date: Wed, 22 Apr 2020 13:00:01 +0200 Subject: [PATCH 21/80] fix path resolving 4 register --- dephell/commands/project_register.py | 1 + 1 file changed, 1 insertion(+) diff --git a/dephell/commands/project_register.py b/dephell/commands/project_register.py index 4ef2cf88..823e41c9 100644 --- a/dephell/commands/project_register.py +++ b/dephell/commands/project_register.py @@ -69,6 +69,7 @@ def __call__(self) -> bool: return True def _register(self, project_path: Path, lib_path: Path = None) -> bool: + project_path = project_path.resolve() self._make_egg_info( project_path=project_path, from_format=self.config['from']['format'], From 36181b9a561a0174b2278367cae232b6995570c8 Mon Sep 17 00:00:00 2001 From: Oliver Hofkens Date: Fri, 24 Apr 2020 10:02:45 +0200 Subject: [PATCH 22/80] Add failing test on warehouses --- tests/test_repositories/test_warehouse_api.py | 6 ++++-- tests/test_repositories/test_warehouse_simple.py | 6 ++++-- 2 files changed, 8 insertions(+), 4 deletions(-) diff --git a/tests/test_repositories/test_warehouse_api.py b/tests/test_repositories/test_warehouse_api.py index ec7f9cb2..a1e02ea6 100644 --- a/tests/test_repositories/test_warehouse_api.py +++ b/tests/test_repositories/test_warehouse_api.py @@ -5,6 +5,7 @@ # external import pytest +from packaging.version import Version # project from dephell.constants import DEFAULT_WAREHOUSE @@ -110,8 +111,9 @@ def test_get_deps_auth(asyncio_mock, temp_cache, fixtures_path: Path): assert client._default_headers['authorization'] == 'Basic Z3JhbTp0ZXN0' +@pytest.mark.parametrize("version", ["0.1.2", Version("0.1.2")]) def test_download(asyncio_mock, temp_cache, fixtures_path: Path, temp_path: Path, - requirements_path: Path): + requirements_path: Path, version): pypi_url = 'https://custom.pypi.org/pypi/' json_response = (fixtures_path / 'warehouse-api-release.json').read_text() json_content = json.loads(json_response) @@ -123,7 +125,7 @@ def test_download(asyncio_mock, temp_cache, fixtures_path: Path, temp_path: Path asyncio_mock.get(file_url, body=file_content) repo = WarehouseAPIRepo(name='pypi', url=pypi_url) - coroutine = repo.download(name='dephell-shells', version='0.1.2', path=temp_path) + coroutine = repo.download(name='dephell-shells', version=version, path=temp_path) result = loop.run_until_complete(asyncio.gather(coroutine))[0] assert result is True assert (temp_path / file_name).exists() diff --git a/tests/test_repositories/test_warehouse_simple.py b/tests/test_repositories/test_warehouse_simple.py index 5950660a..1b8b7c2f 100644 --- a/tests/test_repositories/test_warehouse_simple.py +++ b/tests/test_repositories/test_warehouse_simple.py @@ -6,6 +6,7 @@ # external import pytest +from packaging.version import Version # project from dephell.constants import DEFAULT_WAREHOUSE @@ -128,8 +129,9 @@ def test_get_deps_auth(requests_mock, temp_cache, fixtures_path): assert requests_mock.last_request.headers['Authorization'] == 'Basic Z3JhbTp0ZXN0' +@pytest.mark.parametrize("version", ["0.1.2", Version("0.1.2")]) def test_download(requests_mock, asyncio_mock, temp_cache, fixtures_path: Path, - temp_path: Path, requirements_path: Path): + temp_path: Path, requirements_path: Path, version): pypi_url = 'https://custom.pypi.org/pypi/' text_response = (fixtures_path / 'warehouse-simple.html').read_text() file_url = re.findall( @@ -143,7 +145,7 @@ def test_download(requests_mock, asyncio_mock, temp_cache, fixtures_path: Path, asyncio_mock.get(file_url, body=file_content) repo = WarehouseSimpleRepo(name='pypi', url=pypi_url) - coroutine = repo.download(name='dephell-shells', version='0.1.2', path=temp_path) + coroutine = repo.download(name='dephell-shells', version=version, path=temp_path) result = loop.run_until_complete(asyncio.gather(coroutine))[0] assert result is True assert (temp_path / file_name).exists() From 532047ca2807694be5c3c1b92f483b2aa468f9ee Mon Sep 17 00:00:00 2001 From: Oliver Hofkens Date: Fri, 24 Apr 2020 10:12:29 +0200 Subject: [PATCH 23/80] Fix #425: Convert version object to str in download() --- dephell/repositories/_warehouse/_simple.py | 3 +++ 1 file changed, 3 insertions(+) diff --git a/dephell/repositories/_warehouse/_simple.py b/dephell/repositories/_warehouse/_simple.py index 8b656cdb..b85ec4c8 100644 --- a/dephell/repositories/_warehouse/_simple.py +++ b/dephell/repositories/_warehouse/_simple.py @@ -122,6 +122,9 @@ def search(self, query: Iterable[str]) -> List[Dict[str, str]]: raise NotImplementedError async def download(self, name: str, version: str, path: Path) -> bool: + if not isinstance(version, str): + version = str(version) + links = self._get_links(name=name) good_links = [] for link in links: From 249ae444415629f5cc300bed18df50e5a804dd4d Mon Sep 17 00:00:00 2001 From: Oliver Hofkens Date: Fri, 24 Apr 2020 10:15:43 +0200 Subject: [PATCH 24/80] Replace double quotes with single quotes --- tests/test_repositories/test_warehouse_api.py | 2 +- tests/test_repositories/test_warehouse_simple.py | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/tests/test_repositories/test_warehouse_api.py b/tests/test_repositories/test_warehouse_api.py index a1e02ea6..844a6357 100644 --- a/tests/test_repositories/test_warehouse_api.py +++ b/tests/test_repositories/test_warehouse_api.py @@ -111,7 +111,7 @@ def test_get_deps_auth(asyncio_mock, temp_cache, fixtures_path: Path): assert client._default_headers['authorization'] == 'Basic Z3JhbTp0ZXN0' -@pytest.mark.parametrize("version", ["0.1.2", Version("0.1.2")]) +@pytest.mark.parametrize('version', ['0.1.2', Version('0.1.2')]) def test_download(asyncio_mock, temp_cache, fixtures_path: Path, temp_path: Path, requirements_path: Path, version): pypi_url = 'https://custom.pypi.org/pypi/' diff --git a/tests/test_repositories/test_warehouse_simple.py b/tests/test_repositories/test_warehouse_simple.py index 1b8b7c2f..c8277e46 100644 --- a/tests/test_repositories/test_warehouse_simple.py +++ b/tests/test_repositories/test_warehouse_simple.py @@ -129,7 +129,7 @@ def test_get_deps_auth(requests_mock, temp_cache, fixtures_path): assert requests_mock.last_request.headers['Authorization'] == 'Basic Z3JhbTp0ZXN0' -@pytest.mark.parametrize("version", ["0.1.2", Version("0.1.2")]) +@pytest.mark.parametrize('version', ['0.1.2', Version('0.1.2')]) def test_download(requests_mock, asyncio_mock, temp_cache, fixtures_path: Path, temp_path: Path, requirements_path: Path, version): pypi_url = 'https://custom.pypi.org/pypi/' From b32be4be7783257327987e2d10476974ab36d0e1 Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 27 Apr 2020 11:12:31 +0200 Subject: [PATCH 25/80] trigger CI From 5039e38b420594b97fd9dd71b4c3bb1d304ecda0 Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 27 Apr 2020 11:28:44 +0200 Subject: [PATCH 26/80] test and fix `deps add` --- dephell/actions/_package.py | 5 ++--- dephell/commands/deps_add.py | 1 + tests/test_commands/test_deps_add.py | 33 ++++++++++++++++++++++++++++ 3 files changed, 36 insertions(+), 3 deletions(-) create mode 100644 tests/test_commands/test_deps_add.py diff --git a/dephell/actions/_package.py b/dephell/actions/_package.py index 6bf151b5..6d8a88e8 100644 --- a/dephell/actions/_package.py +++ b/dephell/actions/_package.py @@ -22,6 +22,5 @@ def get_package(req: str, repo: str = None) -> Dependency: def get_resolver(reqs: Iterable[str] = None) -> Resolver: - root = PIPConverter(lock=False).loads_resolver('\n'.join(reqs)) - root.name = 'root' - return root + resolver = PIPConverter(lock=False).loads_resolver('\n'.join(reqs)) + return resolver diff --git a/dephell/commands/deps_add.py b/dephell/commands/deps_add.py index 9604b509..e3d7dde3 100644 --- a/dephell/commands/deps_add.py +++ b/dephell/commands/deps_add.py @@ -38,6 +38,7 @@ def __call__(self) -> bool: # get new deps new_resolver = get_resolver(reqs=self.args.name) new_root = new_resolver.graph._roots[0] + new_root.name = 'new-root' # set envs for dep in new_root.dependencies: diff --git a/tests/test_commands/test_deps_add.py b/tests/test_commands/test_deps_add.py new file mode 100644 index 00000000..99b93611 --- /dev/null +++ b/tests/test_commands/test_deps_add.py @@ -0,0 +1,33 @@ +# built-in +from pathlib import Path + +# external +import pytest + +# project +from dephell.commands import DepsAddCommand +from dephell.config import Config + + +@pytest.mark.allow_hosts() +def test_deps_add_command(temp_path: Path, capsys): + reqs_path = temp_path / 'requirements.txt' + reqs_path.write_text('six==1.12.0') + + config = Config() + config.attach({ + 'level': 'WARNING', + 'silent': True, + 'nocolors': True, + 'from': dict(format='pip', path=reqs_path), + }) + + command = DepsAddCommand(argv=['jinja2==2.0'], config=config) + result = command() + + captured = capsys.readouterr() + print(captured.err) + print(captured.out) + assert result is True + + assert set(reqs_path.read_text().split()) == {'six==1.12.0', 'jinja2==2.0'} From 450679df527e9af4e043923e5653aeca98c17eca Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 27 Apr 2020 12:04:47 +0200 Subject: [PATCH 27/80] + `--ca` --- dephell/config/builders.py | 1 + dephell/config/scheme.py | 1 + dephell/networking.py | 19 +++++++++++++++++-- docs/params.md | 1 + 4 files changed, 20 insertions(+), 2 deletions(-) diff --git a/dephell/config/builders.py b/dephell/config/builders.py index 1339eec9..ff32f6fc 100644 --- a/dephell/config/builders.py +++ b/dephell/config/builders.py @@ -88,6 +88,7 @@ def build_other(parser): other_group.add_argument('--project', help='path to the current project') other_group.add_argument('--bin', help='path to the dir for installing scripts') + other_group.add_argument('--ca', help='path to CA_BUNDLE file for SSL verification.') other_group.add_argument('--envs', nargs='*', help='environments (main, dev) or extras to install') other_group.add_argument('--tests', nargs='*', help='paths to test files') diff --git a/dephell/config/scheme.py b/dephell/config/scheme.py index acfb0946..9fe30653 100644 --- a/dephell/config/scheme.py +++ b/dephell/config/scheme.py @@ -115,6 +115,7 @@ ), 'project': dict(type='string', required=True), 'bin': dict(type='string', required=True), + 'ca': dict(type='string', required=False), 'envs': dict(type='list', schema=dict(type='string'), required=False, empty=False), 'tests': dict(type='list', schema=dict(type='string'), required=True), 'versioning': dict(type='string', required=True, allowed=get_schemes()), diff --git a/dephell/networking.py b/dephell/networking.py index cdafbaa7..8267e068 100644 --- a/dephell/networking.py +++ b/dephell/networking.py @@ -11,6 +11,7 @@ # app from . import __version__ +from .config import config USER_AGENT = 'DepHell/{version}'.format(version=__version__) @@ -18,14 +19,20 @@ def aiohttp_session(*, auth=None, **kwargs): - headers = dict() + headers = {'User-Agent': USER_AGENT} if auth: headers['Authorization'] = auth.encode() - ssl_context = create_default_context(cafile=certifi.where()) + + # setup SSL + cafile = config.get('ca') + if not cafile: + cafile = certifi.where() + ssl_context = create_default_context(cafile=cafile) try: connector = TCPConnector(ssl=ssl_context) except TypeError: connector = TCPConnector(ssl_context=ssl_context) + return ClientSession(headers=headers, connector=connector, **kwargs) @@ -33,12 +40,20 @@ def requests_session(*, auth=None, headers=None, **kwargs): session = requests.Session() if auth: session.auth = auth + + # setup SSL + cafile = config.get('ca') + if cafile: + session.verify = cafile + + # set headers if headers is None: headers = dict() headers.setdefault('User-Agent', USER_AGENT) session.headers = headers if kwargs: session.__dict__.update(kwargs) + return session diff --git a/docs/params.md b/docs/params.md index 538f3167..72b0dc2f 100644 --- a/docs/params.md +++ b/docs/params.md @@ -71,6 +71,7 @@ Other: + `--cache-ttl` -- Time to live for releases list cache (in seconds). 1 hour by default. + `--project` -- path to the current project. Current directory by default. + `--bin` -- path to the dir for installing scripts. ++ `--ca` -- path to a custom [CA bundle](https://www.namecheap.com/support/knowledgebase/article.aspx/986/69/what-is-ca-bundle) file. If provided, will be used for both `requests` and `aiohttp`. + `--envs` -- environments (`main`, `dev`) or extras to install or convert. + `--tests` -- path to test files for [dephell project test](cmd-project-test) command. + `--versioning` -- versioning scheme for project. See [dephell project bump](cmd-project-bump) for details. From d116bcb378027e33e16a74bae27bc8825be1795e Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 27 Apr 2020 12:23:12 +0200 Subject: [PATCH 28/80] test and describe missed params in docs --- docs/params.md | 18 ++++++++++++++++++ tests/test_docs.py | 13 +++++++++++++ 2 files changed, 31 insertions(+) create mode 100644 tests/test_docs.py diff --git a/docs/params.md b/docs/params.md index 72b0dc2f..2dcb80e8 100644 --- a/docs/params.md +++ b/docs/params.md @@ -52,13 +52,27 @@ Commands that accept these parameters: + `{digest}` will be replaced by the short 4-letters digest of the project path to avoid conflicts for the projects with the same name in different locations. + `{env}` will be replaced by current environment (`main` by default). + `--python` -- python version for venv. This can be reloaded in the dependencies file. ++ `--dotenv` -- path to a [.env](https://www.npmjs.com/package/dotenv) file. Will be sourced on a venv activation. + `vars` (config only) -- dict of environment variables to pass in virtual environment. +## Docker + ++ `--docker-repo` -- image name without tag to use for [Docker-based commands](index-docker). ++ `--docker-tag` -- image tag. ++ `--docker-container` -- container name. By default, automatically generated from the project name. + +## Project upload + ++ `--upload-url` -- URL of API endpoint to use to upload dist. ++ `--sign` -- a flag indicates that dists must be signed before uploading. ++ `--identity` -- GPG identity to use to sign dists. + ## Output + `--format` -- output format. + `--level` -- minimal level for log messages. Available levels: `DEBUG`, `INFO`, `WARNING`, `ERROR` and `EXCEPTION`. `INFO` by default. `DEBUG` and `INFO` writes in the stdout, other levels in the stderr. + `--nocolors` -- do not color output. ++ `--table` -- format output as a nice ASCII table. + `--silent` -- suppress any output except errors. Disables progress bar for resolver. + `--filter` -- [filter for JSON output](filters). + `--traceback` -- show traceback for exceptions. @@ -75,6 +89,10 @@ Other: + `--envs` -- environments (`main`, `dev`) or extras to install or convert. + `--tests` -- path to test files for [dephell project test](cmd-project-test) command. + `--versioning` -- versioning scheme for project. See [dephell project bump](cmd-project-bump) for details. ++ `--tag` -- template for git tag to use in [dephell project bump](cmd-project-bump). ++ `command` (config-only) -- default command to run in [dephell venv run](cmd-venv-run) and [dephell docker run](cmd-docker-run). ++ `--vendor-exclude` -- dependencies that shouldn't be [vendorized](index-vendor). ++ `--vendor-path` -- path to store vendorized dependencies.. ## Default values diff --git a/tests/test_docs.py b/tests/test_docs.py new file mode 100644 index 00000000..b446d51b --- /dev/null +++ b/tests/test_docs.py @@ -0,0 +1,13 @@ +from pathlib import Path + +from dephell.config.scheme import SCHEME + + +def test_params_all_described(): + undocumented = {'and', 'auth', 'vars', 'command'} + path = Path(__file__).parent.parent / 'docs' / 'params.md' + content = path.read_text() + for key in SCHEME: + if key in undocumented: + continue + assert '`--' + key in content From e3750154187d27afc36574cb6278ad9084f8b6c5 Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 27 Apr 2020 12:32:07 +0200 Subject: [PATCH 29/80] better poetry format detection --- dephell/converters/poetry.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/dephell/converters/poetry.py b/dephell/converters/poetry.py index c8725686..d165ae74 100644 --- a/dephell/converters/poetry.py +++ b/dephell/converters/poetry.py @@ -33,7 +33,7 @@ def can_parse(self, path: Path, content: Optional[str] = None) -> bool: if isinstance(path, str): path = Path(path) if content: - return '[tool.poetry]' in content + return '[tool.poetry]' in content or '[tool.poetry.' in content return path.name in ('poetry.toml', 'pyproject.toml') def loads(self, content) -> RootDependency: From 5a9eb358fc18a45727583f5fc89bb08ea920a441 Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 27 Apr 2020 14:15:21 +0200 Subject: [PATCH 30/80] small fixes --- dephell/controllers/_graph.py | 2 +- dephell/controllers/_resolver.py | 1 + 2 files changed, 2 insertions(+), 1 deletion(-) diff --git a/dephell/controllers/_graph.py b/dephell/controllers/_graph.py index 322e2cee..c7da0301 100644 --- a/dephell/controllers/_graph.py +++ b/dephell/controllers/_graph.py @@ -118,7 +118,7 @@ def add(self, dep, *, level: Optional[int] = None) -> None: raise KeyError('cannot find any parent for dependency: ' + str(dep.name)) def get_leafs(self, level: Optional[int] = None) -> tuple: - """Get deps that isn't applied yet + """Get deps that aren't applied yet """ layers = self._layers if level is not None: diff --git a/dephell/controllers/_resolver.py b/dephell/controllers/_resolver.py index 0bb21240..858f8e8b 100644 --- a/dephell/controllers/_resolver.py +++ b/dephell/controllers/_resolver.py @@ -163,6 +163,7 @@ def apply_envs(self, envs: set) -> None: continue if not (dep.envs | dep.inherited_envs) & envs: continue + logger.debug('re-apply', extra=dict(dep=dep.name, envs=envs)) self.apply(dep) def apply_markers(self, python) -> None: From 24112d6c21abe1c16d75ff478ab1670d885e7b3b Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 27 Apr 2020 14:15:31 +0200 Subject: [PATCH 31/80] test and fix apply_envs --- dephell/models/requirement.py | 7 +++- tests/helpers.py | 15 +++++++- tests/test_resolving/test_apply_envs.py | 51 +++++++++++++++++++++++++ 3 files changed, 69 insertions(+), 4 deletions(-) create mode 100644 tests/test_resolving/test_apply_envs.py diff --git a/dephell/models/requirement.py b/dephell/models/requirement.py index 6f5cf369..87fa2520 100644 --- a/dephell/models/requirement.py +++ b/dephell/models/requirement.py @@ -30,7 +30,8 @@ def from_graph(cls, graph, *, lock: bool) -> Tuple['Requirement', ...]: roots = [root.name for root in graph.get_layer(0)] # if roots wasn't applied then apply them - if len(graph._layers) == 1: + applied = len(graph._layers) != 1 + if not applied: for root in graph._roots: for dep in root.dependencies: graph.add(dep) @@ -38,7 +39,9 @@ def from_graph(cls, graph, *, lock: bool) -> Tuple['Requirement', ...]: # get all nodes for layer in reversed(graph._layers[1:]): # skip roots for dep in sorted(layer): - if dep.constraint.empty: + if not dep.used: + continue + if applied and not dep.applied: continue if dep.extra is None: req = cls(dep=dep, lock=lock, roots=roots) diff --git a/tests/helpers.py b/tests/helpers.py index 4365cf70..3caed4b3 100644 --- a/tests/helpers.py +++ b/tests/helpers.py @@ -71,7 +71,15 @@ def make_root(root, **releases) -> RootDependency: return root_dep -def check(root, resolved=True, missed=None, **deps): +def set_envs(root: RootDependency, dep_name: str, envs: str) -> None: + for dep in root.dependencies: + if dep.name == dep_name: + dep.envs = envs + return + raise RuntimeError('cannot find dep') + + +def check(root: RootDependency, resolved: bool = True, missed=None, envs: set = None, **deps): resolver = Resolver( graph=Graph(root), mutator=Mutator(), @@ -82,6 +90,9 @@ def check(root, resolved=True, missed=None, **deps): ): result = resolver.resolve(debug=True, silent=True) + if envs is not None: + resolver.apply_envs(envs=envs) + reqs = Requirement.from_graph(resolver.graph, lock=True) reqs = {req.name: req for req in reqs} @@ -104,4 +115,4 @@ def check(root, resolved=True, missed=None, **deps): if missed: for name in missed: - assert name not in reqs + assert name not in reqs, '{} must be missed but it is not'.format(name) diff --git a/tests/test_resolving/test_apply_envs.py b/tests/test_resolving/test_apply_envs.py new file mode 100644 index 00000000..8fcc0043 --- /dev/null +++ b/tests/test_resolving/test_apply_envs.py @@ -0,0 +1,51 @@ +# app +from ..helpers import Fake, check, make_root, set_envs + + +def test_direct_dependencies(): + root = make_root( + root=Fake('', 'a', 'b'), + a=(Fake('1.0'), ), + b=(Fake('1.0'), ), + ) + set_envs(root, 'a', {'main'}) + set_envs(root, 'b', {'dev'}) + check(root=root, a='==1.0', missed=['b'], envs={'main'}) + + +def test_subdependencies(): + root = make_root( + root=Fake('', 'a', 'b'), + a=(Fake('1.0'), ), + b=(Fake('1.0', 'c'), ), + c=(Fake('1.0'), ), + ) + set_envs(root, 'a', {'main'}) + set_envs(root, 'b', {'dev'}) + check(root=root, a='==1.0', missed=['b', 'c'], envs={'main'}) + + +def test_reapply(): + root = make_root( + root=Fake('', 'a', 'b'), + a=(Fake('1.0', 'c'), ), + b=(Fake('1.0', 'c'), ), + c=(Fake('1.0'), ), + ) + set_envs(root, 'a', {'main'}) + set_envs(root, 'b', {'dev'}) + check(root=root, a='==1.0', c='==1.0', missed=['b'], envs={'main'}) + + +def test_unapply_twice(): + root = make_root( + root=Fake('', 'a', 'b', 'c'), + a=(Fake('1.0'), ), + b=(Fake('1.0', 'd'), ), + c=(Fake('1.0', 'd'), ), + d=(Fake('1.0'), ), + ) + set_envs(root, 'a', {'main'}) + set_envs(root, 'b', {'dev'}) + set_envs(root, 'c', {'dev'}) + check(root=root, a='==1.0', missed=['b', 'c', 'd'], envs={'main'}) From dc26931de197f223e3dab8e58ac231b9af2a6f8e Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 27 Apr 2020 14:42:40 +0200 Subject: [PATCH 32/80] DRY and test more cases --- dephell/commands/deps_convert.py | 8 +---- dephell/controllers/_graph.py | 13 +++++++++ dephell/models/requirement.py | 10 ++----- tests/test_resolving/test_apply_envs.py | 39 +++++++++++++++++++++++++ 4 files changed, 55 insertions(+), 15 deletions(-) diff --git a/dephell/commands/deps_convert.py b/dephell/commands/deps_convert.py index fd36bed6..36ae8cdf 100644 --- a/dephell/commands/deps_convert.py +++ b/dephell/commands/deps_convert.py @@ -66,13 +66,7 @@ def __call__(self) -> bool: # filter out deps by `--envs` if self.config.get('envs'): - if len(resolver.graph._layers) == 1: - for root in resolver.graph._roots: - for dep in root.dependencies: - dep.applied = True - resolver.graph.add(dep) - for root in resolver.graph._roots: - root.applied = True + resolver.graph.fast_apply() resolver.apply_envs(set(self.config['envs'])) resolver.graph._layers = resolver.graph._layers[:1] diff --git a/dephell/controllers/_graph.py b/dephell/controllers/_graph.py index c7da0301..c8c95b14 100644 --- a/dephell/controllers/_graph.py +++ b/dephell/controllers/_graph.py @@ -193,6 +193,19 @@ def get_parents(self, *deps, avoid: Optional[list] = None) -> dict: )) return parents + def fast_apply(self) -> bool: + """Apply only the first layer. + """ + if len(self._layers) != 1: + return False + for root in self._roots: + for dep in root.dependencies: + dep.applied = True + self.add(dep) + for root in self._roots: + root.applied = True + return True + def draw(self, path: str = '.dephell_report', suffix: str = '') -> None: dot = graphviz.Digraph( name=self._roots[0].name + suffix, diff --git a/dephell/models/requirement.py b/dephell/models/requirement.py index 87fa2520..ec3cfd7d 100644 --- a/dephell/models/requirement.py +++ b/dephell/models/requirement.py @@ -28,20 +28,14 @@ def from_graph(cls, graph, *, lock: bool) -> Tuple['Requirement', ...]: result = OrderedDict() extras = defaultdict(list) roots = [root.name for root in graph.get_layer(0)] - - # if roots wasn't applied then apply them - applied = len(graph._layers) != 1 - if not applied: - for root in graph._roots: - for dep in root.dependencies: - graph.add(dep) + graph.fast_apply() # if roots wasn't applied, apply them # get all nodes for layer in reversed(graph._layers[1:]): # skip roots for dep in sorted(layer): if not dep.used: continue - if applied and not dep.applied: + if not dep.applied: continue if dep.extra is None: req = cls(dep=dep, lock=lock, roots=roots) diff --git a/tests/test_resolving/test_apply_envs.py b/tests/test_resolving/test_apply_envs.py index 8fcc0043..6c7ef7d7 100644 --- a/tests/test_resolving/test_apply_envs.py +++ b/tests/test_resolving/test_apply_envs.py @@ -1,7 +1,21 @@ +from dephell.controllers import Graph, Mutator, Resolver +from dephell.models import Requirement + # app from ..helpers import Fake, check, make_root, set_envs +def fast_filter(root): + resolver = Resolver( + graph=Graph(root), + mutator=Mutator(), + ) + resolver.graph.fast_apply() + resolver.apply_envs(envs={'main'}) + reqs = Requirement.from_graph(resolver.graph, lock=False) + return {req.name: req for req in reqs} + + def test_direct_dependencies(): root = make_root( root=Fake('', 'a', 'b'), @@ -49,3 +63,28 @@ def test_unapply_twice(): set_envs(root, 'b', {'dev'}) set_envs(root, 'c', {'dev'}) check(root=root, a='==1.0', missed=['b', 'c', 'd'], envs={'main'}) + + +def test_with_real_names(): + root = make_root( + root=Fake('', 'bandit', 'boltons'), + bandit=(Fake('1.0', 'colorama'), ), + boltons=(Fake('1.0'), ), + colorama=(Fake('1.0'), ), + ) + set_envs(root, 'boltons', {'main'}) + set_envs(root, 'bandit', {'dev'}) + check(root=root, boltons='==1.0', missed=['bandit', 'colorama'], envs={'main'}) + + +def test_direct_dependencies_without_resolving(): + root = make_root( + root=Fake('', 'a', 'b'), + a=(Fake('1.0'), ), + b=(Fake('1.0'), ), + ) + set_envs(root, 'a', {'main'}) + set_envs(root, 'b', {'dev'}) + + reqs = fast_filter(root) + assert set(reqs) == {'a'} From 44e08ae63100ba30bc82b42fa3ec0b158b79ce8f Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 27 Apr 2020 14:59:57 +0200 Subject: [PATCH 33/80] fix envs filtering in deps convert --- dephell/commands/deps_convert.py | 9 +++++++-- dephell/models/requirement.py | 5 ++++- 2 files changed, 11 insertions(+), 3 deletions(-) diff --git a/dephell/commands/deps_convert.py b/dephell/commands/deps_convert.py index 36ae8cdf..6703b295 100644 --- a/dephell/commands/deps_convert.py +++ b/dephell/commands/deps_convert.py @@ -66,9 +66,14 @@ def __call__(self) -> bool: # filter out deps by `--envs` if self.config.get('envs'): - resolver.graph.fast_apply() + if not dumper.lock: + resolver.graph.fast_apply() resolver.apply_envs(set(self.config['envs'])) - resolver.graph._layers = resolver.graph._layers[:1] + # If it's not a lockfile, we should drop all dependencies except direct ones. + # While `fast_apply` doesn't produce such dependencies, we want to be sure + # that we can't ever have them in the output. Trust no one. + if not dumper.lock: + resolver.graph._layers = resolver.graph._layers[:2] # dump self.logger.debug('dump dependencies...', extra=dict( diff --git a/dephell/models/requirement.py b/dephell/models/requirement.py index ec3cfd7d..8510e3f7 100644 --- a/dephell/models/requirement.py +++ b/dephell/models/requirement.py @@ -28,7 +28,10 @@ def from_graph(cls, graph, *, lock: bool) -> Tuple['Requirement', ...]: result = OrderedDict() extras = defaultdict(list) roots = [root.name for root in graph.get_layer(0)] - graph.fast_apply() # if roots wasn't applied, apply them + + # if roots weren't applied, apply them + if not lock: + graph.fast_apply() # get all nodes for layer in reversed(graph._layers[1:]): # skip roots From edb5a568c5c9899e74a23397af904e0e6ecc20b3 Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 27 Apr 2020 15:43:51 +0200 Subject: [PATCH 34/80] fix requirements comparation --- dephell/models/requirement.py | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/dephell/models/requirement.py b/dephell/models/requirement.py index 8510e3f7..ae949190 100644 --- a/dephell/models/requirement.py +++ b/dephell/models/requirement.py @@ -219,7 +219,10 @@ def optional(self) -> bool: @staticmethod def _get_comparable_dict(dep) -> dict: - excluded = {'constraint', 'repo', 'link', 'marker', 'license', 'inherited_envs', 'locations'} + excluded = { + 'constraint', 'repo', 'link', 'marker', 'license', + 'inherited_envs', 'locations', 'applied', + } result = attr.asdict(dep, recurse=True, filter=lambda x, _: x.name not in excluded) result['constraint'] = str(dep.constraint) if dep.marker: From a17f9e248c380a7069bf1c16dbb09a3c9484d627 Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 27 Apr 2020 16:03:51 +0200 Subject: [PATCH 35/80] support env in deps tree and colorize output --- dephell/commands/deps_tree.py | 24 +++++++++++++++++++++--- 1 file changed, 21 insertions(+), 3 deletions(-) diff --git a/dephell/commands/deps_tree.py b/dephell/commands/deps_tree.py index 5beb0982..b2eaac03 100644 --- a/dephell/commands/deps_tree.py +++ b/dephell/commands/deps_tree.py @@ -35,7 +35,10 @@ def __call__(self) -> bool: if self.args.type == 'pretty': for dep in sorted(resolver.graph.get_layer(1)): - print('\n'.join(self._make_tree(dep))) + if not dep.applied: + continue + content = '\n'.join(self._make_tree(dep)) + print(self._colorize(content)) return True if self.args.type == 'json': @@ -66,9 +69,9 @@ def _make_tree(cls, dep, *, level: int = 0) -> List[str]: best = dep.group.best_release.version latest = dep.group.best_release.version if best == latest: - template = '{level}- {name} [required: {constraint}, latest: {latest}]' + template = '{level}- {name} [required: `{constraint}`, latest: `{latest}`]' else: - template = '{level}- {name} [required: {constraint}, locked: {best}, latest: {latest}]' + template = '{level}- {name} [required: `{constraint}`, locked: `{best}`, latest: `{latest}`]' lines = [template.format( level=' ' * level, name=dep.name, @@ -80,3 +83,18 @@ def _make_tree(cls, dep, *, level: int = 0) -> List[str]: for subdep in sorted(deps): lines.extend(cls._make_tree(subdep, level=level + 1)) return lines + + @staticmethod + def _colorize(content: str) -> str: + try: + import pygments + import pygments.lexers + import pygments.formatters + except ImportError: + return content + content = pygments.highlight( + code=content, + lexer=pygments.lexers.MarkdownLexer(), + formatter=pygments.formatters.TerminalFormatter(), + ) + return content.strip() From 7da2d0cc9874d057554e441dd08073b9e8399b15 Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 27 Apr 2020 16:32:34 +0200 Subject: [PATCH 36/80] test more cases --- tests/test_resolving/test_apply_envs.py | 29 +++++++++++++++++++++++++ 1 file changed, 29 insertions(+) diff --git a/tests/test_resolving/test_apply_envs.py b/tests/test_resolving/test_apply_envs.py index 6c7ef7d7..ce638704 100644 --- a/tests/test_resolving/test_apply_envs.py +++ b/tests/test_resolving/test_apply_envs.py @@ -77,6 +77,35 @@ def test_with_real_names(): check(root=root, boltons='==1.0', missed=['bandit', 'colorama'], envs={'main'}) +def test_deep_dependencies(): + root = make_root( + root=Fake('', 'apiwrapper', 'sphinx', 'certifi'), + sphinx=(Fake('1.0', 'requests'), ), + apiwrapper=(Fake('1.0', 'requests'), ), + requests=(Fake('1.0', 'certifi'), ), + certifi=(Fake('1.0'), ), + ) + set_envs(root, 'sphinx', {'main'}) + set_envs(root, 'apiwrapper', {'dev'}) + set_envs(root, 'certifi', {'dev'}) + check(root=root, sphinx='==1.0', certifi='==1.0', requests='==1.0', missed=['apiwrapper'], envs={'main'}) + + +def test_very_deep_dependencies_reapply(): + root = make_root( + root=Fake('', 'a', 'b'), + a=(Fake('1.0', 'c'), ), + b=(Fake('1.0', 'c'), ), + + c=(Fake('1.0', 'd'), ), + d=(Fake('1.0', 'e'), ), + e=(Fake('1.0'), ), + ) + set_envs(root, 'a', {'main'}) + set_envs(root, 'b', {'dev'}) + check(root=root, a='==1.0', c='==1.0', d='==1.0', e='==1.0', missed=['b'], envs={'main'}) + + def test_direct_dependencies_without_resolving(): root = make_root( root=Fake('', 'a', 'b'), From 4871a507c9a0267b6668655d7420df581cb3edf1 Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 27 Apr 2020 17:30:54 +0200 Subject: [PATCH 37/80] recursively re-apply deps --- dephell/controllers/_resolver.py | 10 +++++++--- tests/test_resolving/test_apply_envs.py | 13 +++++++++++++ 2 files changed, 20 insertions(+), 3 deletions(-) diff --git a/dephell/controllers/_resolver.py b/dephell/controllers/_resolver.py index 858f8e8b..dbbe5581 100644 --- a/dephell/controllers/_resolver.py +++ b/dephell/controllers/_resolver.py @@ -22,9 +22,9 @@ def __init__(self, graph, mutator): self.graph = graph self.mutator = mutator - def apply(self, parent): + def apply(self, parent, recursive: bool = False): """ - Returns conflicting (incompatible) dependency + Returns conflicting (incompatible) dependency. """ for new_dep in parent.dependencies: other_dep = self.graph.get(new_dep.name) @@ -45,6 +45,10 @@ def apply(self, parent): other_dep += new_dep except TypeError: # conflict happened return other_dep + # `recursive` used only in re-application of dependencies, + # when the graph already was built before. + if recursive: + self.apply(other_dep, recursive=True) # check if not other_dep.compat: return other_dep @@ -164,7 +168,7 @@ def apply_envs(self, envs: set) -> None: if not (dep.envs | dep.inherited_envs) & envs: continue logger.debug('re-apply', extra=dict(dep=dep.name, envs=envs)) - self.apply(dep) + self.apply(dep, recursive=True) def apply_markers(self, python) -> None: implementation = python.implementation diff --git a/tests/test_resolving/test_apply_envs.py b/tests/test_resolving/test_apply_envs.py index ce638704..0ad80ba4 100644 --- a/tests/test_resolving/test_apply_envs.py +++ b/tests/test_resolving/test_apply_envs.py @@ -106,6 +106,19 @@ def test_very_deep_dependencies_reapply(): check(root=root, a='==1.0', c='==1.0', d='==1.0', e='==1.0', missed=['b'], envs={'main'}) +def test_dependencies_unapply_twice_and_reapply(): + root = make_root( + root=Fake('', 'requests', 'sphinx', 'certifi'), + requests=(Fake('1.0', 'certifi'), ), + sphinx=(Fake('1.0', 'requests'), ), + certifi=(Fake('1.0'), ), + ) + set_envs(root, 'sphinx', {'main'}) + set_envs(root, 'requests', {'dev'}) + set_envs(root, 'certifi', {'dev'}) + check(root=root, sphinx='==1.0', requests='==1.0', certifi='==1.0', missed=[], envs={'main'}) + + def test_direct_dependencies_without_resolving(): root = make_root( root=Fake('', 'a', 'b'), From bcb9e9ace3715f1b114678b81e1c8389e9c1257a Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 27 Apr 2020 17:37:02 +0200 Subject: [PATCH 38/80] fix requirment graph fast_apply --- dephell/models/requirement.py | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/dephell/models/requirement.py b/dephell/models/requirement.py index ae949190..f04f65e5 100644 --- a/dephell/models/requirement.py +++ b/dephell/models/requirement.py @@ -30,8 +30,7 @@ def from_graph(cls, graph, *, lock: bool) -> Tuple['Requirement', ...]: roots = [root.name for root in graph.get_layer(0)] # if roots weren't applied, apply them - if not lock: - graph.fast_apply() + graph.fast_apply() # get all nodes for layer in reversed(graph._layers[1:]): # skip roots From 4bd0d6be53ab3690b882d60570b86070c1558de3 Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 27 Apr 2020 19:09:38 +0200 Subject: [PATCH 39/80] fix typo --- dephell/controllers/_resolver.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/dephell/controllers/_resolver.py b/dephell/controllers/_resolver.py index dbbe5581..35514c2c 100644 --- a/dephell/controllers/_resolver.py +++ b/dephell/controllers/_resolver.py @@ -161,13 +161,13 @@ def apply_envs(self, envs: set) -> None: # Some child deps can be unapplied from other child deps, but we need them. # For example, if we need A, but don't need B, and A and B depends on C, - # then C will be unapplied from B. Let's return B in the graph by re-applying A. + # then C will be unapplied from B. Let's return B in the graph by reapplying A. for dep in self.graph: if not dep.applied: continue if not (dep.envs | dep.inherited_envs) & envs: continue - logger.debug('re-apply', extra=dict(dep=dep.name, envs=envs)) + logger.debug('reapply', extra=dict(dep=dep.name, envs=envs)) self.apply(dep, recursive=True) def apply_markers(self, python) -> None: From b98647b195fda9aa975d9e3f8d5a706722699cf3 Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 27 Apr 2020 19:21:01 +0200 Subject: [PATCH 40/80] do not download too big files --- dephell/repositories/_warehouse/_api.py | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/dephell/repositories/_warehouse/_api.py b/dephell/repositories/_warehouse/_api.py index 5b68d597..3545fd15 100644 --- a/dephell/repositories/_warehouse/_api.py +++ b/dephell/repositories/_warehouse/_api.py @@ -38,6 +38,8 @@ 'summary', 'version', } +# Do not download too big files +SIZE_LIMIT = 2 * 1024 * 1024 # 2 Mb @attr.s() @@ -284,8 +286,11 @@ async def _get_from_files(self, files_info: List[dict]) -> Tuple[str, ...]: for converter, checker in rules: for file_info in files_info: + if file_info.get('size') > SIZE_LIMIT: + continue if not checker(file_info): continue + logger.debug('downloading file...', extra=dict(url=file_info['url'])) try: return await self._download_and_parse( url=file_info['url'], From 597cef0a4005ce1d494917825ccbe5c916ed89be Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 27 Apr 2020 19:30:34 +0200 Subject: [PATCH 41/80] make one group releases count configurable --- dephell/models/groups.py | 16 +++++++++++----- 1 file changed, 11 insertions(+), 5 deletions(-) diff --git a/dephell/models/groups.py b/dephell/models/groups.py index f69182d0..a73b8308 100644 --- a/dephell/models/groups.py +++ b/dephell/models/groups.py @@ -12,6 +12,9 @@ loop = asyncio.get_event_loop() +# How many latest releases should go in their own group. +# Lesser value -> less network requests per package and more mutations. +ONE_GROUP_RELEASES = 1 def get_key(release) -> str: @@ -164,12 +167,15 @@ def __iter__(self): self.actualize(group=group) yield group - # load first group + # load the first two groups if not self._loaded_groups: - release = self.releases[0] - self._load_release_deps(release) - self._loaded_releases_count += 1 - yield self._make_group([release]) + for i in range(ONE_GROUP_RELEASES): + if len(self.releases) <= i: + return + release = self.releases[i] + self._load_release_deps(release) + self._loaded_releases_count += 1 + yield self._make_group([release]) # load new groups prev_key = None From cfddb0df04449e8c48497d93f102ea3e722c40e6 Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 27 Apr 2020 20:15:14 +0200 Subject: [PATCH 42/80] avoid network requests in apply_envs for deps convert --- dephell/commands/deps_convert.py | 6 +++--- dephell/controllers/_resolver.py | 14 +++++++++++--- tests/test_resolving/test_apply_envs.py | 16 ++++++++++++++-- 3 files changed, 28 insertions(+), 8 deletions(-) diff --git a/dephell/commands/deps_convert.py b/dephell/commands/deps_convert.py index 6703b295..457746ea 100644 --- a/dephell/commands/deps_convert.py +++ b/dephell/commands/deps_convert.py @@ -66,13 +66,13 @@ def __call__(self) -> bool: # filter out deps by `--envs` if self.config.get('envs'): - if not dumper.lock: + if not should_be_resolved: resolver.graph.fast_apply() - resolver.apply_envs(set(self.config['envs'])) + resolver.apply_envs(envs=set(self.config['envs']), deep=should_be_resolved) # If it's not a lockfile, we should drop all dependencies except direct ones. # While `fast_apply` doesn't produce such dependencies, we want to be sure # that we can't ever have them in the output. Trust no one. - if not dumper.lock: + if not should_be_resolved: resolver.graph._layers = resolver.graph._layers[:2] # dump diff --git a/dephell/controllers/_resolver.py b/dephell/controllers/_resolver.py index 35514c2c..ceb225b1 100644 --- a/dephell/controllers/_resolver.py +++ b/dephell/controllers/_resolver.py @@ -137,7 +137,12 @@ def _resolve(self, debug: bool, silent: bool, level: Optional[int], spinner) -> self.unapply(dep) dep.group = group - def apply_envs(self, envs: set) -> None: + def apply_envs(self, envs: set, deep: bool = True) -> None: + """Filter out dependencies from the graph by the given envs. + + deep: Helps to avoid fetching dependencies (hence the network requests). + Set it to False for not resolved graph to make filtering faster. + """ if not any(root.dependencies for root in self.graph.get_layer(0)): logger.debug('no dependencies, nothing to filter') return @@ -156,7 +161,8 @@ def apply_envs(self, envs: set) -> None: # and ignored in Requirement.from_graph. # It's bad behavior because deps of this dep can be required for other # deps that won't be unapplied. - self.unapply(dep, soft=True) + if deep: + self.unapply(dep, soft=True) dep.applied = False # Some child deps can be unapplied from other child deps, but we need them. @@ -168,7 +174,9 @@ def apply_envs(self, envs: set) -> None: if not (dep.envs | dep.inherited_envs) & envs: continue logger.debug('reapply', extra=dict(dep=dep.name, envs=envs)) - self.apply(dep, recursive=True) + if deep: + self.apply(dep, recursive=True) + dep.applied = True def apply_markers(self, python) -> None: implementation = python.implementation diff --git a/tests/test_resolving/test_apply_envs.py b/tests/test_resolving/test_apply_envs.py index 0ad80ba4..aada059c 100644 --- a/tests/test_resolving/test_apply_envs.py +++ b/tests/test_resolving/test_apply_envs.py @@ -1,3 +1,4 @@ +from dephell.converters import PIPConverter from dephell.controllers import Graph, Mutator, Resolver from dephell.models import Requirement @@ -5,13 +6,13 @@ from ..helpers import Fake, check, make_root, set_envs -def fast_filter(root): +def fast_filter(root, *, deep=True): resolver = Resolver( graph=Graph(root), mutator=Mutator(), ) resolver.graph.fast_apply() - resolver.apply_envs(envs={'main'}) + resolver.apply_envs(envs={'main'}, deep=deep) reqs = Requirement.from_graph(resolver.graph, lock=False) return {req.name: req for req in reqs} @@ -130,3 +131,14 @@ def test_direct_dependencies_without_resolving(): reqs = fast_filter(root) assert set(reqs) == {'a'} + + +def test_not_deep(): + """If deep is False, filtering must work and no network requests can be made. + """ + loader = PIPConverter(lock=False) + root = loader.loads(content='sphinx\nrequests') + root.dependencies[0].envs = {'main'} + root.dependencies[1].envs = {'dev'} + reqs = fast_filter(root, deep=False) + assert set(reqs) == {'sphinx'} From a455cb8764594884b70db5c1422006f3cf643945 Mon Sep 17 00:00:00 2001 From: Gram Date: Tue, 28 Apr 2020 08:01:04 +0200 Subject: [PATCH 43/80] sort imports --- dephell/commands/deps_convert.py | 8 ++++---- tests/test_docs.py | 2 ++ tests/test_resolving/test_apply_envs.py | 3 ++- 3 files changed, 8 insertions(+), 5 deletions(-) diff --git a/dephell/commands/deps_convert.py b/dephell/commands/deps_convert.py index 457746ea..0612f1ed 100644 --- a/dephell/commands/deps_convert.py +++ b/dephell/commands/deps_convert.py @@ -81,10 +81,10 @@ def __call__(self) -> bool: path=self.config['to']['path'], )) - dumper_kwargs = { - 'reqs': Requirement.from_graph(resolver.graph, lock=dumper.lock), - 'project': resolver.graph.metainfo, - } + dumper_kwargs = dict( + reqs=Requirement.from_graph(resolver.graph, lock=dumper.lock), + project=resolver.graph.metainfo, + ) if self.config['to']['path'] == 'stdout': print(dumper.dumps(**dumper_kwargs)) else: diff --git a/tests/test_docs.py b/tests/test_docs.py index b446d51b..871895f1 100644 --- a/tests/test_docs.py +++ b/tests/test_docs.py @@ -1,5 +1,7 @@ +# built-in from pathlib import Path +# project from dephell.config.scheme import SCHEME diff --git a/tests/test_resolving/test_apply_envs.py b/tests/test_resolving/test_apply_envs.py index aada059c..eb9437a9 100644 --- a/tests/test_resolving/test_apply_envs.py +++ b/tests/test_resolving/test_apply_envs.py @@ -1,5 +1,6 @@ -from dephell.converters import PIPConverter +# project from dephell.controllers import Graph, Mutator, Resolver +from dephell.converters import PIPConverter from dephell.models import Requirement # app From 2d816a6c13aed4129e02e2fdae2d3fb6c3c14142 Mon Sep 17 00:00:00 2001 From: Gram Date: Tue, 28 Apr 2020 08:28:58 +0200 Subject: [PATCH 44/80] upd changelog --- docs/changelog.md | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/docs/changelog.md b/docs/changelog.md index e24a8876..fa846bc4 100644 --- a/docs/changelog.md +++ b/docs/changelog.md @@ -2,6 +2,10 @@ Follow [@PythonDepHell](https://twitter.com/PythonDepHell) on Twitter to get updates about new features and releases. +## v.0.8.3 (2020-04-28) + +This release brings a lot of small fixes. See [the milestone](https://github.com/dephell/dephell/milestone/6?closed=1) for the details. The only noticeable change is an ability to provide a custom CA bundle via `--ca` flag. A few next releases also will bring more stability and speed into DepHell. [Stay tuned!](https://twitter.com/PythonDepHell) + ## v.0.8.2 (2020-03-19) New commands: From 15cdcfcfbc57d94130cb45ebdf80c498decf0807 Mon Sep 17 00:00:00 2001 From: Gram Date: Tue, 28 Apr 2020 08:29:08 +0200 Subject: [PATCH 45/80] bump version to 0.8.3 --- dephell/__init__.py | 2 +- docs/conf.py | 2 +- pyproject.toml | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/dephell/__init__.py b/dephell/__init__.py index 638b8b99..d5048b4b 100644 --- a/dephell/__init__.py +++ b/dephell/__init__.py @@ -13,6 +13,6 @@ """ -__version__ = '0.8.2' +__version__ = '0.8.3' __author__ = 'Gram (@orsinium)' __license__ = 'MIT' diff --git a/docs/conf.py b/docs/conf.py index 84782e17..d669e5e9 100644 --- a/docs/conf.py +++ b/docs/conf.py @@ -30,7 +30,7 @@ copyright = '{}, Gram (@orsinium)'.format(date.today().year) author = 'Gram (@orsinium)' -version = '0.8.2' +version = '0.8.3' release = version language = None diff --git a/pyproject.toml b/pyproject.toml index 98ac2988..343444f5 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -105,7 +105,7 @@ import_heading_localfolder = "app" [tool.poetry] name = "dephell" -version = "0.8.2" +version = "0.8.3" authors = ["Gram "] description = "Dependency resolution for Python" readme = "README.md" From 01efc064171e51c590225fbd39fff971884be8f3 Mon Sep 17 00:00:00 2001 From: Gram Date: Tue, 28 Apr 2020 08:29:50 +0200 Subject: [PATCH 46/80] bump setup.py --- setup.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/setup.py b/setup.py index f7904a7b..2db62868 100644 --- a/setup.py +++ b/setup.py @@ -23,7 +23,7 @@ setup( long_description=readme, name='dephell', - version='0.8.2', + version='0.8.3', description='Dependency resolution for Python', python_requires='>=3.6', project_urls={ From 24eb6af040e75cf893919d01e964627b2b9e60ec Mon Sep 17 00:00:00 2001 From: Viginox <31762120+Viginox@users.noreply.github.com> Date: Wed, 13 May 2020 17:17:15 +0900 Subject: [PATCH 47/80] Fix issue with not expanding home paths --- dephell/config/builders.py | 32 ++++++++++++++++++++------------ 1 file changed, 20 insertions(+), 12 deletions(-) diff --git a/dephell/config/builders.py b/dephell/config/builders.py index ff32f6fc..5d6b96a1 100644 --- a/dephell/config/builders.py +++ b/dephell/config/builders.py @@ -1,4 +1,7 @@ # project +# built-in +from pathlib import Path + # external from dephell_versioning import get_schemes @@ -6,6 +9,11 @@ from ..constants import FORMATS, LOG_FORMATTERS, LOG_LEVELS, REPOSITORIES, STRATEGIES +# helper function for path values +def expanded_path(string): + return Path(string).expanduser().resolve().as_posix() + + env_help = ( 'Pipenv has 2 envs in same file: main and dev. ' 'For poetry you can also use main-opt and dev-opt ' @@ -16,22 +24,22 @@ def build_config(parser): config_group = parser.add_argument_group('Configuration file') - config_group.add_argument('-c', '--config', help='path to config file.') + config_group.add_argument('-c', '--config', help='path to config file.', type=expanded_path) config_group.add_argument('-e', '--env', help='environment in config.') def build_from(parser): from_group = parser.add_argument_group('Input file') - from_group.add_argument('--from', help='path or format for reading requirements.') + from_group.add_argument('--from', help='path or format for reading requirements.', type=expanded_path) from_group.add_argument('--from-format', choices=FORMATS, help='format for reading requirements.') - from_group.add_argument('--from-path', help='path to input file.') + from_group.add_argument('--from-path', help='path to input file.', type=expanded_path) def build_to(parser): to_group = parser.add_argument_group('Output file') - to_group.add_argument('--to', help='path or format for writing requirements.') + to_group.add_argument('--to', help='path or format for writing requirements.', type=expanded_path) to_group.add_argument('--to-format', choices=FORMATS, help='output requirements file format.') - to_group.add_argument('--to-path', help='path to output file.') + to_group.add_argument('--to-path', help='path to output file.', type=expanded_path) to_group.add_argument( '--sdist-ratio', help='ratio of tests and project size after which tests will be excluded from sdist.', @@ -68,9 +76,9 @@ def build_output(parser): def build_venv(parser): venv_group = parser.add_argument_group('Virtual environment') - venv_group.add_argument('--venv', help='path to venv directory for project.') + venv_group.add_argument('--venv', help='path to venv directory for project.', type=expanded_path) venv_group.add_argument('--python', help='python version for venv.') - venv_group.add_argument('--dotenv', help='path to .env file') + venv_group.add_argument('--dotenv', help='path to .env file', type=expanded_path) def build_docker(parser): @@ -83,14 +91,14 @@ def build_docker(parser): def build_other(parser): other_group = parser.add_argument_group('Other') - other_group.add_argument('--cache-path', help='path to dephell cache') + other_group.add_argument('--cache-path', help='path to dephell cache', type=expanded_path) other_group.add_argument('--cache-ttl', type=int, help='Time to live for releases list cache') - other_group.add_argument('--project', help='path to the current project') - other_group.add_argument('--bin', help='path to the dir for installing scripts') - other_group.add_argument('--ca', help='path to CA_BUNDLE file for SSL verification.') + other_group.add_argument('--project', help='path to the current project', type=expanded_path) + other_group.add_argument('--bin', help='path to the dir for installing scripts', type=expanded_path) + other_group.add_argument('--ca', help='path to CA_BUNDLE file for SSL verification.', type=expanded_path) other_group.add_argument('--envs', nargs='*', help='environments (main, dev) or extras to install') - other_group.add_argument('--tests', nargs='*', help='paths to test files') + other_group.add_argument('--tests', nargs='*', help='paths to test files', type=expanded_path) other_group.add_argument('--versioning', choices=sorted(get_schemes()), help='versioning scheme for project') From f315d5816949ecfdea250660ab604a6384a88e94 Mon Sep 17 00:00:00 2001 From: Gram Date: Fri, 15 May 2020 11:12:40 +0200 Subject: [PATCH 48/80] prepare --- .gitignore | 4 ++-- tests/test_commands/test_generate_license.py | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/.gitignore b/.gitignore index aaed82a4..c6f6d1c9 100644 --- a/.gitignore +++ b/.gitignore @@ -22,7 +22,7 @@ pip-wheel-metadata/ /README.rst .idea .venv - venv/ - \.python-version +monkeytype.sqlite3 +annotations.json diff --git a/tests/test_commands/test_generate_license.py b/tests/test_commands/test_generate_license.py index 732581db..2e8c0aec 100644 --- a/tests/test_commands/test_generate_license.py +++ b/tests/test_commands/test_generate_license.py @@ -10,7 +10,7 @@ from dephell.config import Config -@pytest.mark.allow_hosts(['pypi.org', '140.211.169.8']) +@pytest.mark.allow_hosts() def test_generate_license_command(temp_path: Path): config = Config() config.attach({'project': str(temp_path)}) From d400b275ef299cf43f52a8f98f5aa438ab8ca87b Mon Sep 17 00:00:00 2001 From: Gram Date: Fri, 15 May 2020 11:24:30 +0200 Subject: [PATCH 49/80] annotate a few things --- dephell/actions/_transform.py | 8 ++++---- dephell/cache.py | 20 ++++++++++++++------ dephell/context_tools.py | 5 ++++- 3 files changed, 22 insertions(+), 11 deletions(-) diff --git a/dephell/actions/_transform.py b/dephell/actions/_transform.py index 4e9f127d..a7394c66 100644 --- a/dephell/actions/_transform.py +++ b/dephell/actions/_transform.py @@ -54,7 +54,7 @@ class ModuleImportModifier: > """ - def __init__(self, old_name, new_name): + def __init__(self, old_name: str, new_name: str) -> None: self.old_name = old_name self.new_name = new_name @@ -91,7 +91,7 @@ class FromImportModifier: > """ - def __init__(self, old_name, new_name): + def __init__(self, old_name: str, new_name: str) -> None: self.old_name = old_name self.new_name = new_name @@ -138,7 +138,7 @@ class ModuleAsImportModifier: > """ - def __init__(self, old_name, new_name): + def __init__(self, old_name: str, new_name: str) -> None: self.old_name = old_name self.new_name = new_name @@ -161,7 +161,7 @@ class StringModifier: string=STRING """ - def __init__(self, old_name, new_name): + def __init__(self, old_name: str, new_name: str) -> None: self.old_name = old_name self.new_name = new_name diff --git a/dephell/cache.py b/dephell/cache.py index 2d5f69dd..ad6ae1d4 100644 --- a/dephell/cache.py +++ b/dephell/cache.py @@ -3,11 +3,19 @@ import pickle from pathlib import Path from time import time -from typing import List +from typing import List, TYPE_CHECKING # app from .cached_property import cached_property from .config import config +from dephell.converters.pip import PIPConverter +from typing import Any +from typing import Optional +from typing import Union + + +if TYPE_CHECKING: + from dephell.models.dependency import Dependency class BaseCache: @@ -53,7 +61,7 @@ def dump(self, data) -> None: class TextCache(BaseCache): ext = '.txt' - def load(self): + def load(self) -> Optional[Any]: if not self.path.exists(): return None with self.path.open('r') as stream: @@ -68,7 +76,7 @@ def dump(self, data: List[str]) -> None: class JSONCache(BaseCache): ext = '.json' - def load(self): + def load(self) -> Optional[Any]: if not self.path.exists(): return None with self.path.open('r') as stream: @@ -78,7 +86,7 @@ def load(self): return None return None - def dump(self, data): + def dump(self, data: Union[list, dict]) -> None: self.path.parent.mkdir(parents=True, exist_ok=True) with self.path.open('w') as stream: json.dump(data, stream) @@ -88,12 +96,12 @@ class RequirementsCache(BaseCache): ext = '.txt' @cached_property - def converter(self): + def converter(self) -> PIPConverter: from .converters import PIPConverter return PIPConverter(lock=False) - def load(self): + def load(self) -> Optional[List[Dependency]]: if not self.path.exists(): return None root = self.converter.load(self.path) diff --git a/dephell/context_tools.py b/dephell/context_tools.py index f44b36e1..0ad1cae2 100644 --- a/dephell/context_tools.py +++ b/dephell/context_tools.py @@ -3,10 +3,13 @@ import sys from contextlib import contextmanager from typing import Dict +from pathlib import Path +from typing import Iterator +from typing import Union @contextmanager -def chdir(path): +def chdir(path: Union[Path, str]) -> Iterator: """Context manager for changing dir and restoring previous workdir after exit. """ curdir = os.getcwd() From 1958689007a3cbdad8d0ca04876eff0a93d37edc Mon Sep 17 00:00:00 2001 From: Gram Date: Fri, 15 May 2020 11:27:45 +0200 Subject: [PATCH 50/80] +simple annotations --- dephell/commands/generate_config.py | 5 +++-- dephell/models/auth.py | 2 +- dephell/models/extra_dependency.py | 2 +- dephell/models/group.py | 2 +- dephell/models/marker_tracker.py | 2 +- dephell/models/release.py | 2 +- dephell/repositories/_conda/_composite.py | 2 +- dephell/repositories/_git/git.py | 5 +++-- dephell/repositories/_warehouse/_api.py | 2 +- dephell/repositories/_warehouse/_local.py | 2 +- dephell/repositories/_warehouse/_simple.py | 2 +- 11 files changed, 15 insertions(+), 13 deletions(-) diff --git a/dephell/commands/generate_config.py b/dephell/commands/generate_config.py index 0d0898b9..3eb105c9 100644 --- a/dephell/commands/generate_config.py +++ b/dephell/commands/generate_config.py @@ -12,6 +12,7 @@ from ..constants import PAIRS, SUFFIXES from ..converters import CONVERTERS from .base import BaseCommand +from tomlkit.items import Table class GenerateConfigCommand(BaseCommand): @@ -33,11 +34,11 @@ def config(self) -> Config: config._data['config'] = 'pyproject.toml' return config - def validate(self): + def validate(self) -> bool: return True @staticmethod - def _make_env(from_format, from_path, to_format, to_path): + def _make_env(from_format: str, from_path: str, to_format: str, to_path: str) -> Table: table = tomlkit.table() table['from'] = tomlkit.inline_table() diff --git a/dephell/models/auth.py b/dephell/models/auth.py index 9473ef95..7f2ff18f 100644 --- a/dephell/models/auth.py +++ b/dephell/models/auth.py @@ -24,6 +24,6 @@ def __call__(self, request): return request # for aiohttp - def encode(self): + def encode(self) -> str: creds = (self.username + ':' + self.password).encode(self.encoding) return 'Basic ' + b64encode(creds).decode('ascii') diff --git a/dephell/models/extra_dependency.py b/dephell/models/extra_dependency.py index d986043f..f911d1f2 100644 --- a/dephell/models/extra_dependency.py +++ b/dephell/models/extra_dependency.py @@ -12,7 +12,7 @@ class ExtraDependency(Dependency): extra = attr.ib(type=str, default='') - def __attrs_post_init__(self): + def __attrs_post_init__(self) -> None: assert self.extra != '' @classmethod diff --git a/dephell/models/group.py b/dephell/models/group.py index 3b6f8c59..0c94f4d8 100644 --- a/dephell/models/group.py +++ b/dephell/models/group.py @@ -88,7 +88,7 @@ def versions(self) -> set: def empty(self) -> bool: return not bool(self.releases) - def __str__(self): + def __str__(self) -> str: versions = sorted(release.version for release in self.releases) versions = [str(v) for v in versions] if not versions: diff --git a/dephell/models/marker_tracker.py b/dephell/models/marker_tracker.py index 8dce4b8c..3d0d443e 100644 --- a/dephell/models/marker_tracker.py +++ b/dephell/models/marker_tracker.py @@ -3,7 +3,7 @@ class MarkerTracker: - def __init__(self): + def __init__(self) -> None: self._markers = dict() @property diff --git a/dephell/models/release.py b/dephell/models/release.py index f35db33f..2196a4f8 100644 --- a/dephell/models/release.py +++ b/dephell/models/release.py @@ -25,7 +25,7 @@ class Release: extra = attr.ib(type=Optional[str], default=None) - def __attrs_post_init__(self): + def __attrs_post_init__(self) -> None: assert '[' not in self.raw_name, self.raw_name @classmethod diff --git a/dephell/repositories/_conda/_composite.py b/dephell/repositories/_conda/_composite.py index 5817e842..3ac64261 100644 --- a/dephell/repositories/_conda/_composite.py +++ b/dephell/repositories/_conda/_composite.py @@ -19,7 +19,7 @@ class CondaRepo(CondaBaseRepo): _requests = attr.ib(default=0) - def __attrs_post_init__(self): + def __attrs_post_init__(self) -> None: if not self.git_repo.channels: self.git_repo.channels = self.channels if not self.cloud_repo.channels: diff --git a/dephell/repositories/_git/git.py b/dephell/repositories/_git/git.py index 0a6b9820..55a75e70 100644 --- a/dephell/repositories/_git/git.py +++ b/dephell/repositories/_git/git.py @@ -53,9 +53,10 @@ def path(self): return path @cached_property - def metaversion(self): + def metaversion(self) -> Optional[str]: if self.link.rev: return self.get_nearest_version(self.link.rev) + return None # PUBLIC METHODS @@ -153,7 +154,7 @@ def _get_rev_hash(self, rev: str): return data[-1].strip().strip('"') @staticmethod - def _clean_tag(tag): + def _clean_tag(tag: str) -> str: return rex_version.fullmatch(tag).groups()[0] def _version_to_rev(self, version) -> str: diff --git a/dephell/repositories/_warehouse/_api.py b/dephell/repositories/_warehouse/_api.py index 3545fd15..5d77e8f8 100644 --- a/dephell/repositories/_warehouse/_api.py +++ b/dephell/repositories/_warehouse/_api.py @@ -56,7 +56,7 @@ class WarehouseAPIRepo(WarehouseBaseRepo): hash = None link = None - def __attrs_post_init__(self): + def __attrs_post_init__(self) -> None: # make name canonical if self.name in ('pypi.org', 'pypi.python.org'): self.name = 'pypi' diff --git a/dephell/repositories/_warehouse/_local.py b/dephell/repositories/_warehouse/_local.py index 70dbc7d2..17223760 100644 --- a/dephell/repositories/_warehouse/_local.py +++ b/dephell/repositories/_warehouse/_local.py @@ -32,7 +32,7 @@ class WarehouseLocalRepo(WarehouseBaseRepo): from_config = attr.ib(type=bool, default=False) propagate = True # deps of deps will inherit repo - def __attrs_post_init__(self): + def __attrs_post_init__(self) -> None: if isinstance(self.path, str): self.path = Path(self.path) diff --git a/dephell/repositories/_warehouse/_simple.py b/dephell/repositories/_warehouse/_simple.py index b85ec4c8..931876d0 100644 --- a/dephell/repositories/_warehouse/_simple.py +++ b/dephell/repositories/_warehouse/_simple.py @@ -40,7 +40,7 @@ class WarehouseSimpleRepo(WarehouseBaseRepo): from_config = attr.ib(type=bool, default=False) propagate = True # deps of deps will inherit repo - def __attrs_post_init__(self): + def __attrs_post_init__(self) -> None: # make name canonical if self.name in ('pypi.org', 'pypi.python.org'): self.name = 'pypi' From 4d6b5b8c8088c0319aae3302e5b5a53ab64d7de5 Mon Sep 17 00:00:00 2001 From: Gram Date: Fri, 15 May 2020 11:42:26 +0200 Subject: [PATCH 51/80] annotate more --- dephell/config/builders.py | 17 +++++++++-------- dephell/config/manager.py | 2 +- dephell/controllers/_graph.py | 8 ++++---- dephell/controllers/_mutator.py | 2 +- dephell/controllers/_resolver.py | 9 +++++++-- dephell/converters/flit.py | 2 +- dephell/converters/installed.py | 4 +++- dephell/converters/pip.py | 2 +- dephell/converters/pipfile.py | 7 +++++-- dephell/converters/pipfilelock.py | 5 ++++- dephell/converters/poetry.py | 11 ++++++++--- dephell/converters/poetrylock.py | 5 +++-- dephell/converters/sdist.py | 2 +- dephell/models/auth.py | 3 ++- dephell/models/constraint.py | 13 +++++++++++-- dephell/models/extra_dependency.py | 4 +++- dephell/models/group.py | 14 +++++++++++--- dephell/models/groups.py | 3 ++- dephell/models/release.py | 5 ++++- dephell/models/requirement.py | 12 +++++++++--- dephell/networking.py | 10 +++++++--- dephell/yaml.py | 5 ++++- 22 files changed, 101 insertions(+), 44 deletions(-) diff --git a/dephell/config/builders.py b/dephell/config/builders.py index ff32f6fc..8ce44de0 100644 --- a/dephell/config/builders.py +++ b/dephell/config/builders.py @@ -4,6 +4,7 @@ # app from ..constants import FORMATS, LOG_FORMATTERS, LOG_LEVELS, REPOSITORIES, STRATEGIES +from dephell_argparse._parser import Parser env_help = ( @@ -14,20 +15,20 @@ ) -def build_config(parser): +def build_config(parser: Parser) -> None: config_group = parser.add_argument_group('Configuration file') config_group.add_argument('-c', '--config', help='path to config file.') config_group.add_argument('-e', '--env', help='environment in config.') -def build_from(parser): +def build_from(parser: Parser) -> None: from_group = parser.add_argument_group('Input file') from_group.add_argument('--from', help='path or format for reading requirements.') from_group.add_argument('--from-format', choices=FORMATS, help='format for reading requirements.') from_group.add_argument('--from-path', help='path to input file.') -def build_to(parser): +def build_to(parser) -> None: to_group = parser.add_argument_group('Output file') to_group.add_argument('--to', help='path or format for writing requirements.') to_group.add_argument('--to-format', choices=FORMATS, help='output requirements file format.') @@ -38,21 +39,21 @@ def build_to(parser): ) -def build_resolver(parser): +def build_resolver(parser: Parser) -> None: resolver_group = parser.add_argument_group('Resolver rules') resolver_group.add_argument('--strategy', choices=STRATEGIES, help='Algorithm to select best release.') resolver_group.add_argument('--prereleases', action='store_true', help='Allow prereleases') resolver_group.add_argument('--mutations', type=int, help='Maximum mutations limit') -def build_api(parser): +def build_api(parser: Parser) -> None: api_group = parser.add_argument_group('APIs endpoints') api_group.add_argument('--warehouse', nargs='*', help='warehouse API URL.') api_group.add_argument('--bitbucket', help='bitbucket API URL.') api_group.add_argument('--repo', choices=REPOSITORIES, help='force repository for first-level deps.') -def build_output(parser): +def build_output(parser: Parser) -> None: output_group = parser.add_argument_group('Console output') output_group.add_argument('--format', choices=LOG_FORMATTERS, help='output format.') output_group.add_argument('--level', choices=LOG_LEVELS, help='minimal level for log messages.') @@ -66,7 +67,7 @@ def build_output(parser): output_group.add_argument('--pdb', action='store_true', help='run pdb for critical exceptions.') -def build_venv(parser): +def build_venv(parser: Parser) -> None: venv_group = parser.add_argument_group('Virtual environment') venv_group.add_argument('--venv', help='path to venv directory for project.') venv_group.add_argument('--python', help='python version for venv.') @@ -80,7 +81,7 @@ def build_docker(parser): docker_group.add_argument('--docker-container', help='container name') -def build_other(parser): +def build_other(parser: Parser) -> None: other_group = parser.add_argument_group('Other') other_group.add_argument('--cache-path', help='path to dephell cache') diff --git a/dephell/config/manager.py b/dephell/config/manager.py index 9ee1a89f..4d1cc386 100644 --- a/dephell/config/manager.py +++ b/dephell/config/manager.py @@ -183,7 +183,7 @@ def validate(self) -> bool: def format_errors(self) -> str: return json.dumps(self.errors, indent=2, sort_keys=True) - def __getattr__(self, name): + def __getattr__(self, name: str): return getattr(self._data, name) def __getitem__(self, name: str): diff --git a/dephell/controllers/_graph.py b/dephell/controllers/_graph.py index c8c95b14..029eaf46 100644 --- a/dephell/controllers/_graph.py +++ b/dephell/controllers/_graph.py @@ -1,7 +1,7 @@ # built-in from collections import ChainMap from logging import getLogger -from typing import TYPE_CHECKING, Optional +from typing import TYPE_CHECKING, Iterator, Optional # app from ..imports import lazy_import @@ -63,7 +63,7 @@ def __contains__(self, dep) -> bool: dep = dep.name return dep in self._mapping - def __iter__(self): + def __iter__(self) -> Iterator: return iter(self._mapping.values()) def __repr__(self): @@ -76,7 +76,7 @@ def __repr__(self): class Graph: conflict = None # type: Optional[Dependency] - def __init__(self, *roots): + def __init__(self, *roots: RootDependency) -> None: for root in roots: if not root.dependencies: logger.warning('empty root passed') @@ -260,7 +260,7 @@ def metainfo(self) -> RootDependency: # magic - def __iter__(self): + def __iter__(self) -> Iterator: return iter(self.deps) def __contains__(self, dep) -> bool: diff --git a/dephell/controllers/_mutator.py b/dephell/controllers/_mutator.py index 221ef0bf..b8f2901a 100644 --- a/dephell/controllers/_mutator.py +++ b/dephell/controllers/_mutator.py @@ -16,7 +16,7 @@ logger = getLogger('dephell.controllers') -def lazy_product(*all_groups): +def lazy_product(*all_groups) -> Iterator: slices = [[] for _ in range(len(all_groups))] all_groups = [iter(groups) for groups in all_groups] diff --git a/dephell/controllers/_resolver.py b/dephell/controllers/_resolver.py index ceb225b1..e30283f4 100644 --- a/dephell/controllers/_resolver.py +++ b/dephell/controllers/_resolver.py @@ -1,7 +1,7 @@ # built-in import re from logging import getLogger -from typing import Optional +from typing import Optional, TYPE_CHECKING # external from packaging.markers import Marker @@ -13,12 +13,17 @@ from ._conflict import analyze_conflict +if TYPE_CHECKING: + from dephell.controllers._graph import Graph + from dephell.controllers._mutator import Mutator + + logger = getLogger('dephell.resolver') REX_BASE_VERSION = re.compile(r'[0-9\.]+') class Resolver: - def __init__(self, graph, mutator): + def __init__(self, graph: Graph, mutator: Mutator) -> None: self.graph = graph self.mutator = mutator diff --git a/dephell/converters/flit.py b/dephell/converters/flit.py index 4302f8fa..3fa77f39 100644 --- a/dephell/converters/flit.py +++ b/dephell/converters/flit.py @@ -275,7 +275,7 @@ def dumps(self, reqs, project: RootDependency, content=None) -> str: return tomlkit.dumps(doc) - def _format_req(self, req): + def _format_req(self, req: Requirement) -> str: line = req.name if req.extras: line += '[{extras}]'.format(extras=','.join(req.extras)) diff --git a/dephell/converters/installed.py b/dephell/converters/installed.py index 67ef4303..4fec134f 100644 --- a/dephell/converters/installed.py +++ b/dephell/converters/installed.py @@ -14,6 +14,8 @@ from .base import BaseConverter from .egginfo import EggInfoConverter from .wheel import WheelConverter +from dephell.controllers._resolver import Resolver +from typing import List @attr.s() @@ -25,7 +27,7 @@ class InstalledConverter(BaseConverter): 'command-not-found', # https://stackoverflow.com/a/22676267 } - def load_resolver(self, path=None, paths=None): + def load_resolver(self, path=None, paths: List[Path] = None) -> Resolver: if path is not None: root = self.load(path=path) else: diff --git a/dephell/converters/pip.py b/dephell/converters/pip.py index a7fd93d2..6363b6be 100644 --- a/dephell/converters/pip.py +++ b/dephell/converters/pip.py @@ -160,7 +160,7 @@ def dumps(self, reqs, project: Optional[RootDependency] = None, return '\n'.join(lines) + '\n' @staticmethod - def _get_finder(): + def _get_finder() -> PackageFinder: try: return PackageFinder(find_links=[], index_urls=[], session=PipSession()) except TypeError: diff --git a/dephell/converters/pipfile.py b/dephell/converters/pipfile.py index 8ae6f0cd..b05ff3a8 100644 --- a/dephell/converters/pipfile.py +++ b/dephell/converters/pipfile.py @@ -12,9 +12,12 @@ # app from ..controllers import DependencyMaker, RepositoriesRegistry -from ..models import Constraint, Dependency, RootDependency +from ..models import Constraint, Dependency, Requirement, RootDependency from ..repositories import WarehouseBaseRepo, WarehouseLocalRepo, get_repo from .base import BaseConverter +from tomlkit.items import InlineTable +from tomlkit.items import String +from typing import Union VCS_LIST = ('git', 'svn', 'hg', 'bzr') @@ -197,7 +200,7 @@ def _make_deps(self, root, name: str, content) -> List[Dependency]: editable=content.get('editable', False), ) - def _format_req(self, req): + def _format_req(self, req: Requirement) -> Union[InlineTable, String]: result = tomlkit.inline_table() for name, value in req: if name == 'rev': diff --git a/dephell/converters/pipfilelock.py b/dephell/converters/pipfilelock.py index ce0a7254..3a73ac31 100644 --- a/dephell/converters/pipfilelock.py +++ b/dephell/converters/pipfilelock.py @@ -16,6 +16,9 @@ from ..models import RootDependency from ..repositories import WarehouseBaseRepo, WarehouseLocalRepo from .pipfile import PIPFileConverter +from dephell.models.requirement import Requirement +from typing import Any +from typing import Dict # https://stackoverflow.com/a/23820416 @@ -120,7 +123,7 @@ def _get_hash(data: dict) -> str: content = json.dumps(data, sort_keys=True, separators=(',', ':')) return sha256(content.encode('utf8')).hexdigest() - def _format_req(self, req): + def _format_req(self, req: Requirement) -> Dict[str, Any]: result = dict() for name, value in req: if name == 'rev': diff --git a/dephell/converters/poetry.py b/dephell/converters/poetry.py index d165ae74..9d09d1ca 100644 --- a/dephell/converters/poetry.py +++ b/dephell/converters/poetry.py @@ -12,9 +12,14 @@ # app from ..controllers import DependencyMaker, Readme, RepositoriesRegistry -from ..models import Author, Constraint, Dependency, EntryPoint, RootDependency +from ..models import Author, Constraint, Dependency, EntryPoint, RootDependency, Requirement from ..repositories import WarehouseLocalRepo from .base import BaseConverter +from tomlkit.items import Table +from typing import Tuple +from tomlkit.items import InlineTable +from tomlkit.items import String +from typing import Union @attr.s() @@ -239,7 +244,7 @@ def dumps(self, reqs, project: RootDependency, content=None) -> str: return tomlkit.dumps(doc).rstrip() + '\n' @staticmethod - def _add_entrypoints(section, entrypoints): + def _add_entrypoints(section: Table, entrypoints: Tuple[EntryPoint, ...]) -> None: # drop old console_scripts if 'scripts' in section: scripts = {e.name for e in entrypoints if e.group == 'console_scripts'} @@ -370,7 +375,7 @@ def _make_deps(self, root, name: str, content, envs: set) -> List[Dependency]: ) return deps - def _format_req(self, req): + def _format_req(self, req: Requirement) -> Union[InlineTable, String]: result = tomlkit.inline_table() for name, value in req: if name in self.fields: diff --git a/dephell/converters/poetrylock.py b/dephell/converters/poetrylock.py index 2ea66562..871605fc 100644 --- a/dephell/converters/poetrylock.py +++ b/dephell/converters/poetrylock.py @@ -12,9 +12,10 @@ # app from ..controllers import DependencyMaker, RepositoriesRegistry -from ..models import Constraint, Dependency, RootDependency +from ..models import Constraint, Dependency, RootDependency, Requirement from ..repositories import WarehouseBaseRepo, WarehouseLocalRepo from .base import BaseConverter +from tomlkit.items import Table @attr.s() @@ -191,7 +192,7 @@ def _make_deps(cls, root, content, envs, repo) -> List[Dependency]: return deps - def _format_req(self, req): + def _format_req(self, req: Requirement) -> Table: result = tomlkit.table() for name, value in req: if name in self.fields: diff --git a/dephell/converters/sdist.py b/dephell/converters/sdist.py index eaadbe29..bde8ccd6 100644 --- a/dephell/converters/sdist.py +++ b/dephell/converters/sdist.py @@ -126,7 +126,7 @@ def dump(self, reqs, path: Path, project: RootDependency) -> None: self._write_additional_files(tar=tar, project=project, subdir=subdir) - def _write_additional_files(self, *, tar, project, subdir): + def _write_additional_files(self, *, tar: TarFile, project: RootDependency, subdir: str) -> None: # write readme if project.readme: tar.add( diff --git a/dephell/models/auth.py b/dephell/models/auth.py index 7f2ff18f..2d0d460a 100644 --- a/dephell/models/auth.py +++ b/dephell/models/auth.py @@ -5,6 +5,7 @@ # external import attr from requests.auth import HTTPBasicAuth +from requests.models import PreparedRequest @attr.s(eq=True, order=True, frozen=True) @@ -15,7 +16,7 @@ class Auth(HTTPBasicAuth): encoding = attr.ib(type=str, default='latin1') # for requests - def __call__(self, request): + def __call__(self, request: PreparedRequest) -> PreparedRequest: # additional check to prevent lack of creds if urlparse(request.url).hostname != self.hostname: return request diff --git a/dephell/models/constraint.py b/dephell/models/constraint.py index c0f7998e..1cf770f3 100644 --- a/dephell/models/constraint.py +++ b/dephell/models/constraint.py @@ -1,12 +1,21 @@ # built-in from copy import deepcopy +from typing import TYPE_CHECKING # external from dephell_specifier import RangeSpecifier +from typing import Any +from typing import Union + + +if TYPE_CHECKING: + from .dependency import Dependency + from .extra_dependency import ExtraDependency + from .root import RootDependency class Constraint: - def __init__(self, source, spec): + def __init__(self, source: Union['Dependency', 'ExtraDependency', 'RootDependency'], spec: Any) -> None: """ source (Dependency) spec (str, LegacySpecifier, Specifier) @@ -76,7 +85,7 @@ def copy(self) -> 'Constraint': def __and__(self, other): return self.copy().__iand__(other) - def __iand__(self, other): + def __iand__(self, other: 'Constraint') -> 'Constraint': if not isinstance(other, Constraint): return NotImplemented for name, group in other._groups.items(): diff --git a/dephell/models/extra_dependency.py b/dephell/models/extra_dependency.py index f911d1f2..0193d133 100644 --- a/dephell/models/extra_dependency.py +++ b/dephell/models/extra_dependency.py @@ -6,6 +6,8 @@ from ..cached_property import cached_property from .dependency import Dependency from .groups import Groups +from tomlkit.items import String +from typing import Union @attr.s(eq=False, order=False) @@ -16,7 +18,7 @@ def __attrs_post_init__(self) -> None: assert self.extra != '' @classmethod - def from_dep(cls, dep, extra): + def from_dep(cls, dep: Dependency, extra: Union[str, String]) -> 'ExtraDependency': return cls(**attr.asdict(dep, recurse=False), extra=extra) @cached_property diff --git a/dephell/models/group.py b/dephell/models/group.py index 0c94f4d8..693014c3 100644 --- a/dephell/models/group.py +++ b/dephell/models/group.py @@ -1,10 +1,18 @@ # built-in from operator import attrgetter from typing import Optional +from typing import TYPE_CHECKING # app from ..cached_property import cached_property from ..config import config +from dephell.models.release import Release +from dephell.models.root import RootRelease +from typing import Union + + +if TYPE_CHECKING: + from .dependency import Dependency class Group: @@ -19,7 +27,7 @@ def __init__(self, number: int, releases: set, dep=None): # BEST RELEASE PROPERTIES @property - def best_release(self): + def best_release(self) -> Release: strategy = max if config['strategy'] == 'max' else min best_time = strategy(release.time for release in self.releases) best_releases = [release for release in self.releases if release.time == best_time] @@ -34,7 +42,7 @@ def time(self): # RANDOM RELEASE PROPERTIES @cached_property - def random(self): + def random(self) -> Union[Release, RootRelease]: return next(iter(self.all_releases)) @cached_property @@ -52,7 +60,7 @@ def extra(self) -> Optional[str]: # OTHER PROPERTIES @cached_property - def metadependency(self): + def metadependency(self) -> 'Dependency': """MetaDependency is a dependency on the parent for extra. For example, `requests[security]` extra depends on `requests` Dependency. diff --git a/dephell/models/groups.py b/dephell/models/groups.py index a73b8308..7055207a 100644 --- a/dephell/models/groups.py +++ b/dephell/models/groups.py @@ -9,6 +9,7 @@ from ..cached_property import cached_property from ..config import config from .group import Group +from typing import Iterator loop = asyncio.get_event_loop() @@ -161,7 +162,7 @@ def _make_group(self, releases) -> Group: self.actualize(group=group) return group - def __iter__(self): + def __iter__(self) -> Iterator: # return all groups from cache for group in self._loaded_groups: self.actualize(group=group) diff --git a/dephell/models/release.py b/dephell/models/release.py index 2196a4f8..fd3b73c5 100644 --- a/dephell/models/release.py +++ b/dephell/models/release.py @@ -10,6 +10,9 @@ # app from ..cached_property import cached_property +from typing import Any +from typing import Dict +from typing import List @attr.s(hash=False, eq=False, order=False) @@ -29,7 +32,7 @@ def __attrs_post_init__(self) -> None: assert '[' not in self.raw_name, self.raw_name @classmethod - def from_response(cls, name, version, info, extra=None): + def from_response(cls, name: str, version: str, info: List[Dict[str, Any]], extra=None) -> 'Release': latest = info[-1] python = latest['requires_python'] if python is not None: diff --git a/dephell/models/requirement.py b/dephell/models/requirement.py index f04f65e5..0bd9be65 100644 --- a/dephell/models/requirement.py +++ b/dephell/models/requirement.py @@ -1,6 +1,6 @@ # built-in from collections import OrderedDict, defaultdict -from typing import Iterable, Optional, Set, Tuple +from typing import Iterable, Optional, Set, Tuple, TYPE_CHECKING # external import attr @@ -8,6 +8,12 @@ # app from ..cached_property import cached_property +from typing import Any +from typing import Iterator + + +if TYPE_CHECKING: + from dephell.models.release import Release # noqa: F401 class Requirement: @@ -53,7 +59,7 @@ def from_graph(cls, graph, *, lock: bool) -> Tuple['Requirement', ...]: return tuple(result.values()) @cached_property - def release(self): + def release(self) -> Optional['Release']: if self.lock: return self.dep.group.best_release @@ -243,7 +249,7 @@ def same_dep(self, other_dep) -> bool: # magic methods - def __iter__(self): + def __iter__(self) -> Iterator[Any]: for name in self._properties: value = getattr(self, name) if value: diff --git a/dephell/networking.py b/dephell/networking.py index 8267e068..707f1200 100644 --- a/dephell/networking.py +++ b/dephell/networking.py @@ -12,13 +12,17 @@ # app from . import __version__ from .config import config +from typing import Any +from typing import Optional +from dephell.models.auth import Auth +from requests.sessions import Session USER_AGENT = 'DepHell/{version}'.format(version=__version__) logger = getLogger('dephell.networking') -def aiohttp_session(*, auth=None, **kwargs): +def aiohttp_session(*, auth: Optional[Auth] = None, **kwargs: Any) -> ClientSession: headers = {'User-Agent': USER_AGENT} if auth: headers['Authorization'] = auth.encode() @@ -36,7 +40,7 @@ def aiohttp_session(*, auth=None, **kwargs): return ClientSession(headers=headers, connector=connector, **kwargs) -def requests_session(*, auth=None, headers=None, **kwargs): +def requests_session(*, auth: Optional[Any] = None, headers: Optional[Any] = None, **kwargs: Any) -> Session: session = requests.Session() if auth: session.auth = auth @@ -61,7 +65,7 @@ def aiohttp_repeat(func=None, *, count: int = 4): if func is None: return partial(func, count=count) - async def wrapper(*args, **kwargs): + async def wrapper(*args: Any, **kwargs: Any) -> Optional[Any]: for pause in range(1, count + 1): try: return await func(*args, **kwargs) diff --git a/dephell/yaml.py b/dephell/yaml.py index a0dfa76e..fbcac8f3 100644 --- a/dephell/yaml.py +++ b/dephell/yaml.py @@ -1,5 +1,8 @@ # app from .imports import lazy_import +from typing import Any +from typing import Dict +from typing import Optional, TextIO ruamel_yaml = lazy_import('ruamel.yaml', package='ruamel.yaml') @@ -24,6 +27,6 @@ def yaml_load(stream, *, safe: bool = True): return py_yaml.load(stream) -def yaml_dump(data, stream): +def yaml_dump(data: Dict[str, Any], stream: TextIO) -> Optional[Any]: parser = ruamel_yaml.YAML() return parser.dump(data, stream) From c39bca41245a22706728738d95b66e545ed51f85 Mon Sep 17 00:00:00 2001 From: Gram Date: Fri, 15 May 2020 11:45:10 +0200 Subject: [PATCH 52/80] fix lazy importing --- dephell/cache.py | 8 ++++---- dephell/controllers/_resolver.py | 2 +- dephell/models/group.py | 8 ++++---- 3 files changed, 9 insertions(+), 9 deletions(-) diff --git a/dephell/cache.py b/dephell/cache.py index ad6ae1d4..f3cc412b 100644 --- a/dephell/cache.py +++ b/dephell/cache.py @@ -8,14 +8,14 @@ # app from .cached_property import cached_property from .config import config -from dephell.converters.pip import PIPConverter from typing import Any from typing import Optional from typing import Union if TYPE_CHECKING: - from dephell.models.dependency import Dependency + from .converters.pip import PIPConverter + from .models.dependency import Dependency # noqa: F401 class BaseCache: @@ -96,12 +96,12 @@ class RequirementsCache(BaseCache): ext = '.txt' @cached_property - def converter(self) -> PIPConverter: + def converter(self) -> 'PIPConverter': from .converters import PIPConverter return PIPConverter(lock=False) - def load(self) -> Optional[List[Dependency]]: + def load(self) -> Optional[List['Dependency']]: if not self.path.exists(): return None root = self.converter.load(self.path) diff --git a/dephell/controllers/_resolver.py b/dephell/controllers/_resolver.py index e30283f4..3872d17f 100644 --- a/dephell/controllers/_resolver.py +++ b/dephell/controllers/_resolver.py @@ -23,7 +23,7 @@ class Resolver: - def __init__(self, graph: Graph, mutator: Mutator) -> None: + def __init__(self, graph: 'Graph', mutator: 'Mutator') -> None: self.graph = graph self.mutator = mutator diff --git a/dephell/models/group.py b/dephell/models/group.py index 693014c3..e6d62bfd 100644 --- a/dephell/models/group.py +++ b/dephell/models/group.py @@ -6,13 +6,13 @@ # app from ..cached_property import cached_property from ..config import config -from dephell.models.release import Release -from dephell.models.root import RootRelease from typing import Union if TYPE_CHECKING: from .dependency import Dependency + from .release import Release + from .root import RootRelease # noqa: F401 class Group: @@ -27,7 +27,7 @@ def __init__(self, number: int, releases: set, dep=None): # BEST RELEASE PROPERTIES @property - def best_release(self) -> Release: + def best_release(self) -> 'Release': strategy = max if config['strategy'] == 'max' else min best_time = strategy(release.time for release in self.releases) best_releases = [release for release in self.releases if release.time == best_time] @@ -42,7 +42,7 @@ def time(self): # RANDOM RELEASE PROPERTIES @cached_property - def random(self) -> Union[Release, RootRelease]: + def random(self) -> Union['Release', 'RootRelease']: return next(iter(self.all_releases)) @cached_property From ccefea40ed4e9997ceb9b8e8ed42485bd8811f20 Mon Sep 17 00:00:00 2001 From: Gram Date: Fri, 15 May 2020 11:45:24 +0200 Subject: [PATCH 53/80] sort imports --- dephell/cache.py | 5 +---- dephell/commands/generate_config.py | 2 +- dephell/config/builders.py | 2 +- dephell/context_tools.py | 4 +--- dephell/controllers/_resolver.py | 2 +- dephell/converters/installed.py | 7 ++++--- dephell/converters/pipfile.py | 6 ++---- dephell/converters/pipfilelock.py | 8 ++++---- dephell/converters/poetry.py | 10 +++------- dephell/converters/poetrylock.py | 4 ++-- dephell/models/constraint.py | 4 +--- dephell/models/extra_dependency.py | 6 ++++-- dephell/models/group.py | 4 +--- dephell/models/groups.py | 3 +-- dephell/models/release.py | 5 +---- dephell/models/requirement.py | 4 +--- dephell/networking.py | 9 +++++---- dephell/yaml.py | 6 +++--- 18 files changed, 37 insertions(+), 54 deletions(-) diff --git a/dephell/cache.py b/dephell/cache.py index f3cc412b..57ecb0d2 100644 --- a/dephell/cache.py +++ b/dephell/cache.py @@ -3,14 +3,11 @@ import pickle from pathlib import Path from time import time -from typing import List, TYPE_CHECKING +from typing import TYPE_CHECKING, Any, List, Optional, Union # app from .cached_property import cached_property from .config import config -from typing import Any -from typing import Optional -from typing import Union if TYPE_CHECKING: diff --git a/dephell/commands/generate_config.py b/dephell/commands/generate_config.py index 3eb105c9..3768c09a 100644 --- a/dephell/commands/generate_config.py +++ b/dephell/commands/generate_config.py @@ -5,6 +5,7 @@ # external import tomlkit +from tomlkit.items import Table # app from ..cached_property import cached_property @@ -12,7 +13,6 @@ from ..constants import PAIRS, SUFFIXES from ..converters import CONVERTERS from .base import BaseCommand -from tomlkit.items import Table class GenerateConfigCommand(BaseCommand): diff --git a/dephell/config/builders.py b/dephell/config/builders.py index 8ce44de0..9606cabe 100644 --- a/dephell/config/builders.py +++ b/dephell/config/builders.py @@ -1,10 +1,10 @@ # project # external +from dephell_argparse._parser import Parser from dephell_versioning import get_schemes # app from ..constants import FORMATS, LOG_FORMATTERS, LOG_LEVELS, REPOSITORIES, STRATEGIES -from dephell_argparse._parser import Parser env_help = ( diff --git a/dephell/context_tools.py b/dephell/context_tools.py index 0ad1cae2..ae12fbe6 100644 --- a/dephell/context_tools.py +++ b/dephell/context_tools.py @@ -2,10 +2,8 @@ import os import sys from contextlib import contextmanager -from typing import Dict from pathlib import Path -from typing import Iterator -from typing import Union +from typing import Dict, Iterator, Union @contextmanager diff --git a/dephell/controllers/_resolver.py b/dephell/controllers/_resolver.py index 3872d17f..4345769c 100644 --- a/dephell/controllers/_resolver.py +++ b/dephell/controllers/_resolver.py @@ -1,7 +1,7 @@ # built-in import re from logging import getLogger -from typing import Optional, TYPE_CHECKING +from typing import TYPE_CHECKING, Optional # external from packaging.markers import Marker diff --git a/dephell/converters/installed.py b/dephell/converters/installed.py index 4fec134f..3c671eff 100644 --- a/dephell/converters/installed.py +++ b/dephell/converters/installed.py @@ -1,21 +1,22 @@ # built-in import sys from pathlib import Path -from typing import Iterable, Union +from typing import Iterable, List, Union # external import attr from dephell_discover import Root as PackageRoot from packaging.utils import canonicalize_name +# project +from dephell.controllers._resolver import Resolver + # app from ..controllers import DependencyMaker from ..models import RootDependency from .base import BaseConverter from .egginfo import EggInfoConverter from .wheel import WheelConverter -from dephell.controllers._resolver import Resolver -from typing import List @attr.s() diff --git a/dephell/converters/pipfile.py b/dephell/converters/pipfile.py index b05ff3a8..cf49c8e7 100644 --- a/dephell/converters/pipfile.py +++ b/dephell/converters/pipfile.py @@ -1,6 +1,6 @@ # built-in from pathlib import Path -from typing import List, Optional +from typing import List, Optional, Union # external import attr @@ -9,15 +9,13 @@ from dephell_pythons import Pythons from dephell_specifier import RangeSpecifier from packaging.utils import canonicalize_name +from tomlkit.items import InlineTable, String # app from ..controllers import DependencyMaker, RepositoriesRegistry from ..models import Constraint, Dependency, Requirement, RootDependency from ..repositories import WarehouseBaseRepo, WarehouseLocalRepo, get_repo from .base import BaseConverter -from tomlkit.items import InlineTable -from tomlkit.items import String -from typing import Union VCS_LIST = ('git', 'svn', 'hg', 'bzr') diff --git a/dephell/converters/pipfilelock.py b/dephell/converters/pipfilelock.py index 3a73ac31..873dea2e 100644 --- a/dephell/converters/pipfilelock.py +++ b/dephell/converters/pipfilelock.py @@ -3,7 +3,7 @@ from collections import OrderedDict from hashlib import sha256 from pathlib import Path -from typing import Optional +from typing import Any, Dict, Optional # external import attr @@ -11,14 +11,14 @@ from dephell_pythons import Pythons from dephell_specifier import RangeSpecifier +# project +from dephell.models.requirement import Requirement + # app from ..controllers import RepositoriesRegistry from ..models import RootDependency from ..repositories import WarehouseBaseRepo, WarehouseLocalRepo from .pipfile import PIPFileConverter -from dephell.models.requirement import Requirement -from typing import Any -from typing import Dict # https://stackoverflow.com/a/23820416 diff --git a/dephell/converters/poetry.py b/dephell/converters/poetry.py index 9d09d1ca..cf5f5126 100644 --- a/dephell/converters/poetry.py +++ b/dephell/converters/poetry.py @@ -1,7 +1,7 @@ # built-in from collections import defaultdict from pathlib import Path -from typing import List, Optional +from typing import List, Optional, Tuple, Union # external import attr @@ -9,17 +9,13 @@ from dephell_discover import Root as PackageRoot from dephell_specifier import RangeSpecifier from packaging.utils import canonicalize_name +from tomlkit.items import InlineTable, String, Table # app from ..controllers import DependencyMaker, Readme, RepositoriesRegistry -from ..models import Author, Constraint, Dependency, EntryPoint, RootDependency, Requirement +from ..models import Author, Constraint, Dependency, EntryPoint, Requirement, RootDependency from ..repositories import WarehouseLocalRepo from .base import BaseConverter -from tomlkit.items import Table -from typing import Tuple -from tomlkit.items import InlineTable -from tomlkit.items import String -from typing import Union @attr.s() diff --git a/dephell/converters/poetrylock.py b/dephell/converters/poetrylock.py index 871605fc..b9ebe772 100644 --- a/dephell/converters/poetrylock.py +++ b/dephell/converters/poetrylock.py @@ -9,13 +9,13 @@ from dephell_discover import Root as PackageRoot from dephell_links import DirLink from dephell_specifier import RangeSpecifier +from tomlkit.items import Table # app from ..controllers import DependencyMaker, RepositoriesRegistry -from ..models import Constraint, Dependency, RootDependency, Requirement +from ..models import Constraint, Dependency, Requirement, RootDependency from ..repositories import WarehouseBaseRepo, WarehouseLocalRepo from .base import BaseConverter -from tomlkit.items import Table @attr.s() diff --git a/dephell/models/constraint.py b/dephell/models/constraint.py index 1cf770f3..4c9a3a5f 100644 --- a/dephell/models/constraint.py +++ b/dephell/models/constraint.py @@ -1,11 +1,9 @@ # built-in from copy import deepcopy -from typing import TYPE_CHECKING +from typing import TYPE_CHECKING, Any, Union # external from dephell_specifier import RangeSpecifier -from typing import Any -from typing import Union if TYPE_CHECKING: diff --git a/dephell/models/extra_dependency.py b/dephell/models/extra_dependency.py index 0193d133..7748ef1a 100644 --- a/dephell/models/extra_dependency.py +++ b/dephell/models/extra_dependency.py @@ -1,13 +1,15 @@ # external +# built-in +from typing import Union + import attr from packaging.utils import canonicalize_name +from tomlkit.items import String # app from ..cached_property import cached_property from .dependency import Dependency from .groups import Groups -from tomlkit.items import String -from typing import Union @attr.s(eq=False, order=False) diff --git a/dephell/models/group.py b/dephell/models/group.py index e6d62bfd..273a7a4c 100644 --- a/dephell/models/group.py +++ b/dephell/models/group.py @@ -1,12 +1,10 @@ # built-in from operator import attrgetter -from typing import Optional -from typing import TYPE_CHECKING +from typing import TYPE_CHECKING, Optional, Union # app from ..cached_property import cached_property from ..config import config -from typing import Union if TYPE_CHECKING: diff --git a/dephell/models/groups.py b/dephell/models/groups.py index 7055207a..0ee59019 100644 --- a/dephell/models/groups.py +++ b/dephell/models/groups.py @@ -1,6 +1,6 @@ # built-in import asyncio -from typing import Optional +from typing import Iterator, Optional # external import attr @@ -9,7 +9,6 @@ from ..cached_property import cached_property from ..config import config from .group import Group -from typing import Iterator loop = asyncio.get_event_loop() diff --git a/dephell/models/release.py b/dephell/models/release.py index fd3b73c5..442120da 100644 --- a/dephell/models/release.py +++ b/dephell/models/release.py @@ -1,6 +1,6 @@ # built-in from datetime import datetime -from typing import Optional +from typing import Any, Dict, List, Optional # external import attr @@ -10,9 +10,6 @@ # app from ..cached_property import cached_property -from typing import Any -from typing import Dict -from typing import List @attr.s(hash=False, eq=False, order=False) diff --git a/dephell/models/requirement.py b/dephell/models/requirement.py index 0bd9be65..b81ae885 100644 --- a/dephell/models/requirement.py +++ b/dephell/models/requirement.py @@ -1,6 +1,6 @@ # built-in from collections import OrderedDict, defaultdict -from typing import Iterable, Optional, Set, Tuple, TYPE_CHECKING +from typing import TYPE_CHECKING, Any, Iterable, Iterator, Optional, Set, Tuple # external import attr @@ -8,8 +8,6 @@ # app from ..cached_property import cached_property -from typing import Any -from typing import Iterator if TYPE_CHECKING: diff --git a/dephell/networking.py b/dephell/networking.py index 707f1200..faa91d3c 100644 --- a/dephell/networking.py +++ b/dephell/networking.py @@ -3,19 +3,20 @@ from logging import getLogger from ssl import create_default_context from time import sleep +from typing import Any, Optional # external import certifi import requests from aiohttp import ClientError, ClientSession, TCPConnector +from requests.sessions import Session + +# project +from dephell.models.auth import Auth # app from . import __version__ from .config import config -from typing import Any -from typing import Optional -from dephell.models.auth import Auth -from requests.sessions import Session USER_AGENT = 'DepHell/{version}'.format(version=__version__) diff --git a/dephell/yaml.py b/dephell/yaml.py index fbcac8f3..16e82e04 100644 --- a/dephell/yaml.py +++ b/dephell/yaml.py @@ -1,8 +1,8 @@ # app +# built-in +from typing import Any, Dict, Optional, TextIO + from .imports import lazy_import -from typing import Any -from typing import Dict -from typing import Optional, TextIO ruamel_yaml = lazy_import('ruamel.yaml', package='ruamel.yaml') From b58d7f8c40fb0b2951ceafd4ee372f184c5ca98e Mon Sep 17 00:00:00 2001 From: Gram Date: Fri, 15 May 2020 12:41:45 +0200 Subject: [PATCH 54/80] handle typing in actions --- dephell/actions/_dotenv.py | 2 +- dephell/actions/_downloads.py | 17 +++++++++-------- dephell/actions/_entrypoints.py | 5 +++-- dephell/actions/_json.py | 10 +++++----- dephell/actions/_package.py | 2 +- dephell/actions/_python.py | 16 ++++++++-------- dephell/actions/_transform.py | 5 +---- dephell/models/root.py | 8 ++++++-- pyproject.toml | 2 +- 9 files changed, 35 insertions(+), 32 deletions(-) diff --git a/dephell/actions/_dotenv.py b/dephell/actions/_dotenv.py index 37d368b2..e8b9ba51 100644 --- a/dephell/actions/_dotenv.py +++ b/dephell/actions/_dotenv.py @@ -35,7 +35,7 @@ def read_dotenv(path: Path, env_vars: Dict[str, str] = None) -> Dict[str, str]: # clean and substitute value value = ' '.join(shlex.split(value, comments=True)) value = value.replace(r'\$', '$$') # escaping - value = decode(value, 'unicode-escape') + value = decode(value, 'unicode-escape') # type: ignore if '$' in value: value = Template(value).safe_substitute(env_vars) diff --git a/dephell/actions/_downloads.py b/dephell/actions/_downloads.py index d21cd14f..208c7c11 100644 --- a/dephell/actions/_downloads.py +++ b/dephell/actions/_downloads.py @@ -2,7 +2,7 @@ from collections import defaultdict from datetime import date, timedelta from itertools import zip_longest -from typing import Dict, Iterable, Iterator, List +from typing import Any, DefaultDict, Dict, Sequence, Iterator, List # external import attr @@ -20,9 +20,9 @@ @attr.s() class DateList: - start = attr.ib() - end = attr.ib() - _data = attr.ib(factory=dict, repr=False) + start = attr.ib(type=date) + end = attr.ib(type=date) + _data = attr.ib(factory=dict, repr=False, type=Dict[str, int]) def add(self, date: str, value: int): self._data[date] = value @@ -34,7 +34,7 @@ def __iter__(self) -> Iterator[int]: moment += timedelta(1) -def make_chart(values: Iterable[int], group: int = None, ticks: str = '_▁▂▃▄▅▆▇█') -> str: +def make_chart(values: Sequence[int], group: int = None, ticks: str = '_▁▂▃▄▅▆▇█') -> str: peek = max(values) if peek == 0: chart = ticks[-1] * len(values) @@ -62,7 +62,7 @@ def get_total_downloads(name: str) -> Dict[str, int]: ) -def get_downloads_by_category(*, category: str, name: str) -> List[Dict[str, int]]: +def get_downloads_by_category(*, category: str, name: str) -> List[Dict[str, Any]]: url = CATEGORIES_URLS[category].format(name) with requests_session() as session: response = session.get(url) @@ -70,14 +70,15 @@ def get_downloads_by_category(*, category: str, name: str) -> List[Dict[str, int body = response.json()['data'] yesterday = date.today() - timedelta(1) + grouped: DefaultDict[str, DateList] grouped = defaultdict(lambda: DateList(start=yesterday - timedelta(30), end=yesterday)) for line in body: category = line['category'].replace('.', '') grouped[category].add(date=line['date'], value=line['downloads']) result = [] - for category, downloads in grouped.items(): - downloads = list(downloads) + for category, dates in grouped.items(): + downloads = list(dates) if sum(downloads) == 0: continue result.append(dict( diff --git a/dephell/actions/_entrypoints.py b/dephell/actions/_entrypoints.py index ec1bea23..fd255406 100644 --- a/dephell/actions/_entrypoints.py +++ b/dephell/actions/_entrypoints.py @@ -1,5 +1,6 @@ # built-in from logging import getLogger +from pathlib import Path from typing import Iterable, Optional, Tuple # external @@ -15,7 +16,7 @@ logger = getLogger('dephell.actions') -def _get_matching_path(paths: Iterable, name: str) -> Optional[str]: +def _get_matching_path(paths: Iterable[Path], name: str) -> Optional[Path]: name = canonicalize_name(name) for path in paths: package_name = path.stem.split('-')[0] @@ -55,7 +56,7 @@ def get_entrypoints(*, venv: VEnv, name: str) -> Optional[Tuple[EntryPoint, ...] canonicalize_name(name).replace('_', '-'), canonicalize_name(name).replace('-', '').replace('_', ''), } - paths = (venv.bin_path / name for name in names) + paths = tuple(venv.bin_path / name for name in names) if IS_WINDOWS: paths = tuple(p.with_suffix('.exe') for p in paths) diff --git a/dephell/actions/_json.py b/dephell/actions/_json.py index 65a765f8..cf41ef4d 100644 --- a/dephell/actions/_json.py +++ b/dephell/actions/_json.py @@ -2,7 +2,7 @@ import json from collections import defaultdict from functools import reduce -from typing import Optional +from typing import Optional, Dict, Any # app from ..imports import lazy_import @@ -124,19 +124,19 @@ def _beautify(data, *, colors: bool, table: bool) -> str: ) # list of dicts if isinstance(data, list) and data and isinstance(data[0], dict): - table = [] + result = [] for row in data: row = _flatdict(row) keys = tuple(row) row = [v for _, v in sorted(row.items())] - table.append(row) + result.append(row) return tabulate.tabulate( - table, + result, headers=keys, tablefmt='fancy_grid', ) - json_params = dict(indent=2, sort_keys=True, ensure_ascii=False) + json_params = dict(indent=2, sort_keys=True, ensure_ascii=False) # type: Dict[str, Any] dumped = json.dumps(data, **json_params) if not colors: return dumped diff --git a/dephell/actions/_package.py b/dephell/actions/_package.py index 6d8a88e8..541ee1f9 100644 --- a/dephell/actions/_package.py +++ b/dephell/actions/_package.py @@ -21,6 +21,6 @@ def get_package(req: str, repo: str = None) -> Dependency: return dep -def get_resolver(reqs: Iterable[str] = None) -> Resolver: +def get_resolver(reqs: Iterable[str]) -> Resolver: resolver = PIPConverter(lock=False).loads_resolver('\n'.join(reqs)) return resolver diff --git a/dephell/actions/_python.py b/dephell/actions/_python.py index 9ba0724a..234fd798 100644 --- a/dephell/actions/_python.py +++ b/dephell/actions/_python.py @@ -1,7 +1,7 @@ # built-in import subprocess from pathlib import Path -from typing import Optional +from typing import Optional, Union # external from dephell_pythons import Python, Pythons @@ -62,14 +62,14 @@ def get_lib_path(python_path: Path) -> Optional[Path]: """Find site-packages or dist-packages dir for the given python """ # get user site dir path - user_site = None + user_site = None # type: Union[None, Path] cmd = [str(python_path), '-c', r'print(__import__("site").USER_SITE)'] result = subprocess.run(cmd, stdout=subprocess.PIPE) if result.returncode == 0: - user_site = result.stdout.decode().strip() - if user_site: - user_site = Path(user_site) - if not user_site.exists(): + line = result.stdout.decode().strip() + if line: + user_site = Path(line) + if user_site and user_site.exists(): user_site = None # get sys.path paths @@ -78,8 +78,8 @@ def get_lib_path(python_path: Path) -> Optional[Path]: if result.returncode != 0: return None paths = [] - for path in result.stdout.decode().splitlines(): - path = Path(path) + for line in result.stdout.decode().splitlines(): + path = Path(line) if not path.exists(): continue paths.append(path) diff --git a/dephell/actions/_transform.py b/dephell/actions/_transform.py index a7394c66..7b03c63f 100644 --- a/dephell/actions/_transform.py +++ b/dephell/actions/_transform.py @@ -11,16 +11,13 @@ if TYPE_CHECKING: - import bowler.helpers as bowler_helpers - import fissix.pytree as fissix_pytree from bowler import LN, Capture, Filename, Query - from fissix import fixer_util modifiers = [] -def _register(modifier): +def _register(modifier: type) -> type: modifiers.append(modifier) return modifier diff --git a/dephell/models/root.py b/dephell/models/root.py index c3518a6e..bc8f8d37 100644 --- a/dephell/models/root.py +++ b/dephell/models/root.py @@ -2,7 +2,7 @@ from contextlib import suppress from itertools import chain from pathlib import Path -from typing import Tuple +from typing import List, Tuple, TYPE_CHECKING # external import attr @@ -17,6 +17,10 @@ from .group import Group +if TYPE_CHECKING: + from .dependency import Dependency # noqa: F401 + + @attr.s() class RootRelease: raw_name = attr.ib() @@ -38,7 +42,7 @@ def __str__(self): @attr.s() class RootDependency: raw_name = attr.ib(default='root') - dependencies = attr.ib(factory=list, repr=False) + dependencies = attr.ib(factory=list, repr=False, type=List['Dependency']) repo = attr.ib(default=None, repr=False) # additional info strings diff --git a/pyproject.toml b/pyproject.toml index 343444f5..2fa8bc01 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -33,7 +33,7 @@ command = "flake8" from = {format = "poetry", path = "pyproject.toml"} # mypy isn't specified in dependencies, # but `dephell venv run` command will install it automatically -command = "mypy --ignore-missing-imports --allow-redefinition dephell" +command = "mypy --ignore-missing-imports --allow-redefinition --follow-imports=silent dephell/actions" # Test project package in the separated venv: # $ dephell project test --env=pytest From ce56467bf847af6e9bc2ebb671b618ad27fcf274 Mon Sep 17 00:00:00 2001 From: Gram Date: Fri, 15 May 2020 13:53:40 +0200 Subject: [PATCH 55/80] type check commands --- dephell/actions/_contributing.py | 4 ++-- dephell/actions/_transform.py | 6 +++--- dephell/commands/deps_convert.py | 3 ++- dephell/commands/deps_install.py | 2 +- dephell/commands/deps_tree.py | 2 ++ dephell/commands/inspect_project.py | 3 ++- dephell/commands/jail_try.py | 2 +- dephell/commands/package_show.py | 4 +++- dephell/commands/project_test.py | 22 ++++++++++++---------- dephell/commands/vendor_download.py | 8 ++++---- dephell/commands/vendor_import.py | 4 ---- dephell/commands/venv_run.py | 4 ++-- dephell/models/dependency.py | 7 ++++--- pyproject.toml | 2 +- 14 files changed, 39 insertions(+), 34 deletions(-) diff --git a/dephell/actions/_contributing.py b/dephell/actions/_contributing.py index baddb5ba..e7c1b0b2 100644 --- a/dephell/actions/_contributing.py +++ b/dephell/actions/_contributing.py @@ -1,6 +1,6 @@ # built-in from pathlib import Path -from typing import Any, Dict, Optional +from typing import Any, Dict # external from jinja2 import Environment, PackageLoader @@ -29,7 +29,7 @@ ) -def make_contributing(config: Dict[str, Dict[str, Any]], project_path: Path) -> Optional[str]: +def make_contributing(config: Dict[str, Dict[str, Any]], project_path: Path) -> str: template = env.get_template('contributing.md.j2') envs = dict() for name, category in KNOWN_SECTIONS: diff --git a/dephell/actions/_transform.py b/dephell/actions/_transform.py index 7b03c63f..6b0c935c 100644 --- a/dephell/actions/_transform.py +++ b/dephell/actions/_transform.py @@ -195,7 +195,7 @@ class DottedModuleImportModifier: ) """ - def __init__(self, old_name, new_name): + def __init__(self, old_name: str, new_name: str) -> None: self.old_name = old_name self.new_name = new_name @@ -205,7 +205,7 @@ def __call__(self, node: 'LN', capture: 'Capture', filename: 'Filename') -> None else: self._modify_import(capture) - def _modify_import(self, capture): + def _modify_import(self, capture) -> None: new_name_node = build_new_name_node( old_node=capture['module_name'], new_name=self.new_name, @@ -214,7 +214,7 @@ def _modify_import(self, capture): ) capture['module_name'].replace(new_name_node) - def _modify_power(self, node): + def _modify_power(self, node: 'LN') -> None: prefix = node.children[0].prefix # remove old prefix diff --git a/dephell/commands/deps_convert.py b/dephell/commands/deps_convert.py index 0612f1ed..82b06798 100644 --- a/dephell/commands/deps_convert.py +++ b/dephell/commands/deps_convert.py @@ -1,6 +1,7 @@ # built-in from argparse import ArgumentParser from pathlib import Path +from typing import Dict, Any # app from ..actions import attach_deps @@ -84,7 +85,7 @@ def __call__(self) -> bool: dumper_kwargs = dict( reqs=Requirement.from_graph(resolver.graph, lock=dumper.lock), project=resolver.graph.metainfo, - ) + ) # type: Dict[str, Any] if self.config['to']['path'] == 'stdout': print(dumper.dumps(**dumper_kwargs)) else: diff --git a/dephell/commands/deps_install.py b/dephell/commands/deps_install.py index e84b771e..7893e447 100644 --- a/dephell/commands/deps_install.py +++ b/dephell/commands/deps_install.py @@ -97,6 +97,6 @@ def _get_install_remove(self, graph, python) -> Tuple[list, list]: # remove packages not in graph if self.sync: names = set(installed) - {req.name for req in reqs} - remove.extend(SimpleNamespace(name=name) for name in names) + remove.extend(SimpleNamespace(name=name) for name in names) # type: ignore return install, remove diff --git a/dephell/commands/deps_tree.py b/dephell/commands/deps_tree.py index b2eaac03..26e1675a 100644 --- a/dephell/commands/deps_tree.py +++ b/dephell/commands/deps_tree.py @@ -64,6 +64,8 @@ def __call__(self) -> bool: self.logger.info('graph saved into .dephell_report/') return True + raise RuntimeError('unreachable') + @classmethod def _make_tree(cls, dep, *, level: int = 0) -> List[str]: best = dep.group.best_release.version diff --git a/dephell/commands/inspect_project.py b/dephell/commands/inspect_project.py index b5fa79ce..c53ce71b 100644 --- a/dephell/commands/inspect_project.py +++ b/dephell/commands/inspect_project.py @@ -1,6 +1,7 @@ # built-in from argparse import ArgumentParser from pathlib import Path +from typing import Any, Dict # app from ..actions import make_json @@ -34,7 +35,7 @@ def __call__(self) -> bool: name=root.raw_name, version=root.version, description=root.description, - ) + ) # type: Dict[str, Any] if root.python: result['python'] = str(root.python) if root.links: diff --git a/dephell/commands/jail_try.py b/dephell/commands/jail_try.py index 1ae366c7..9e878f60 100644 --- a/dephell/commands/jail_try.py +++ b/dephell/commands/jail_try.py @@ -41,7 +41,7 @@ def __call__(self) -> bool: if isinstance(command, str): command = shlex.split(command) - with TemporaryDirectory() as base_path: + with TemporaryDirectory() as base_path: # type: Path # type: ignore base_path = Path(base_path) # make venv diff --git a/dephell/commands/package_show.py b/dephell/commands/package_show.py index cf2bb31f..4c3a30f5 100644 --- a/dephell/commands/package_show.py +++ b/dephell/commands/package_show.py @@ -1,5 +1,7 @@ # built-in from argparse import ArgumentParser +from pathlib import Path +from typing import List # app from ..actions import format_size, get_package, get_path_size, get_python_env, make_json @@ -30,7 +32,7 @@ def __call__(self) -> bool: root = InstalledConverter().load(paths=python.lib_paths, names={self.args.name}) local_versions = [] - local_places = [] + local_places = [] # type: List[Path] for subdep in root.dependencies: if subdep.name == dep.name: local_versions = str(subdep.constraint).replace('=', '').split(' || ') diff --git a/dephell/commands/project_test.py b/dephell/commands/project_test.py index 607555ff..6e3e334c 100644 --- a/dephell/commands/project_test.py +++ b/dephell/commands/project_test.py @@ -5,9 +5,10 @@ from argparse import REMAINDER, ArgumentParser from pathlib import Path from tempfile import TemporaryDirectory +from typing import Dict, Tuple # external -from dephell_pythons import Pythons +from dephell_pythons import Pythons, Python from dephell_venvs import VEnv # app @@ -70,25 +71,26 @@ def __call__(self) -> bool: # choose pythons self.logger.info('get interpreters') pythons = Pythons() + choosen_pythons: Tuple[Python, ...] if 'python' in self.config: # get from config choosen_pythons = (pythons.get_best(self.config['python']), ) else: # get from project - choosen_pythons = dict() - pyrhon_constraint = resolver.graph.metainfo.python + pythons_by_version = dict() # type: Dict[str, Python] + python_constraint = resolver.graph.metainfo.python for python in pythons: version = str(python.get_short_version()) - if version in choosen_pythons: + if version in pythons_by_version: continue - if python.version not in pyrhon_constraint: + if python.version not in python_constraint: continue - choosen_pythons[version] = python - choosen_pythons = tuple(choosen_pythons.values()) + pythons_by_version[version] = python + choosen_pythons = tuple(pythons_by_version.values()) for python in choosen_pythons: - with TemporaryDirectory() as path: - root_path = Path(path) + with TemporaryDirectory() as root_path: # type: Path # type: ignore + root_path = Path(root_path) # make venv self.logger.info('create venv', extra=dict(python=str(python.version))) @@ -96,7 +98,7 @@ def __call__(self) -> bool: venv.create(python_path=python.path) # copy tests - for path in self.config['tests']: + for path in self.config['tests']: # type: Path # type: ignore self.logger.info('copy files', extra=dict(path=path)) path = Path(path) if not path.exists(): diff --git a/dephell/commands/vendor_download.py b/dephell/commands/vendor_download.py index 14e65bab..0b993124 100644 --- a/dephell/commands/vendor_download.py +++ b/dephell/commands/vendor_download.py @@ -45,7 +45,7 @@ def __call__(self) -> bool: def _download_packages(self, resolver, output_path: Path, exclude: Iterable[str] = None) -> int: exclude = set(exclude or []) - with TemporaryDirectory() as archives_path: + with TemporaryDirectory() as archives_path: # type: Path # type: ignore archives_path = Path(archives_path) loop = asyncio.get_event_loop() @@ -74,14 +74,14 @@ def _download_packages(self, resolver, output_path: Path, def _extract_modules(self, dep, archive_path: Path, output_path: Path) -> bool: # say to shutils that wheel can be parsed as zip - if 'wheel' not in shutil._UNPACK_FORMATS: + if 'wheel' not in shutil._UNPACK_FORMATS: # type: ignore shutil.register_unpack_format( name='wheel', extensions=['.whl'], - function=shutil._unpack_zipfile, + function=shutil._unpack_zipfile, # type: ignore ) - with TemporaryDirectory(suffix=dep.name) as package_path: + with TemporaryDirectory(suffix=dep.name) as package_path: # type: Path # type: ignore package_path = Path(package_path) shutil.unpack_archive(str(archive_path), str(package_path)) if len(list(package_path.iterdir())) == 1: diff --git a/dephell/commands/vendor_import.py b/dephell/commands/vendor_import.py index 7cf683b2..28fa352a 100644 --- a/dephell/commands/vendor_import.py +++ b/dephell/commands/vendor_import.py @@ -1,7 +1,6 @@ # built-in from argparse import ArgumentParser from pathlib import Path -from typing import TYPE_CHECKING # app from ..actions import transform_imports @@ -12,9 +11,6 @@ bowler = lazy_import('bowler') -if TYPE_CHECKING: - import bowler - class VendorImportCommand(BaseCommand): """Patch all imports in project to use vendored dependencies. diff --git a/dephell/commands/venv_run.py b/dephell/commands/venv_run.py index d3adf082..47f9c587 100644 --- a/dephell/commands/venv_run.py +++ b/dephell/commands/venv_run.py @@ -59,13 +59,13 @@ def __call__(self) -> bool: self.logger.warning('executable is not found in venv, trying to install...', extra=dict( executable=command[0], )) - result = install_dep( + installed = install_dep( name=command[0], python_path=venv.python_path, logger=self.logger, silent=self.config['silent'], ) - if not result: + if not installed: return False if not executable.exists(): self.logger.error('package installed, but executable is not found') diff --git a/dephell/models/dependency.py b/dephell/models/dependency.py index 94e7bfbc..fded56a9 100644 --- a/dephell/models/dependency.py +++ b/dephell/models/dependency.py @@ -1,6 +1,7 @@ # built-in from copy import deepcopy -from typing import Tuple +from pathlib import Path +from typing import Dict, Set, Tuple # external import attr @@ -29,7 +30,7 @@ class Dependency: # optional info description = attr.ib(type=str, default='', repr=False) # summary authors = attr.ib(factory=tuple, repr=False) # author{,_email}, maintainer{,_email} - links = attr.ib(factory=dict, repr=False) # project_url{,s}, package_url + links = attr.ib(factory=Dict[str, str], repr=False) # project_url{,s}, package_url classifiers = attr.ib(type=tuple, factory=tuple, repr=False) # classifiers license = attr.ib(default=None, repr=False) # license @@ -40,7 +41,7 @@ class Dependency: marker = attr.ib(type=MarkerTracker, factory=MarkerTracker, repr=False) envs = attr.ib(type=set, factory=set, repr=False) # which root extras cause this dep inherited_envs = attr.ib(type=set, factory=set, repr=False) # envs of parents - locations = attr.ib(type=set, factory=set, repr=False) # package places on disk + locations = attr.ib(type=Set[Path], factory=set, repr=False) # package places on disk extra = None diff --git a/pyproject.toml b/pyproject.toml index 2fa8bc01..63d31b58 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -33,7 +33,7 @@ command = "flake8" from = {format = "poetry", path = "pyproject.toml"} # mypy isn't specified in dependencies, # but `dephell venv run` command will install it automatically -command = "mypy --ignore-missing-imports --allow-redefinition --follow-imports=silent dephell/actions" +command = "mypy --ignore-missing-imports --allow-redefinition --follow-imports=silent dephell/actions dephell/commands" # Test project package in the separated venv: # $ dephell project test --env=pytest From ed9ab5eb3f0b2e2c78798246c59368274465d917 Mon Sep 17 00:00:00 2001 From: Gram Date: Fri, 15 May 2020 14:46:13 +0200 Subject: [PATCH 56/80] fix --- dephell/models/dependency.py | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/dephell/models/dependency.py b/dephell/models/dependency.py index fded56a9..669454dd 100644 --- a/dephell/models/dependency.py +++ b/dephell/models/dependency.py @@ -28,11 +28,11 @@ class Dependency: applied = attr.ib(type=bool, default=False, repr=False) # optional info - description = attr.ib(type=str, default='', repr=False) # summary - authors = attr.ib(factory=tuple, repr=False) # author{,_email}, maintainer{,_email} - links = attr.ib(factory=Dict[str, str], repr=False) # project_url{,s}, package_url - classifiers = attr.ib(type=tuple, factory=tuple, repr=False) # classifiers - license = attr.ib(default=None, repr=False) # license + description = attr.ib(type=str, default='', repr=False) # summary + authors = attr.ib(factory=tuple, repr=False) # author{,_email}, maintainer{,_email} + links = attr.ib(factory=dict, type=Dict[str, str], repr=False) # project_url{,s}, package_url + classifiers = attr.ib(type=tuple, factory=tuple, repr=False) # classifiers + license = attr.ib(default=None, repr=False) # license # info from requirements file editable = attr.ib(type=bool, default=False, repr=False) From 890a8bdc88e6d36e56698797e62762a709caa582 Mon Sep 17 00:00:00 2001 From: Gram Date: Fri, 15 May 2020 15:05:42 +0200 Subject: [PATCH 57/80] fix flake8 --- dephell/models/constraint.py | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/dephell/models/constraint.py b/dephell/models/constraint.py index 4c9a3a5f..a76a7e39 100644 --- a/dephell/models/constraint.py +++ b/dephell/models/constraint.py @@ -7,9 +7,9 @@ if TYPE_CHECKING: - from .dependency import Dependency - from .extra_dependency import ExtraDependency - from .root import RootDependency + from .dependency import Dependency # noqa: F401 + from .extra_dependency import ExtraDependency # noqa: F401 + from .root import RootDependency # noqa: F401 class Constraint: From a0c30fbd740b608050acddf67a07bf0c0a6322d2 Mon Sep 17 00:00:00 2001 From: Gram Date: Fri, 15 May 2020 15:05:58 +0200 Subject: [PATCH 58/80] sort imports --- dephell/actions/_downloads.py | 2 +- dephell/actions/_json.py | 2 +- dephell/commands/deps_convert.py | 2 +- dephell/commands/project_test.py | 2 +- dephell/models/root.py | 2 +- 5 files changed, 5 insertions(+), 5 deletions(-) diff --git a/dephell/actions/_downloads.py b/dephell/actions/_downloads.py index 208c7c11..9ee4d8ba 100644 --- a/dephell/actions/_downloads.py +++ b/dephell/actions/_downloads.py @@ -2,7 +2,7 @@ from collections import defaultdict from datetime import date, timedelta from itertools import zip_longest -from typing import Any, DefaultDict, Dict, Sequence, Iterator, List +from typing import Any, DefaultDict, Dict, Iterator, List, Sequence # external import attr diff --git a/dephell/actions/_json.py b/dephell/actions/_json.py index cf41ef4d..5627010d 100644 --- a/dephell/actions/_json.py +++ b/dephell/actions/_json.py @@ -2,7 +2,7 @@ import json from collections import defaultdict from functools import reduce -from typing import Optional, Dict, Any +from typing import Any, Dict, Optional # app from ..imports import lazy_import diff --git a/dephell/commands/deps_convert.py b/dephell/commands/deps_convert.py index 82b06798..d0711492 100644 --- a/dephell/commands/deps_convert.py +++ b/dephell/commands/deps_convert.py @@ -1,7 +1,7 @@ # built-in from argparse import ArgumentParser from pathlib import Path -from typing import Dict, Any +from typing import Any, Dict # app from ..actions import attach_deps diff --git a/dephell/commands/project_test.py b/dephell/commands/project_test.py index 6e3e334c..bfcefe23 100644 --- a/dephell/commands/project_test.py +++ b/dephell/commands/project_test.py @@ -8,7 +8,7 @@ from typing import Dict, Tuple # external -from dephell_pythons import Pythons, Python +from dephell_pythons import Python, Pythons from dephell_venvs import VEnv # app diff --git a/dephell/models/root.py b/dephell/models/root.py index bc8f8d37..f609654a 100644 --- a/dephell/models/root.py +++ b/dephell/models/root.py @@ -2,7 +2,7 @@ from contextlib import suppress from itertools import chain from pathlib import Path -from typing import List, Tuple, TYPE_CHECKING +from typing import TYPE_CHECKING, List, Tuple # external import attr From 4114ecc636f0d21b9cd616105301308c0337b1cf Mon Sep 17 00:00:00 2001 From: Gram Date: Fri, 15 May 2020 15:09:53 +0200 Subject: [PATCH 59/80] fix markdown lint --- .travis.yml | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/.travis.yml b/.travis.yml index 0571f245..325e6eea 100644 --- a/.travis.yml +++ b/.travis.yml @@ -51,7 +51,8 @@ matrix: # https://github.com/igorshubovych/markdownlint-cli - name: markdown lint - language: generic + language: node_js + node_js: "14" install: - npm install -g markdownlint-cli script: From cdf7e050f9c057220cb99be7ecad0d8b35407f8e Mon Sep 17 00:00:00 2001 From: Gram Date: Fri, 15 May 2020 15:10:17 +0200 Subject: [PATCH 60/80] run type checks on ci --- .travis.yml | 3 +++ 1 file changed, 3 insertions(+) diff --git a/.travis.yml b/.travis.yml index 325e6eea..4d2a78a3 100644 --- a/.travis.yml +++ b/.travis.yml @@ -67,6 +67,9 @@ matrix: - python: "3.7" env: ENV=flake8 + - python: "3.7" + env: ENV=typing + - python: "3.7" env: ENV=isort script: From 36383f982303904f499981651cc6769ed4d6ccca Mon Sep 17 00:00:00 2001 From: Gram Date: Fri, 15 May 2020 15:19:54 +0200 Subject: [PATCH 61/80] make markdown lint on ci faster --- .travis.yml | 2 ++ 1 file changed, 2 insertions(+) diff --git a/.travis.yml b/.travis.yml index 4d2a78a3..2e2647d7 100644 --- a/.travis.yml +++ b/.travis.yml @@ -53,6 +53,8 @@ matrix: - name: markdown lint language: node_js node_js: "14" + before_install: + - true install: - npm install -g markdownlint-cli script: From fbf738cd3c4db73fa3e6932daaa35b39858b03e1 Mon Sep 17 00:00:00 2001 From: Adam Wallis Date: Tue, 19 May 2020 14:52:05 -0400 Subject: [PATCH 62/80] Safely test for optional "type" field in poetry lock The "source" field in a poetry lock file can optionally have a "type" field. However, in cases where an alternative "simple" index is offered, e.g., artifactory, this type field is not used. This patch makes checking this type field safe by returning a None in the case that the field doesn't exist. Fixes: https://github.com/dephell/dephell/issues/437 --- dephell/converters/poetrylock.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/dephell/converters/poetrylock.py b/dephell/converters/poetrylock.py index b9ebe772..bb267df0 100644 --- a/dephell/converters/poetrylock.py +++ b/dephell/converters/poetrylock.py @@ -118,12 +118,12 @@ def _make_deps(cls, root, content, envs, repo) -> List[Dependency]: # get link url = None if 'source' in content: - if content['source']['type'] == 'legacy': + if content['source'].get('type') == 'legacy': repo = repo.make(content['source']['reference']) else: repo = None url = content['source']['url'] - if content['source']['type'] == 'git': + if content['source'].get('type') == 'git': url = 'git+' + url if 'reference' in content['source']: url += '@' + content['source']['reference'] From 73f18e80b59e3069c07ee1cbb3ab21d793607ce8 Mon Sep 17 00:00:00 2001 From: Gram Date: Tue, 2 Jun 2020 14:23:19 +0200 Subject: [PATCH 63/80] Fix markers merging When we merge markers for dependency from different sources and one source has an empty marker specified, convert it to empty markers after all. In other words, if a library has a dependency without markers specified that means "always install the dependency, no markers should be applied" --- dephell/models/marker_tracker.py | 30 +++++++++++++++++++++--------- 1 file changed, 21 insertions(+), 9 deletions(-) diff --git a/dephell/models/marker_tracker.py b/dephell/models/marker_tracker.py index 3d0d443e..a28f33ec 100644 --- a/dephell/models/marker_tracker.py +++ b/dephell/models/marker_tracker.py @@ -1,30 +1,42 @@ +from typing import Dict, Union + # external from dephell_markers import Markers, OrMarker class MarkerTracker: + _markers: Dict[str, Markers] + def __init__(self) -> None: self._markers = dict() @property def markers(self) -> Markers: + container = Markers() + + if not self._markers: + return container if len(self._markers) == 1: return next(iter(self._markers.values())) - container = Markers() - markers = [m._marker for m in self._markers.values() if m._marker] + + # Empty marker means "no markers should be applied, always match the dependency". + for marker in self._markers.values(): + if not marker: + return container + + # If no empty markers specified, merge all markers as `or` + markers = [m._marker for m in self._markers.values()] container._marker = OrMarker(*markers) return container - def apply(self, *, source, markers) -> 'MarkerTracker': - if not markers: - return self + def apply(self, *, source, markers: Union[str, Markers]) -> 'MarkerTracker': if type(source) is not str: source = source.name if source in self._markers: raise ValueError('marker for given source already added') if type(markers) is str: markers = Markers(markers) - self._markers[source] = markers + self._markers[source] = markers # type: ignore return self def merge(self, other: 'MarkerTracker') -> None: @@ -37,17 +49,17 @@ def unapply(self, source) -> None: if source in self._markers: del self._markers[source] - def __getattr__(self, name): + def __getattr__(self, name: str): if name not in dir(Markers): raise AttributeError(name) return getattr(self.markers, name) def __bool__(self) -> bool: - return any(marker for marker in self._markers.values()) + return bool(self.markers) def __str__(self) -> str: return str(self.markers) - def __repr__(self): + def __repr__(self) -> str: markers = map(repr, self._markers.values()) return '{}({})'.format(type(self).__name__, ', '.join(markers)) From 4aae2c055396052fa730cd737d18dbc27089c0b6 Mon Sep 17 00:00:00 2001 From: Gram Date: Tue, 2 Jun 2020 15:31:35 +0200 Subject: [PATCH 64/80] check and fix types in config --- dephell/config/logging_config.py | 5 ++++- dephell/config/manager.py | 38 ++++++++++++++++++++++---------- pyproject.toml | 2 +- 3 files changed, 31 insertions(+), 14 deletions(-) diff --git a/dephell/config/logging_config.py b/dephell/config/logging_config.py index e51193ef..be6a1ba4 100644 --- a/dephell/config/logging_config.py +++ b/dephell/config/logging_config.py @@ -1,4 +1,7 @@ -LOGGING = { +from typing import Any, Dict + + +LOGGING: Dict[str, Any] = { 'version': 1, 'disable_existing_loggers': False, 'filters': { diff --git a/dephell/config/manager.py b/dephell/config/manager.py index 4d1cc386..18e7513a 100644 --- a/dephell/config/manager.py +++ b/dephell/config/manager.py @@ -8,7 +8,7 @@ from logging.config import dictConfig from os import environ from pathlib import Path -from typing import Dict, Optional +from typing import Any, DefaultDict, Dict, Optional # external import tomlkit @@ -36,12 +36,12 @@ class Config: def __init__(self, data: Optional[dict] = None): self._data = data or deepcopy(DEFAULT) - def setup_logging(self, data: Optional[dict] = None) -> None: + def setup_logging(self, data: Optional[Dict[str, Any]] = None) -> None: captureWarnings(True) if data is None: data = LOGGING if self._data: - data['loggers']['dephell']['level'] = self['level'] + data['loggers']['dephell']['level'] = self._data['level'] for formatter in data['formatters'].values(): formatter['colors'] = not self['nocolors'] formatter['traceback'] = self['traceback'] @@ -49,7 +49,11 @@ def setup_logging(self, data: Optional[dict] = None) -> None: handler['formatter'] = self['format'] dictConfig(LOGGING) - def attach(self, data: dict, container: Optional[dict] = None) -> None: + def attach(self, data: Dict[str, Any], container: Optional[Dict[str, Any]] = None) -> None: + """Merge `data` into `container`. + + If no container specified, merge into the current config. + """ if container is None: container = self._data @@ -70,12 +74,20 @@ def attach(self, data: dict, container: Optional[dict] = None) -> None: new_value.append(subvalue) value = new_value + # add a new value into the container if key not in container: container[key] = value - elif isinstance(value, dict): - self.attach(data=value, container=container[key]) - else: - container[key] = value + continue + + # merge dicts + if isinstance(value, dict): + subcontainer = container[key] + if isinstance(subcontainer, dict): + self.attach(data=value, container=subcontainer) + continue + + # overwrite the current value + container[key] = value @staticmethod def _expand_converter(text: str) -> Dict[str, str]: @@ -128,8 +140,8 @@ def attach_file(self, path: str, env: str, silent: bool = False) -> Optional[dic self.env = env return data - def attach_cli(self, args, sep: str = '_') -> dict: - data = defaultdict(dict) + def attach_cli(self, args, sep: str = '_') -> Dict[str, Any]: + data = defaultdict(dict) # type: DefaultDict[str, Any] for name, value in args._get_kwargs(): if value is None or value is False: continue @@ -144,8 +156,10 @@ def attach_cli(self, args, sep: str = '_') -> dict: self.attach(data) return dict(data) - def attach_env_vars(self, *, env_vars: Dict[str, str] = environ, sep: str = '_') -> dict: - data = defaultdict(dict) + def attach_env_vars(self, *, env_vars: Dict[str, str] = None, sep: str = '_') -> dict: + if env_vars is None: + env_vars = dict(environ) + data = defaultdict(dict) # type: DefaultDict[str, Any] for name, value in env_vars.items(): # drop templated part from name match = ENV_VAR_REX.fullmatch(name) diff --git a/pyproject.toml b/pyproject.toml index 63d31b58..10655084 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -33,7 +33,7 @@ command = "flake8" from = {format = "poetry", path = "pyproject.toml"} # mypy isn't specified in dependencies, # but `dephell venv run` command will install it automatically -command = "mypy --ignore-missing-imports --allow-redefinition --follow-imports=silent dephell/actions dephell/commands" +command = "mypy --ignore-missing-imports --allow-redefinition --follow-imports=silent dephell/actions dephell/commands dephell/config" # Test project package in the separated venv: # $ dephell project test --env=pytest From d525ba50b1ee7dfedad1bc39a703a50c427e77e8 Mon Sep 17 00:00:00 2001 From: Gram Date: Tue, 2 Jun 2020 15:33:09 +0200 Subject: [PATCH 65/80] include yaml in type tests --- dephell/yaml.py | 8 ++++---- pyproject.toml | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/dephell/yaml.py b/dephell/yaml.py index 16e82e04..4cce3ee3 100644 --- a/dephell/yaml.py +++ b/dephell/yaml.py @@ -1,6 +1,6 @@ # app # built-in -from typing import Any, Dict, Optional, TextIO +from typing import Any, Dict, TextIO from .imports import lazy_import @@ -9,7 +9,7 @@ py_yaml = lazy_import('yaml', package='PyYAML') -def yaml_load(stream, *, safe: bool = True): +def yaml_load(stream: TextIO, *, safe: bool = True): if safe: parser = ruamel_yaml.YAML(typ='safe') else: @@ -27,6 +27,6 @@ def yaml_load(stream, *, safe: bool = True): return py_yaml.load(stream) -def yaml_dump(data: Dict[str, Any], stream: TextIO) -> Optional[Any]: +def yaml_dump(data: Dict[str, Any], stream: TextIO): parser = ruamel_yaml.YAML() - return parser.dump(data, stream) + parser.dump(data, stream) diff --git a/pyproject.toml b/pyproject.toml index 10655084..85cdb3b0 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -33,7 +33,7 @@ command = "flake8" from = {format = "poetry", path = "pyproject.toml"} # mypy isn't specified in dependencies, # but `dephell venv run` command will install it automatically -command = "mypy --ignore-missing-imports --allow-redefinition --follow-imports=silent dephell/actions dephell/commands dephell/config" +command = "mypy --ignore-missing-imports --allow-redefinition --follow-imports=silent dephell/actions dephell/commands dephell/config dephell/yaml.py" # Test project package in the separated venv: # $ dephell project test --env=pytest From 3dfc37b970733e28b3d7b5cb8cbee5368ac2f122 Mon Sep 17 00:00:00 2001 From: Gram Date: Tue, 2 Jun 2020 15:41:57 +0200 Subject: [PATCH 66/80] allow `command` to be a list --- dephell/config/scheme.py | 10 ++++++++-- pyproject.toml | 6 +++++- 2 files changed, 13 insertions(+), 3 deletions(-) diff --git a/dephell/config/scheme.py b/dephell/config/scheme.py index 9fe30653..51b7eae5 100644 --- a/dephell/config/scheme.py +++ b/dephell/config/scheme.py @@ -119,8 +119,14 @@ 'envs': dict(type='list', schema=dict(type='string'), required=False, empty=False), 'tests': dict(type='list', schema=dict(type='string'), required=True), 'versioning': dict(type='string', required=True, allowed=get_schemes()), - 'command': dict(type='string', required=False), - 'vendor': dict( + 'command': dict( + anyof=[ + dict(type='string'), + dict(type='list', schema=dict(type='string')), + ], + required=False, + ), + 'vendor': dict( type='dict', required=True, schema={ diff --git a/pyproject.toml b/pyproject.toml index 85cdb3b0..909510d2 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -33,7 +33,11 @@ command = "flake8" from = {format = "poetry", path = "pyproject.toml"} # mypy isn't specified in dependencies, # but `dephell venv run` command will install it automatically -command = "mypy --ignore-missing-imports --allow-redefinition --follow-imports=silent dephell/actions dephell/commands dephell/config dephell/yaml.py" +command = [ + "mypy", + "--ignore-missing-imports", "--allow-redefinition", "--follow-imports=silent", + "dephell/actions", "dephell/commands", "dephell/config", "dephell/yaml.py" +] # Test project package in the separated venv: # $ dephell project test --env=pytest From 47b1d652a595d866389ecd1b37f503a614aee71c Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 24 Aug 2020 12:10:28 +0200 Subject: [PATCH 67/80] Fix site-packages lookup --- dephell/actions/_python.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/dephell/actions/_python.py b/dephell/actions/_python.py index 234fd798..b557dfa8 100644 --- a/dephell/actions/_python.py +++ b/dephell/actions/_python.py @@ -69,7 +69,7 @@ def get_lib_path(python_path: Path) -> Optional[Path]: line = result.stdout.decode().strip() if line: user_site = Path(line) - if user_site and user_site.exists(): + if user_site and not user_site.exists(): user_site = None # get sys.path paths From 1148341ab4d83d68dd300910fa420c8d191e8fb2 Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 24 Aug 2020 12:13:07 +0200 Subject: [PATCH 68/80] Fix Travis CI python path --- .travis.yml | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/.travis.yml b/.travis.yml index 2e2647d7..e3a09948 100644 --- a/.travis.yml +++ b/.travis.yml @@ -15,7 +15,7 @@ before_install: # - curl https://raw.githubusercontent.com/dephell/dephell/master/install.py | /opt/python/3.6/bin/python # https://github.com/travis-ci/travis-ci/issues/8589 - > - /opt/python/3.7/bin/python install.py + /opt/python/3.7.1/bin/python install.py --branch=${TRAVIS_PULL_REQUEST_BRANCH:-$TRAVIS_BRANCH} --slug=${TRAVIS_PULL_REQUEST_SLUG:-dephell/dephell} - dephell inspect self @@ -29,7 +29,7 @@ matrix: include: - python: "3.6.7" env: ENV=pytest - - python: "3.7" + - python: "3.7.1" env: ENV=pytest - python: "3.8" env: ENV=pytest @@ -61,27 +61,27 @@ matrix: - bash -c "markdownlint --config markdownlint.json **/*.md" - name: offline - python: "3.7" + python: "3.7.1" env: ENV=pytest script: - dephell venv run --env=$ENV pytest --no-network tests/ - - python: "3.7" + - python: "3.7.1" env: ENV=flake8 - - python: "3.7" + - python: "3.7.1" env: ENV=typing - - python: "3.7" + - python: "3.7.1" env: ENV=isort script: - dephell venv run --env=$ENV flake8 - - python: "3.7" + - python: "3.7.1" env: ENV=docs - name: poetry - python: "3.7" + python: "3.7.1" env: ENV=main before_install: - pip install poetry From b34011c04e49562b5afe3e946f01024ad5629ac1 Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 24 Aug 2020 12:28:51 +0200 Subject: [PATCH 69/80] fix failing tests --- tests/test_actions/test_entrypoints.py | 3 ++- tests/test_repositories/test_conda.py | 4 ++++ 2 files changed, 6 insertions(+), 1 deletion(-) diff --git a/tests/test_actions/test_entrypoints.py b/tests/test_actions/test_entrypoints.py index 0bef4490..0a4cd320 100644 --- a/tests/test_actions/test_entrypoints.py +++ b/tests/test_actions/test_entrypoints.py @@ -38,4 +38,5 @@ class FakeVenv: entrypoints = get_entrypoints(venv=FakeVenv, name='pytest') assert len(entrypoints) == 2 assert {e.name for e in entrypoints} == {'pytest', 'py.test'} - assert {e.path for e in entrypoints} == {'pytest:main'} + exp = ({'pytest:main'}, {'pytest:console_main'}) + assert {e.path for e in entrypoints} in exp diff --git a/tests/test_repositories/test_conda.py b/tests/test_repositories/test_conda.py index 2c4fb048..94aeeac0 100644 --- a/tests/test_repositories/test_conda.py +++ b/tests/test_repositories/test_conda.py @@ -10,6 +10,7 @@ from dephell.repositories import CondaCloudRepo, CondaGitRepo, CondaRepo +@pytest.mark.xfail(reason='conda.anaconda.org is dead') @pytest.mark.allow_hosts() @pytest.mark.parametrize('repo_class', [CondaRepo, CondaCloudRepo]) def test_conda_get_releases(repo_class): @@ -21,6 +22,7 @@ def test_conda_get_releases(repo_class): assert not {'3.0.3', '3.1.0', '4.0.0', '4.1.0'} - versions +@pytest.mark.xfail(reason='conda.anaconda.org is dead') @pytest.mark.allow_hosts() @pytest.mark.skipif('TRAVIS_OS_NAME' in environ, reason='Travis CI usually out of rate for Github') def test_conda_get_releases_git(): @@ -32,6 +34,7 @@ def test_conda_get_releases_git(): assert not {'3.0.3', '3.1.0', '4.0.0', '4.1.0'} - versions +@pytest.mark.xfail(reason='conda.anaconda.org is dead') @pytest.mark.allow_hosts() @pytest.mark.parametrize('repo_class', [CondaRepo, CondaCloudRepo]) def test_conda_deps(repo_class): @@ -43,6 +46,7 @@ def test_conda_deps(repo_class): assert 'prodigal' in deps +@pytest.mark.xfail(reason='conda.anaconda.org is dead') @pytest.mark.allow_hosts() @pytest.mark.skipif('TRAVIS_OS_NAME' in environ, reason='Travis CI usually out of rate for Github') def test_conda_deps_git(): From bef3f03cd8513b457c0b92aa8f3b60cc645cf717 Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 24 Aug 2020 12:42:26 +0200 Subject: [PATCH 70/80] make ruamel.yaml optional --- pyproject.toml | 6 +++++- setup.py | 6 ++---- 2 files changed, 7 insertions(+), 5 deletions(-) diff --git a/pyproject.toml b/pyproject.toml index 909510d2..c8eada34 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -205,4 +205,8 @@ isort = {extras = ["pyproject"], version = "*"} [tool.poetry.extras] docs = ["alabaster", "pygments-github-lexers", "recommonmark", "sphinx"] tests = ["aioresponses", "pytest", "requests-mock"] -full = ["aiofiles", "appdirs", "autopep8", "bowler", "colorama", "docker", "dockerpty", "fissix", "graphviz", "html5lib", "pygments", "python-gnupg", "tabulate", "yapf"] +full = [ + "aiofiles", "appdirs", "autopep8", "bowler", "colorama", "docker", "dockerpty", + "fissix", "graphviz", "html5lib", "pygments", "python-gnupg", "ruamel.yaml", + "tabulate", "yapf", +] diff --git a/setup.py b/setup.py index 2db62868..8223777d 100644 --- a/setup.py +++ b/setup.py @@ -9,10 +9,8 @@ except ImportError: from distutils.core import setup -# built-in import os.path - readme = '' here = os.path.abspath(os.path.dirname(__file__)) readme_path = os.path.join(here, 'README.rst') @@ -64,7 +62,7 @@ 'dephell-setuptools>=0.2.1', 'dephell-shells>=0.1.3', 'dephell-specifier>=0.1.7', 'dephell-venvs>=0.1.16', 'dephell-versioning', 'jinja2', 'm2r', 'packaging', - 'pip<=19.3.1,>=18.0', 'requests', 'ruamel.yaml', 'tomlkit', 'yaspin' + 'pip<=19.3.1,>=18.0', 'requests', 'tomlkit', 'yaspin' ], extras_require={ "dev": [ @@ -78,7 +76,7 @@ "full": [ "aiofiles", "appdirs", "autopep8", "bowler", "colorama", "docker", "dockerpty", "fissix", "graphviz", "html5lib", "pygments", - "python-gnupg", "tabulate", "yapf" + "python-gnupg", "ruamel.yaml", "tabulate", "yapf" ], "tests": ["aioresponses", "pytest", "requests-mock"] }, From 9367bb2cd24ef1033316f83624b44c6682d68fba Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 24 Aug 2020 12:48:08 +0200 Subject: [PATCH 71/80] adopt the project for the latest isort --- dephell/actions/_autocomplete.py | 2 ++ dephell/actions/_transform.py | 1 + dephell/cache.py | 3 +++ dephell/commands/deps_tree.py | 3 ++- dephell/config/builders.py | 1 - dephell/config/logging_config.py | 1 + dephell/config/manager.py | 1 + dephell/config/scheme.py | 1 - dephell/controllers/_docker.py | 1 + dephell/controllers/_graph.py | 1 + dephell/controllers/_resolver.py | 1 + dephell/controllers/_uploader.py | 1 + dephell/converters/pip.py | 9 +++++++++ dephell/converters/sdist.py | 1 + dephell/converters/setuppy.py | 2 ++ dephell/imports.py | 1 + dephell/logging_helpers.py | 2 ++ dephell/models/constraint.py | 7 ++++--- dephell/models/dependency.py | 2 ++ dephell/models/extra_dependency.py | 2 +- dephell/models/group.py | 2 ++ dephell/models/marker_tracker.py | 1 + dephell/models/requirement.py | 1 + dephell/models/root.py | 2 ++ dephell/repositories/_getter.py | 1 + dephell/repositories/_local.py | 3 ++- dephell/repositories/_warehouse/_api.py | 1 + dephell/repositories/_warehouse/_base.py | 1 + dephell/repositories/_warehouse/_local.py | 1 + dephell/repositories/_warehouse/_simple.py | 1 + dephell/yaml.py | 2 +- install.py | 7 +++++++ pyproject.toml | 2 +- setup.py | 3 +++ tests/conftest.py | 1 + tests/test_actions/test_transform.py | 1 + tests/test_converters/test_all.py | 2 +- 37 files changed, 64 insertions(+), 11 deletions(-) diff --git a/dephell/actions/_autocomplete.py b/dephell/actions/_autocomplete.py index d930c499..50be1a45 100644 --- a/dephell/actions/_autocomplete.py +++ b/dephell/actions/_autocomplete.py @@ -20,6 +20,7 @@ def make_bash_autocomplete() -> str: + # app from ..commands import COMMANDS template = templates.get_template('autocomplete.sh.j2') @@ -40,6 +41,7 @@ def make_bash_autocomplete() -> str: def make_zsh_autocomplete() -> str: + # app from ..commands import COMMANDS template = templates.get_template('autocomplete-zsh.sh.j2') diff --git a/dephell/actions/_transform.py b/dephell/actions/_transform.py index 6b0c935c..fb500c11 100644 --- a/dephell/actions/_transform.py +++ b/dephell/actions/_transform.py @@ -11,6 +11,7 @@ if TYPE_CHECKING: + # external from bowler import LN, Capture, Filename, Query diff --git a/dephell/cache.py b/dephell/cache.py index 57ecb0d2..14806cb0 100644 --- a/dephell/cache.py +++ b/dephell/cache.py @@ -11,6 +11,7 @@ if TYPE_CHECKING: + # app from .converters.pip import PIPConverter from .models.dependency import Dependency # noqa: F401 @@ -94,6 +95,7 @@ class RequirementsCache(BaseCache): @cached_property def converter(self) -> 'PIPConverter': + # app from .converters import PIPConverter return PIPConverter(lock=False) @@ -105,6 +107,7 @@ def load(self) -> Optional[List['Dependency']]: return root.dependencies def dump(self, root): + # app from .controllers import Graph from .models import Requirement diff --git a/dephell/commands/deps_tree.py b/dephell/commands/deps_tree.py index 26e1675a..dcf9cd4c 100644 --- a/dephell/commands/deps_tree.py +++ b/dephell/commands/deps_tree.py @@ -89,9 +89,10 @@ def _make_tree(cls, dep, *, level: int = 0) -> List[str]: @staticmethod def _colorize(content: str) -> str: try: + # external import pygments - import pygments.lexers import pygments.formatters + import pygments.lexers except ImportError: return content content = pygments.highlight( diff --git a/dephell/config/builders.py b/dephell/config/builders.py index bd286470..e5b4c590 100644 --- a/dephell/config/builders.py +++ b/dephell/config/builders.py @@ -1,4 +1,3 @@ -# project # built-in from pathlib import Path diff --git a/dephell/config/logging_config.py b/dephell/config/logging_config.py index be6a1ba4..107c3203 100644 --- a/dephell/config/logging_config.py +++ b/dephell/config/logging_config.py @@ -1,3 +1,4 @@ +# built-in from typing import Any, Dict diff --git a/dephell/config/manager.py b/dephell/config/manager.py index 18e7513a..710c8e91 100644 --- a/dephell/config/manager.py +++ b/dephell/config/manager.py @@ -91,6 +91,7 @@ def attach(self, data: Dict[str, Any], container: Optional[Dict[str, Any]] = Non @staticmethod def _expand_converter(text: str) -> Dict[str, str]: + # app from ..converters import CONVERTERS # passed converter that doesn't require path diff --git a/dephell/config/scheme.py b/dephell/config/scheme.py index 51b7eae5..3f029546 100644 --- a/dephell/config/scheme.py +++ b/dephell/config/scheme.py @@ -1,4 +1,3 @@ -# project # external from dephell_versioning import get_schemes diff --git a/dephell/controllers/_docker.py b/dephell/controllers/_docker.py index b36636fa..5f0190ca 100644 --- a/dephell/controllers/_docker.py +++ b/dephell/controllers/_docker.py @@ -17,6 +17,7 @@ dockerpty = lazy_import('dockerpty') if TYPE_CHECKING: + # external import docker import dockerpty diff --git a/dephell/controllers/_graph.py b/dephell/controllers/_graph.py index 029eaf46..42340bc7 100644 --- a/dephell/controllers/_graph.py +++ b/dephell/controllers/_graph.py @@ -14,6 +14,7 @@ if TYPE_CHECKING: + # external import graphviz import graphviz.backend as graphviz_backend diff --git a/dephell/controllers/_resolver.py b/dephell/controllers/_resolver.py index 4345769c..0fa04b71 100644 --- a/dephell/controllers/_resolver.py +++ b/dephell/controllers/_resolver.py @@ -14,6 +14,7 @@ if TYPE_CHECKING: + # project from dephell.controllers._graph import Graph from dephell.controllers._mutator import Mutator diff --git a/dephell/controllers/_uploader.py b/dephell/controllers/_uploader.py index f990190f..1cf01ea9 100644 --- a/dephell/controllers/_uploader.py +++ b/dephell/controllers/_uploader.py @@ -146,6 +146,7 @@ def _get_metadata(cls, root) -> dict: @staticmethod def _get_reqs_info(reqs: list) -> dict: + # app from ..converters import EggInfoConverter extras = set() diff --git a/dephell/converters/pip.py b/dephell/converters/pip.py index 6363b6be..6d6181db 100644 --- a/dephell/converters/pip.py +++ b/dephell/converters/pip.py @@ -20,17 +20,22 @@ try: # pip<20.0.1 + # external from pip._internal.index import PackageFinder except ImportError: # pip>=20.0.1 + # external from pip._internal.index.package_finder import PackageFinder try: + # external from pip._internal.download import PipSession except ImportError: try: + # external from pip._internal.network import PipSession except ImportError: + # external from pip._internal.network.session import PipSession @@ -167,6 +172,7 @@ def _get_finder() -> PackageFinder: pass # pip 19.3 + # external from pip._internal.models.search_scope import SearchScope from pip._internal.models.selection_prefs import SelectionPreferences try: @@ -178,11 +184,14 @@ def _get_finder() -> PackageFinder: except TypeError: pass + # external from pip._internal.models.target_python import TargetPython try: # pip 19.3.1 + # external from pip._internal.collector import LinkCollector except ImportError: + # external from pip._internal.index.collector import LinkCollector return PackageFinder.create( link_collector=LinkCollector( diff --git a/dephell/converters/sdist.py b/dephell/converters/sdist.py index bde8ccd6..388f026f 100644 --- a/dephell/converters/sdist.py +++ b/dephell/converters/sdist.py @@ -171,6 +171,7 @@ def _write_additional_files(self, *, tar: TarFile, project: RootDependency, subd ) # write tests + # app from ..actions import get_path_size if self.ratio is None: self.ratio = config['sdist']['ratio'] diff --git a/dephell/converters/setuppy.py b/dephell/converters/setuppy.py index 8bbbdb3a..c7dfdb18 100644 --- a/dephell/converters/setuppy.py +++ b/dephell/converters/setuppy.py @@ -21,11 +21,13 @@ try: + # external from yapf.yapflib.style import CreateGoogleStyle from yapf.yapflib.yapf_api import FormatCode except ImportError: FormatCode = None try: + # external from autopep8 import fix_code except ImportError: fix_code = None diff --git a/dephell/imports.py b/dephell/imports.py index bce60138..899e439a 100644 --- a/dephell/imports.py +++ b/dephell/imports.py @@ -22,6 +22,7 @@ def _module(self): return import_module(name=self._name) def _install(self): + # app from .package_manager import PackageManager name = self._package or self._name.split('.', maxsplit=1)[0] diff --git a/dephell/logging_helpers.py b/dephell/logging_helpers.py index d6d08dad..b7d4f01f 100644 --- a/dephell/logging_helpers.py +++ b/dephell/logging_helpers.py @@ -8,8 +8,10 @@ try: try: + # external from colorama import Fore, init except ImportError: + # external from pip._vendor.colorama import Fore, init init() except ImportError: diff --git a/dephell/models/constraint.py b/dephell/models/constraint.py index a76a7e39..c017b583 100644 --- a/dephell/models/constraint.py +++ b/dephell/models/constraint.py @@ -7,9 +7,10 @@ if TYPE_CHECKING: - from .dependency import Dependency # noqa: F401 - from .extra_dependency import ExtraDependency # noqa: F401 - from .root import RootDependency # noqa: F401 + # app + from .dependency import Dependency # noqa: F401 + from .extra_dependency import ExtraDependency # noqa: F401 + from .root import RootDependency # noqa: F401 class Constraint: diff --git a/dephell/models/dependency.py b/dephell/models/dependency.py index 669454dd..9ac14793 100644 --- a/dephell/models/dependency.py +++ b/dephell/models/dependency.py @@ -82,6 +82,7 @@ def dependencies(self) -> Tuple['Dependency', ...]: if deps is not None: return deps + # app from ..controllers import DependencyMaker deps = [] for dep in self.group.dependencies: @@ -201,6 +202,7 @@ def __str__(self) -> str: return result def __iadd__(self, dep: 'Dependency') -> 'Dependency': + # app from ..repositories import GitRepo if not isinstance(dep, type(self)): diff --git a/dephell/models/extra_dependency.py b/dephell/models/extra_dependency.py index 7748ef1a..c79a90ea 100644 --- a/dephell/models/extra_dependency.py +++ b/dephell/models/extra_dependency.py @@ -1,7 +1,7 @@ -# external # built-in from typing import Union +# external import attr from packaging.utils import canonicalize_name from tomlkit.items import String diff --git a/dephell/models/group.py b/dephell/models/group.py index 273a7a4c..f99ae543 100644 --- a/dephell/models/group.py +++ b/dephell/models/group.py @@ -8,6 +8,7 @@ if TYPE_CHECKING: + # app from .dependency import Dependency from .release import Release from .root import RootRelease # noqa: F401 @@ -69,6 +70,7 @@ def metadependency(self) -> 'Dependency': raise ValueError('dep required for group of extras') min_version = min(self.versions) max_version = max(self.versions) + # app from ..controllers import DependencyMaker return DependencyMaker.from_requirement( source=self.dep, diff --git a/dephell/models/marker_tracker.py b/dephell/models/marker_tracker.py index a28f33ec..d6927d00 100644 --- a/dephell/models/marker_tracker.py +++ b/dephell/models/marker_tracker.py @@ -1,3 +1,4 @@ +# built-in from typing import Dict, Union # external diff --git a/dephell/models/requirement.py b/dephell/models/requirement.py index b81ae885..8e519e80 100644 --- a/dephell/models/requirement.py +++ b/dephell/models/requirement.py @@ -11,6 +11,7 @@ if TYPE_CHECKING: + # project from dephell.models.release import Release # noqa: F401 diff --git a/dephell/models/root.py b/dephell/models/root.py index f609654a..8b2e9c4d 100644 --- a/dephell/models/root.py +++ b/dephell/models/root.py @@ -18,6 +18,7 @@ if TYPE_CHECKING: + # app from .dependency import Dependency # noqa: F401 @@ -107,6 +108,7 @@ def python_compat(self) -> bool: @property def warehouses(self) -> tuple: + # app from ..repositories import WarehouseBaseRepo repos = dict() diff --git a/dephell/repositories/_getter.py b/dephell/repositories/_getter.py index 13a288a4..1eba5cec 100644 --- a/dephell/repositories/_getter.py +++ b/dephell/repositories/_getter.py @@ -19,6 +19,7 @@ def get_repo(link=None, *, name: str = None, default=None): + # app from ..controllers import RepositoriesRegistry if name is not None: diff --git a/dephell/repositories/_local.py b/dephell/repositories/_local.py index 72ad925b..4d4c8590 100644 --- a/dephell/repositories/_local.py +++ b/dephell/repositories/_local.py @@ -50,7 +50,8 @@ async def get_dependencies(self, name: str, version: str, extra: Optional[str] = return deps def get_root(self, name: str, version: str): - from ..converters import EggInfoConverter, SDistConverter, WheelConverter, CONVERTERS + # app + from ..converters import CONVERTERS, EggInfoConverter, SDistConverter, WheelConverter if not self.path.exists(): raise FileNotFoundError(str(self.path)) diff --git a/dephell/repositories/_warehouse/_api.py b/dephell/repositories/_warehouse/_api.py index 5d77e8f8..cca29fd9 100644 --- a/dephell/repositories/_warehouse/_api.py +++ b/dephell/repositories/_warehouse/_api.py @@ -272,6 +272,7 @@ async def _get_from_files(self, files_info: List[dict]) -> Tuple[str, ...]: # if file_info['packagetype'] == 'bdist_wheel': # return () + # app from ...converters import SDistConverter, WheelConverter sdist = SDistConverter() diff --git a/dephell/repositories/_warehouse/_base.py b/dephell/repositories/_warehouse/_base.py index 6520fbdf..2db67410 100644 --- a/dephell/repositories/_warehouse/_base.py +++ b/dephell/repositories/_warehouse/_base.py @@ -18,6 +18,7 @@ try: + # external import aiofiles except ImportError: aiofiles = None diff --git a/dephell/repositories/_warehouse/_local.py b/dephell/repositories/_warehouse/_local.py index 17223760..f62c9f78 100644 --- a/dephell/repositories/_warehouse/_local.py +++ b/dephell/repositories/_warehouse/_local.py @@ -104,6 +104,7 @@ def _get_hash(path: Path) -> str: return digest.hexdigest() def _get_deps_from_files(self, name, version): + # app from ...converters import SDistConverter, WheelConverter paths = [] diff --git a/dephell/repositories/_warehouse/_simple.py b/dephell/repositories/_warehouse/_simple.py index 931876d0..c3fe1d8c 100644 --- a/dephell/repositories/_warehouse/_simple.py +++ b/dephell/repositories/_warehouse/_simple.py @@ -192,6 +192,7 @@ def _get_links(self, name: str) -> List[Dict[str, str]]: return links async def _get_deps_from_links(self, name: str, version): + # app from ...converters import SDistConverter, WheelConverter links = self._get_links(name=name) diff --git a/dephell/yaml.py b/dephell/yaml.py index 4cce3ee3..0b572268 100644 --- a/dephell/yaml.py +++ b/dephell/yaml.py @@ -1,7 +1,7 @@ -# app # built-in from typing import Any, Dict, TextIO +# app from .imports import lazy_import diff --git a/install.py b/install.py index a5afea9e..1825f22f 100644 --- a/install.py +++ b/install.py @@ -77,19 +77,24 @@ def args(self): def pip_main(self): # install try: + # external import pip # noQA: F401 except ImportError: print('install pip') + # built-in from ensurepip import bootstrap bootstrap() # import try: + # external from pip._internal.main import main except ImportError: try: + # external from pip._internal import main except ImportError: + # external from pip import main return main @@ -97,6 +102,7 @@ def pip_main(self): @cached_property def data_dir(self) -> Path: try: + # external from appdirs import user_data_dir except ImportError: @@ -111,6 +117,7 @@ def data_dir(self) -> Path: return path / 'dephell' self.pip_main(['install', 'appdirs']) + # external from appdirs import user_data_dir return Path(user_data_dir('dephell')) diff --git a/pyproject.toml b/pyproject.toml index c8eada34..69242cb8 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -74,7 +74,7 @@ command = "sphinx-build -W docs docs/build" [tool.dephell.isort] from = {format = "poetry", path = "pyproject.toml"} envs = ["main", "full", "dev"] -command = "isort -y" +command = "isort ." [tool.dephell.vendorized] from = {format = "poetry", path = "pyproject.toml"} diff --git a/setup.py b/setup.py index 8223777d..0ac53acc 100644 --- a/setup.py +++ b/setup.py @@ -5,12 +5,15 @@ # https://github.com/dephell/dephell try: + # external from setuptools import setup except ImportError: from distutils.core import setup +# built-in import os.path + readme = '' here = os.path.abspath(os.path.dirname(__file__)) readme_path = os.path.join(here, 'README.rst') diff --git a/tests/conftest.py b/tests/conftest.py index 3e38a1e6..ccc38a01 100644 --- a/tests/conftest.py +++ b/tests/conftest.py @@ -88,6 +88,7 @@ def temp_path(tmp_path: Path): @pytest.fixture() def temp_cache(temp_path): + # project from dephell.config import config config.attach({'cache': {'path': str(temp_path)}}) diff --git a/tests/test_actions/test_transform.py b/tests/test_actions/test_transform.py index 9dcbb778..c7711956 100644 --- a/tests/test_actions/test_transform.py +++ b/tests/test_actions/test_transform.py @@ -50,6 +50,7 @@ # ), ]) def test_transform_imports(code_in: str, code_out: str, old_name: str, new_name: str, temp_path: Path): + # external from bowler import Query code_in += '\n' diff --git a/tests/test_converters/test_all.py b/tests/test_converters/test_all.py index 62f2ac30..cca78f53 100644 --- a/tests/test_converters/test_all.py +++ b/tests/test_converters/test_all.py @@ -1,7 +1,7 @@ -# external # built-in from pathlib import Path +# external import attr import pytest From 59213023ea43545f6a7f40cb5aefccbd63229b89 Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 24 Aug 2020 13:02:22 +0200 Subject: [PATCH 72/80] fix isort skip --- tests/requirements/module.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/requirements/module.py b/tests/requirements/module.py index d836e3e5..0d8f3fa0 100644 --- a/tests/requirements/module.py +++ b/tests/requirements/module.py @@ -7,4 +7,4 @@ 1 / 0 -import pytest # noqa: E402 +import pytest # noqa: E402 # isort:skip From ccd115ab2b0734b51af70ab004d77bec2180c8a3 Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 24 Aug 2020 14:22:01 +0200 Subject: [PATCH 73/80] more type annotations --- dephell/controllers/_conflict.py | 2 ++ dephell/controllers/_uploader.py | 19 ++++++++++--------- 2 files changed, 12 insertions(+), 9 deletions(-) diff --git a/dephell/controllers/_conflict.py b/dephell/controllers/_conflict.py index b98a149b..aa66ae5e 100644 --- a/dephell/controllers/_conflict.py +++ b/dephell/controllers/_conflict.py @@ -1,6 +1,7 @@ # built-in import re from logging import getLogger +from typing import Tuple # external from jinja2 import Environment, PackageLoader @@ -47,6 +48,7 @@ def analyze_conflict(resolver, suffix: str = '') -> str: logger.warning(e.args[0]) conflict = resolver.graph.conflict + templates: Tuple[str, ...] if conflict is None: templates = ('state.html.j2', ) elif not resolver.graph.conflict.python_compat: diff --git a/dephell/controllers/_uploader.py b/dephell/controllers/_uploader.py index 1cf01ea9..5c91d5e1 100644 --- a/dephell/controllers/_uploader.py +++ b/dephell/controllers/_uploader.py @@ -3,7 +3,7 @@ import subprocess from io import BytesIO from pathlib import Path -from typing import Dict +from typing import Any, Dict from urllib.parse import urlparse # external @@ -28,7 +28,7 @@ def __attrs_post_init__(self): @cached_property def hostname(self) -> str: - return urlparse(self.url).hostname + return urlparse(self.url).hostname or 'pypi.org' @staticmethod def _fix_url(url: str) -> str: @@ -47,10 +47,11 @@ def _fix_url(url: str) -> str: def _get_hashes(path: Path) -> Dict[str, str]: sha256_manager = hashlib.sha256() md5_manager = hashlib.md5() + + blake2_manager: Any = None if hasattr(hashlib, 'blake2b'): blake2_manager = hashlib.blake2b(digest_size=32) - else: - blake2_manager = None + with path.open('rb') as stream: while True: data = stream.read(65536) @@ -67,8 +68,8 @@ def _get_hashes(path: Path) -> Dict[str, str]: ) @classmethod - def _get_file_info(cls, path: Path) -> dict: - result = dict() + def _get_file_info(cls, path: Path) -> Dict[str, str]: + result: Dict[str, str] = dict() # file type and python version if path.suffix == '.whl': @@ -83,12 +84,12 @@ def _get_file_info(cls, path: Path) -> dict: # gpg signature sign_path = path.with_suffix(path.suffix + '.asc') if sign_path.exists(): - result['gpg_signature'] = sign_path.read_bytes() + result['gpg_signature'] = sign_path.read_text() return result @classmethod - def _get_metadata(cls, root) -> dict: + def _get_metadata(cls, root) -> Dict[str, Any]: meta = dict( # defaults that goes as-is on API comment=None, @@ -137,7 +138,7 @@ def _get_metadata(cls, root) -> dict: for key, url in root.links.items(): key = key[0].upper() + key[1:] - meta['project_urls'].append('{}, {}'.format(key, url)) + meta['project_urls'].append('{}, {}'.format(key, url)) # type: ignore if root.python: meta['requires_python'] = str(root.python.peppify()) From d640b9759a29c5f190c257273e154529bbeace22 Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 24 Aug 2020 14:23:35 +0200 Subject: [PATCH 74/80] drop Snyk support at all --- dephell/controllers/__init__.py | 3 - dephell/controllers/_snyk.py | 103 ---------------------------- docs/cmd-deps-audit.md | 2 - tests/test_controllers/test_snyk.py | 15 ---- 4 files changed, 123 deletions(-) delete mode 100644 dephell/controllers/_snyk.py delete mode 100644 tests/test_controllers/test_snyk.py diff --git a/dephell/controllers/__init__.py b/dephell/controllers/__init__.py index 6367fee0..6aff1565 100644 --- a/dephell/controllers/__init__.py +++ b/dephell/controllers/__init__.py @@ -8,7 +8,6 @@ from ._repos import RepositoriesRegistry from ._resolver import Resolver from ._safety import Safety, SafetyVulnInfo -from ._snyk import Snyk, SnykVulnInfo from ._uploader import Uploader @@ -24,7 +23,5 @@ 'Resolver', 'Safety', 'SafetyVulnInfo', - 'Snyk', - 'SnykVulnInfo', 'Uploader', ] diff --git a/dephell/controllers/_snyk.py b/dephell/controllers/_snyk.py deleted file mode 100644 index ecd37b1d..00000000 --- a/dephell/controllers/_snyk.py +++ /dev/null @@ -1,103 +0,0 @@ -# built-in -import re -from collections import defaultdict -from typing import Dict, List, Optional, Tuple, Union -from xml.etree import ElementTree - -# external -import attr -from dephell_specifier import RangeSpecifier -from packaging.version import VERSION_PATTERN, Version - -# app -from ..cached_property import cached_property -from ..networking import requests_session - - -RSS_URL = 'https://snyk.io/vuln/feed.xml?type=pip' -REX_VERSION = re.compile(VERSION_PATTERN, re.VERBOSE | re.IGNORECASE) -REX_TAG = re.compile(r'<\/?[a-z]+.*?>') -REX_LINK = re.compile(r'https?\:\/\/[a-z]+[^\s\"]+') - - -@attr.s(slots=True) -class SnykVulnInfo: - name = attr.ib(type=str) - severity = attr.ib(type=str) - description = attr.ib(type=str) - version = attr.ib(type=Optional[Version]) - links = attr.ib(type=Tuple[str, ...]) - - @property - def specifier(self) -> RangeSpecifier: - return RangeSpecifier('<' + str(self.version)) - - -@attr.s() -class Snyk: - """ - https://snyk.io/vuln?type=pip - - RSS was broken! - """ - url = attr.ib(type=str, default=RSS_URL) - - @cached_property - def vulns(self) -> Dict[str, List[SnykVulnInfo]]: - with requests_session() as session: - response = session.get(self.url) - response.raise_for_status() - root = ElementTree.fromstring(response.content) - - result = defaultdict(list) - for item in root[0]: - if item.tag != 'item': - continue - item = {field.tag: field.text for field in item} - desc = self._parse_description(item['description']) - desc['links'].append(item['link']) - - versions = [Version(version) for version in desc['versions'] if version] - version = max(versions) if versions else None - - result[desc['name']].append(SnykVulnInfo( - name=desc['name'], - severity=desc['severity'], - description=item['title'].split('https://snyk.io/')[0], - version=version, - links=tuple(desc['links']), - )) - - return result - - def _parse_description(self, text: str): - result = dict(links=[], versions=[]) - for line in text.splitlines(): - clean = REX_TAG.sub('', line.strip()) - if clean.startswith('Severity:'): - result['severity'] = clean.split()[1] - continue - if clean.startswith('Affects:'): - result['name'] = clean.split()[1] - continue - if ' or higher' in clean: - result['versions'] = self._get_versions(clean) - result['links'].extend(REX_LINK.findall(line)) - return result - - @staticmethod - def _get_versions(text) -> List[str]: - versions = [] - for word in text.split(): - if REX_VERSION.fullmatch(word): - versions.append(word) - return versions - - def get(self, name: str, version: Union[str, Version]) -> List[SnykVulnInfo]: - if type(version) is str: - version = Version(version) - vulns = [] - for vuln in self.vulns.get(name, []): - if vuln.version is None or version < vuln.version: - vulns.append(vuln) - return vulns diff --git a/docs/cmd-deps-audit.md b/docs/cmd-deps-audit.md index d70cc2eb..6b3a06cd 100644 --- a/docs/cmd-deps-audit.md +++ b/docs/cmd-deps-audit.md @@ -8,8 +8,6 @@ This command returns non-zero code if some vulnerabilities was found, so you can [pyup.io](https://pyup.io/) provides public repository [safety-db](https://github.com/pyupio/safety-db) with all vulnerabilities in their database. DepHell uses it. This repository automatically updates every month. So, if you want to get actual reports you have to use their official solutions. They provide Safety CI that [free for Open Source](https://pyup.io/pricing/) and $30 for personal usage. If you have "Business" plan you also can get API key and use their [official CLI](https://github.com/pyupio/safety). -We used [snyk.io](https://snyk.io/) before, but now they have removed RSS feed. - ## Dependencies lookup 1. If some package and version explicitly specified then this package will be used. Example: `dephell deps audit jinja2==2.0`. diff --git a/tests/test_controllers/test_snyk.py b/tests/test_controllers/test_snyk.py deleted file mode 100644 index bef2e481..00000000 --- a/tests/test_controllers/test_snyk.py +++ /dev/null @@ -1,15 +0,0 @@ -# external -import pytest - -# project -from dephell.controllers import Snyk - - -@pytest.mark.skipif(True, reason='RSS feed was removed from snyk') -@pytest.mark.allow_hosts() -def test_safety(): - snyk = Snyk() - assert sum(len(vulns) for vulns in snyk.vulns.values()) == 50 - - for name, vulns in snyk.vulns.items(): - assert len(snyk.get(name=name, version='0.0.0')) == len(vulns) From 969d465691d4d721fa6971227bdf7fe048412073 Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 24 Aug 2020 15:21:17 +0200 Subject: [PATCH 75/80] more types support --- dephell/controllers/_mutator.py | 5 +++-- dephell/controllers/_repos.py | 26 ++++++++++++++++-------- dephell/controllers/_safety.py | 2 +- dephell/repositories/_warehouse/_base.py | 8 ++++++++ dephell/repositories/base.py | 4 ++-- 5 files changed, 31 insertions(+), 14 deletions(-) diff --git a/dephell/controllers/_mutator.py b/dephell/controllers/_mutator.py index b8f2901a..ad2f456c 100644 --- a/dephell/controllers/_mutator.py +++ b/dephell/controllers/_mutator.py @@ -1,7 +1,7 @@ # built-in from itertools import product from logging import getLogger -from typing import Iterable, Iterator, Optional, Sequence, Set, Tuple +from typing import Iterable, Iterator, List, Optional, Sequence, Set, Tuple # external import attr @@ -17,7 +17,7 @@ def lazy_product(*all_groups) -> Iterator: - slices = [[] for _ in range(len(all_groups))] + slices: List[List[str]] = [[] for _ in range(len(all_groups))] all_groups = [iter(groups) for groups in all_groups] while True: @@ -62,6 +62,7 @@ def mutate(self, graph: Graph) -> Optional[Tuple[Group, ...]]: self._check_not_empty, # self._check_soft, ) + assert graph.conflict # hint for mypy for check in checker: for groups in self.get_mutations(deps=parents): if check(groups=groups, deps=parents, conflict=graph.conflict): diff --git a/dephell/controllers/_repos.py b/dephell/controllers/_repos.py index b59b078e..3f9d1951 100644 --- a/dephell/controllers/_repos.py +++ b/dephell/controllers/_repos.py @@ -1,7 +1,7 @@ # built-in from functools import lru_cache from pathlib import Path -from typing import Dict, Iterable, List, Optional +from typing import Dict, Iterable, List, Optional, Set from urllib.parse import urljoin, urlparse # external @@ -31,14 +31,12 @@ def _has_api(url: str) -> bool: @attr.s() class RepositoriesRegistry(WarehouseBaseRepo): - repos = attr.ib(factory=list) + repos: List[WarehouseBaseRepo] = attr.ib(factory=list) prereleases = attr.ib(type=bool, factory=lambda: global_config['prereleases']) # allow prereleases from_config = attr.ib(type=bool, default=False) - _urls = attr.ib(factory=set) - _names = attr.ib(factory=set) - - propagate = True + _urls: Set[str] = attr.ib(factory=set) + _names: Set[str] = attr.ib(factory=set) def add_repo(self, *, url: str, name: str = None, from_config: bool = False) -> bool: if url in self._urls: @@ -74,6 +72,8 @@ def add_repo(self, *, url: str, name: str = None, from_config: bool = False) -> name = urlparse(url).hostname if name in self._names: return False + if not name: + name = 'pypi' self._names.add(name) if _has_api(url=url): @@ -169,14 +169,22 @@ async def download(self, name: str, version: str, path: Path) -> bool: def name(self) -> str: return self.repos[0].name - @property - def url(self) -> str: + @property # type: ignore + def url(self) -> str: # type: ignore return self.repos[0].url + @url.setter + def url(self, url: str): # type: ignore + self.repos[0].url = url + @property def pretty_url(self) -> str: return self.url + @pretty_url.setter + def pretty_url(self, url: str): + self.repos[0].url = url + @property - def propagate(self) -> bool: + def propagate(self) -> bool: # type: ignore return self.repos[0].propagate diff --git a/dephell/controllers/_safety.py b/dephell/controllers/_safety.py index a3aa6c2d..dcc03c62 100644 --- a/dephell/controllers/_safety.py +++ b/dephell/controllers/_safety.py @@ -63,7 +63,7 @@ def vulns(self) -> Dict[str, Tuple[SafetyVulnInfo, ...]]: return vulns def get(self, name: str, version: Union[str, Version]) -> List[SafetyVulnInfo]: - if type(version) is str: + if isinstance(version, str): version = Version(version) vulns = [] for vuln in self.vulns.get(name, []): diff --git a/dephell/repositories/_warehouse/_base.py b/dephell/repositories/_warehouse/_base.py index 2db67410..e8d63d28 100644 --- a/dephell/repositories/_warehouse/_base.py +++ b/dephell/repositories/_warehouse/_base.py @@ -34,6 +34,14 @@ class WarehouseBaseRepo(Interface): def prereleases(self) -> bool: raise NotImplementedError + @cached_property + def url(self) -> str: + raise NotImplementedError + + @cached_property + def name(self) -> str: + raise NotImplementedError + @cached_property def from_config(self): raise NotImplementedError diff --git a/dephell/repositories/base.py b/dephell/repositories/base.py index d4be6e47..60041e66 100644 --- a/dephell/repositories/base.py +++ b/dephell/repositories/base.py @@ -8,7 +8,7 @@ class Interface(metaclass=abc.ABCMeta): - propagate = False + propagate: bool = False @abc.abstractmethod def get_releases(self, dep) -> tuple: @@ -23,7 +23,7 @@ def pretty_url(self): return self.__dict__.get('pretty_url', self.url) @pretty_url.setter - def pretty_url(self, url): + def pretty_url(self, url: str): self.__dict__['pretty_url'] = url def search(self, query: Iterable[str]) -> List[Dict[str, str]]: From 056e4ac2cc806981e27b048188c0f41aa17b87a4 Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 24 Aug 2020 15:32:38 +0200 Subject: [PATCH 76/80] better type check for cached_property --- dephell/cached_property.pyi | 33 ++++++++++++++++++++++++++++++++ dephell/commands/deps_check.py | 2 ++ dephell/commands/deps_install.py | 2 ++ dephell/models/release.py | 6 +++--- mypy.ini | 5 +++++ pyproject.toml | 4 ++-- 6 files changed, 47 insertions(+), 5 deletions(-) create mode 100644 dephell/cached_property.pyi create mode 100644 mypy.ini diff --git a/dephell/cached_property.pyi b/dephell/cached_property.pyi new file mode 100644 index 00000000..4aae4a6c --- /dev/null +++ b/dephell/cached_property.pyi @@ -0,0 +1,33 @@ +from typing import ( + Any, + Callable, + Generic, + Optional, + Type, + TypeVar, + overload, +) + +_AnyCallable = Callable[..., Any] + +_T = TypeVar("_T") +_S = TypeVar("_S") + + +# https://github.com/python/typeshed/blob/master/stdlib/3/functools.pyi +class cached_property(Generic[_S, _T]): + func: Callable[[_S], _T] + + def __init__(self, func: Callable[[_S], _T]) -> None: + ... + + @overload + def __get__(self, instance: None, owner: Optional[Type[_S]] = ...) -> 'cached_property[_S, _T]': + ... + + @overload + def __get__(self, instance: _S, owner: Optional[Type[_S]] = ...) -> _T: + ... + + def __set_name__(self, owner: Type[_S], name: str) -> None: + ... diff --git a/dephell/commands/deps_check.py b/dephell/commands/deps_check.py index 5ea595a4..b1d38aee 100644 --- a/dephell/commands/deps_check.py +++ b/dephell/commands/deps_check.py @@ -42,6 +42,8 @@ def __call__(self) -> bool: data = [] reqs = Requirement.from_graph(graph=resolver.graph, lock=True) for req in reqs: + if not req.version: + continue version = req.version.strip('=') # not installed if req.name not in installed: diff --git a/dephell/commands/deps_install.py b/dephell/commands/deps_install.py index 7893e447..33618c61 100644 --- a/dephell/commands/deps_install.py +++ b/dephell/commands/deps_install.py @@ -82,6 +82,8 @@ def _get_install_remove(self, graph, python) -> Tuple[list, list]: install.append(req) continue # installed the same version, skip + if not req.version: + continue version = req.version.strip('=') if version in installed[req.name]: continue diff --git a/dephell/models/release.py b/dephell/models/release.py index 442120da..74fbd10a 100644 --- a/dephell/models/release.py +++ b/dephell/models/release.py @@ -16,14 +16,14 @@ class Release: dependencies = None # type: tuple - raw_name = attr.ib(type=str) - version = attr.ib(converter=parse) # type: ignore + raw_name: str = attr.ib() + version: str = attr.ib(converter=parse) # type: ignore time = attr.ib(repr=False) # upload_time python = attr.ib(default=None, repr=False) # requires_python hashes = attr.ib(factory=tuple, repr=False) # digests/sha256 urls = attr.ib(factory=tuple, repr=False) # url - extra = attr.ib(type=Optional[str], default=None) + extra: Optional[str] = attr.ib(default=None) def __attrs_post_init__(self) -> None: assert '[' not in self.raw_name, self.raw_name diff --git a/mypy.ini b/mypy.ini new file mode 100644 index 00000000..e128b5ae --- /dev/null +++ b/mypy.ini @@ -0,0 +1,5 @@ +[mypy] +allow_redefinition = True +follow_imports = silent +ignore_missing_imports = True +show_error_codes = True diff --git a/pyproject.toml b/pyproject.toml index 69242cb8..25451296 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -35,8 +35,8 @@ from = {format = "poetry", path = "pyproject.toml"} # but `dephell venv run` command will install it automatically command = [ "mypy", - "--ignore-missing-imports", "--allow-redefinition", "--follow-imports=silent", - "dephell/actions", "dephell/commands", "dephell/config", "dephell/yaml.py" + "dephell/actions", "dephell/commands", "dephell/config", + "dephell/yaml.py" ] # Test project package in the separated venv: From 9a5a7b0860cc2ec9ed939b7f9f60fd1159ec28d4 Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 24 Aug 2020 15:45:12 +0200 Subject: [PATCH 77/80] fix more typing --- dephell/controllers/_docker.py | 26 ++++++++++++++++---------- dephell/controllers/_graph.py | 15 +++++++++------ dephell/controllers/_repos.py | 8 ++++++-- dephell/controllers/_resolver.py | 6 +++++- pyproject.toml | 2 +- 5 files changed, 37 insertions(+), 20 deletions(-) diff --git a/dephell/controllers/_docker.py b/dephell/controllers/_docker.py index 5f0190ca..fe01297a 100644 --- a/dephell/controllers/_docker.py +++ b/dephell/controllers/_docker.py @@ -12,16 +12,16 @@ from ..imports import lazy_import from ..networking import requests_session - -docker = lazy_import('docker') -dockerpty = lazy_import('dockerpty') - if TYPE_CHECKING: # external import docker import dockerpty +docker = lazy_import('docker') # noqa: F811 +dockerpty = lazy_import('dockerpty') # noqa: F811 + + DOCKER_PREFIX = 'dephell-' @@ -142,14 +142,18 @@ def create(self, *, pull=True) -> None: ) def stop(self) -> None: - self.container.stop() + if self.container: + self.container.stop() def remove(self) -> None: - self.stop() - self.container.remove(force=True) - for container in self.network.containers: - self.network.disconnect(container, force=True) - self.network.remove() + if self.container: + self.stop() + self.container.remove(force=True) + + if self.network: + for container in self.network.containers: + self.network.disconnect(container, force=True) + self.network.remove() def exists(self) -> bool: if 'container' in self.__dict__: @@ -162,6 +166,8 @@ def activate(self) -> None: def run(self, command: List[str]) -> None: if dockerpty is None: raise RuntimeError('cannot run Docker on Windows') + if not self.container: + raise RuntimeError('cannot find container') self.container.start() dockerpty.exec_command( client=self.client.api, diff --git a/dephell/controllers/_graph.py b/dephell/controllers/_graph.py index 42340bc7..9a9b831a 100644 --- a/dephell/controllers/_graph.py +++ b/dephell/controllers/_graph.py @@ -1,7 +1,7 @@ # built-in from collections import ChainMap from logging import getLogger -from typing import TYPE_CHECKING, Iterator, Optional +from typing import Any, Dict, TYPE_CHECKING, Iterator, List, Optional # app from ..imports import lazy_import @@ -9,20 +9,22 @@ from ..models.root import RootDependency -graphviz = lazy_import('graphviz') -graphviz_backend = lazy_import('graphviz.backend') - - if TYPE_CHECKING: # external import graphviz import graphviz.backend as graphviz_backend +graphviz = lazy_import('graphviz') # noqa: F811 +graphviz_backend = lazy_import('graphviz.backend') # noqa: F811 + + logger = getLogger(__name__) class Layer: + _mapping: Dict[str, Any] + def __init__(self, level: int, *deps): self.level = level self._mapping = dict() @@ -75,7 +77,8 @@ def __repr__(self): class Graph: - conflict = None # type: Optional[Dependency] + conflict: Optional[Dependency] = None + _layers: List[Layer] def __init__(self, *roots: RootDependency) -> None: for root in roots: diff --git a/dephell/controllers/_repos.py b/dephell/controllers/_repos.py index 3f9d1951..bc2e3b45 100644 --- a/dephell/controllers/_repos.py +++ b/dephell/controllers/_repos.py @@ -132,23 +132,27 @@ def make(self, name: str) -> 'RepositoriesRegistry': return type(self)(repos=repos, prereleases=self.prereleases) def get_releases(self, dep) -> tuple: - first_exception = None + first_exception: Optional[Exception] = None for repo in self.repos: try: return repo.get_releases(dep=dep) except PackageNotFoundError as exc: if first_exception is None: first_exception = exc + if first_exception is None: + raise LookupError('no repositories in registry') raise first_exception async def get_dependencies(self, name: str, version: str, extra: Optional[str] = None) -> tuple: - first_exception = None + first_exception: Optional[Exception] = None for repo in self.repos: try: return await repo.get_dependencies(name=name, version=version, extra=extra) except PackageNotFoundError as exc: if first_exception is None: first_exception = exc + if first_exception is None: + raise LookupError('no repositories in registry') raise first_exception def search(self, query: Iterable[str]) -> List[Dict[str, str]]: diff --git a/dephell/controllers/_resolver.py b/dephell/controllers/_resolver.py index 0fa04b71..5d951649 100644 --- a/dephell/controllers/_resolver.py +++ b/dephell/controllers/_resolver.py @@ -142,6 +142,7 @@ def _resolve(self, debug: bool, silent: bool, level: Optional[int], spinner) -> )) self.unapply(dep) dep.group = group + return None def apply_envs(self, envs: set, deep: bool = True) -> None: """Filter out dependencies from the graph by the given envs. @@ -191,7 +192,10 @@ def apply_markers(self, python) -> None: # get only base part of python version because `packagings` drops # all markers for python prereleases - python_version = REX_BASE_VERSION.match(str(python.version)).group() + python_version = str(python.version) + match = REX_BASE_VERSION.match(python_version) + if match: + python_version = match.group() for dep in self.graph: if not dep.applied: diff --git a/pyproject.toml b/pyproject.toml index 25451296..3ab04065 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -36,7 +36,7 @@ from = {format = "poetry", path = "pyproject.toml"} command = [ "mypy", "dephell/actions", "dephell/commands", "dephell/config", - "dephell/yaml.py" + "dephell/controllers", "dephell/yaml.py" ] # Test project package in the separated venv: From 9057a2ebc6ae1cda86d1bca44f6201ab8072abf0 Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 24 Aug 2020 15:55:04 +0200 Subject: [PATCH 78/80] fully type check controllers --- dephell/commands/project_test.py | 2 +- dephell/controllers/_repos.py | 7 ++++--- dephell/repositories/_warehouse/_base.py | 18 +++++------------- mypy.ini | 1 + 4 files changed, 11 insertions(+), 17 deletions(-) diff --git a/dephell/commands/project_test.py b/dephell/commands/project_test.py index bfcefe23..d68a89c1 100644 --- a/dephell/commands/project_test.py +++ b/dephell/commands/project_test.py @@ -98,7 +98,7 @@ def __call__(self) -> bool: venv.create(python_path=python.path) # copy tests - for path in self.config['tests']: # type: Path # type: ignore + for path in self.config['tests']: # type: Path self.logger.info('copy files', extra=dict(path=path)) path = Path(path) if not path.exists(): diff --git a/dephell/controllers/_repos.py b/dephell/controllers/_repos.py index bc2e3b45..49e19d7b 100644 --- a/dephell/controllers/_repos.py +++ b/dephell/controllers/_repos.py @@ -1,7 +1,7 @@ # built-in from functools import lru_cache from pathlib import Path -from typing import Dict, Iterable, List, Optional, Set +from typing import Dict, Iterable, List, Optional, Set, Type, Union from urllib.parse import urljoin, urlparse # external @@ -76,6 +76,7 @@ def add_repo(self, *, url: str, name: str = None, from_config: bool = False) -> name = 'pypi' self._names.add(name) + cls: Union[Type[WarehouseAPIRepo], Type[WarehouseSimpleRepo]] if _has_api(url=url): cls = WarehouseAPIRepo else: @@ -170,7 +171,7 @@ async def download(self, name: str, version: str, path: Path) -> bool: # properties @property - def name(self) -> str: + def name(self) -> str: # type: ignore return self.repos[0].name @property # type: ignore @@ -178,7 +179,7 @@ def url(self) -> str: # type: ignore return self.repos[0].url @url.setter - def url(self, url: str): # type: ignore + def url(self, url: str): self.repos[0].url = url @property diff --git a/dephell/repositories/_warehouse/_base.py b/dephell/repositories/_warehouse/_base.py index e8d63d28..b48b64bd 100644 --- a/dephell/repositories/_warehouse/_base.py +++ b/dephell/repositories/_warehouse/_base.py @@ -3,7 +3,7 @@ from logging import getLogger from pathlib import Path from tempfile import TemporaryDirectory -from typing import Tuple +from typing import Any, Tuple from urllib.parse import urlparse, urlunparse # external @@ -29,18 +29,10 @@ class WarehouseBaseRepo(Interface): - # I'm not sure how to combine `@abstractproperty` and `= attr.ib()` - @cached_property - def prereleases(self) -> bool: - raise NotImplementedError - - @cached_property - def url(self) -> str: - raise NotImplementedError - - @cached_property - def name(self) -> str: - raise NotImplementedError + prereleases: bool + url: str + name: str + auth: Any @cached_property def from_config(self): diff --git a/mypy.ini b/mypy.ini index e128b5ae..78a98ac3 100644 --- a/mypy.ini +++ b/mypy.ini @@ -3,3 +3,4 @@ allow_redefinition = True follow_imports = silent ignore_missing_imports = True show_error_codes = True +warn_unused_ignores = True From c0eb9232f7ccd5dd816e79dba7a2956468b4e52c Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 24 Aug 2020 17:12:09 +0200 Subject: [PATCH 79/80] sort imports --- dephell/cached_property.pyi | 12 +++--------- dephell/controllers/_docker.py | 1 + dephell/controllers/_graph.py | 2 +- setup.py | 2 ++ 4 files changed, 7 insertions(+), 10 deletions(-) diff --git a/dephell/cached_property.pyi b/dephell/cached_property.pyi index 4aae4a6c..452d77d4 100644 --- a/dephell/cached_property.pyi +++ b/dephell/cached_property.pyi @@ -1,12 +1,6 @@ -from typing import ( - Any, - Callable, - Generic, - Optional, - Type, - TypeVar, - overload, -) +# built-in +from typing import Any, Callable, Generic, Optional, Type, TypeVar, overload + _AnyCallable = Callable[..., Any] diff --git a/dephell/controllers/_docker.py b/dephell/controllers/_docker.py index fe01297a..824c7c70 100644 --- a/dephell/controllers/_docker.py +++ b/dephell/controllers/_docker.py @@ -12,6 +12,7 @@ from ..imports import lazy_import from ..networking import requests_session + if TYPE_CHECKING: # external import docker diff --git a/dephell/controllers/_graph.py b/dephell/controllers/_graph.py index 9a9b831a..93e45219 100644 --- a/dephell/controllers/_graph.py +++ b/dephell/controllers/_graph.py @@ -1,7 +1,7 @@ # built-in from collections import ChainMap from logging import getLogger -from typing import Any, Dict, TYPE_CHECKING, Iterator, List, Optional +from typing import TYPE_CHECKING, Any, Dict, Iterator, List, Optional # app from ..imports import lazy_import diff --git a/setup.py b/setup.py index 0ac53acc..bc06fb97 100644 --- a/setup.py +++ b/setup.py @@ -8,8 +8,10 @@ # external from setuptools import setup except ImportError: + # built-in from distutils.core import setup +# built-in # built-in import os.path From de96f01fcfd8dd620b049369a8ec30dde566c5de Mon Sep 17 00:00:00 2001 From: Gram Date: Mon, 11 Jan 2021 22:31:39 +0100 Subject: [PATCH 80/80] Update README.md --- README.md | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/README.md b/README.md index a0817956..748cdf18 100644 --- a/README.md +++ b/README.md @@ -1,3 +1,9 @@ +# THE PROJECT IS ARCHIVED + +Forks: https://github.com/orsinium/forks + +--- + # ![DepHell](./assets/logo.png) [![pypi](https://img.shields.io/pypi/v/dephell.svg)](https://pypi.python.org/pypi/dephell/)