Initial Commit

This commit is contained in:
Timmy Welch 2023-04-27 11:29:06 -07:00
commit 03ac6f2277
No known key found for this signature in database
8 changed files with 294 additions and 0 deletions

1
.activate.sh Symbolic link
View File

@ -0,0 +1 @@
venv/bin/activate.xsh

1
.deactivate.sh Normal file
View File

@ -0,0 +1 @@
deactivate

85
.gitignore vendored Normal file
View File

@ -0,0 +1,85 @@
# Covers JetBrains IDEs: IntelliJ, RubyMine, PhpStorm, AppCode, PyCharm, CLion
*.iml
## Directory-based project format:
.idea/
### Other editors
.*.swp
nbproject/
.vscode
*.exe
*.zip
# Byte-compiled / optimized / DLL files
__pycache__/
*.py[cod]
*$py.class
# C extensions
*.so
# Distribution / packaging
.Python
build/
develop-eggs/
dist/
downloads/
eggs/
.eggs/
lib/
lib64/
parts/
sdist/
var/
wheels/
share/python-wheels/
*.egg-info/
.installed.cfg
*.egg
MANIFEST
# Installer logs
pip-log.txt
pip-delete-this-directory.txt
# Unit test / coverage reports
htmlcov/
.tox/
.nox/
.coverage
.coverage.*
.cache
nosetests.xml
coverage.xml
*.cover
*.py,cover
.hypothesis/
.pytest_cache/
cover/
# Environments
.env
.venv
env/
venv/
ENV/
env.bak/
venv.bak/
# mypy
.mypy_cache/
.dmypy.json
dmypy.json
# Pyre type checker
.pyre/
# pytype static type analyzer
.pytype/
# for testing
temp/
tmp/

39
.pre-commit-config.yaml Normal file
View File

@ -0,0 +1,39 @@
repos:
- repo: https://github.com/pre-commit/pre-commit-hooks
rev: v4.4.0
hooks:
- id: trailing-whitespace
- id: end-of-file-fixer
- id: check-yaml
- id: debug-statements
- id: double-quote-string-fixer
- id: name-tests-test
- id: requirements-txt-fixer
- repo: https://github.com/asottile/setup-cfg-fmt
rev: v2.2.0
hooks:
- id: setup-cfg-fmt
- repo: https://github.com/asottile/reorder_python_imports
rev: v3.9.0
hooks:
- id: reorder-python-imports
args: [--py38-plus, --add-import, 'from __future__ import annotations']
- repo: https://github.com/asottile/add-trailing-comma
rev: v2.4.0
hooks:
- id: add-trailing-comma
args: [--py36-plus]
- repo: https://github.com/asottile/pyupgrade
rev: v3.3.1
hooks:
- id: pyupgrade
args: [--py311-plus]
- repo: https://github.com/pre-commit/mirrors-autopep8
rev: v2.0.2
hooks:
- id: autopep8
- repo: https://github.com/PyCQA/flake8
rev: 6.0.0
hooks:
- id: flake8
additional_dependencies: [flake8-encodings, flake8-warnings, flake8-builtins, flake8-length, flake8-print]

6
pyproject.toml Normal file
View File

@ -0,0 +1,6 @@
[build-system]
requires = ["setuptools>=42", "wheel", "setuptools_scm[toml]>=3.4"]
build-backend = "setuptools.build_meta"
[tool.setuptools_scm]
local_scheme = "no-local-version"

73
setup.cfg Normal file
View File

@ -0,0 +1,73 @@
[metadata]
name = virtualenv_discovery_exclude_current
description = custom discovery that excludes current interpreter
author = Timmy Welch
author_email = timmy@narnian.us
license = MIT
classifiers =
Programming Language :: Python :: 3
Programming Language :: Python :: 3 :: Only
[options]
py_modules = virtualenv_discovery_exclude_current
install_requires =
virtualenv>=20.22.0
python_requires = >=3.7
[options.entry_points]
virtualenv.discovery =
monkeypatch = virtualenv_discovery_exclude_current:Mock
[tox:tox]
envlist = wheel
[testenv:wheel]
description = Generate wheel and tar.gz
labels =
release
build
skip_install = true
deps =
build
commands_pre =
-python -c 'import shutil,pathlib; \
shutil.rmtree("./build/", ignore_errors=True); \
shutil.rmtree("./dist/", ignore_errors=True)'
commands =
python -m build
[testenv:pypi-upload]
description = Upload wheel to PyPi
platform = Linux
labels =
release
skip_install = true
depends = wheel
deps =
twine
passenv =
TWINE_*
setenv =
TWINE_NON_INTERACTIVE=true
commands =
python -m twine upload dist/*.whl dist/*.tar.gz
[pep8]
ignore = E265,E501
max_line_length = 120
[flake8]
extend-ignore = E501, A003
max_line_length = 120
[coverage:run]
plugins = covdefaults
[coverage:report]
fail_under = 95
[mypy-testing.*]
disallow_untyped_defs = false
[mypy-tests.*]
disallow_untyped_defs = false

4
setup.py Normal file
View File

@ -0,0 +1,4 @@
from __future__ import annotations
from setuptools import setup
setup()

View File

@ -0,0 +1,85 @@
from __future__ import annotations
import logging
import os
from virtualenv.discovery.builtin import Builtin
from virtualenv.discovery.builtin import check_path
from virtualenv.discovery.builtin import get_paths
from virtualenv.discovery.builtin import LazyPathDump
from virtualenv.discovery.builtin import PathPythonInfo
from virtualenv.discovery.builtin import possible_specs
from virtualenv.discovery.py_info import PythonInfo
from virtualenv.discovery.py_spec import PythonSpec
# Same as Builtin, needed for scope
class Mock(Builtin):
def run(self):
for python_spec in self.python_spec:
result = get_interpreter(python_spec, self.try_first_with, self.app_data, self._env)
if result is not None:
return result
return None
# Same as builtin, needed for scope
def get_interpreter(key, try_first_with, app_data=None, env=None):
spec = PythonSpec.from_string_spec(key)
logging.info('find interpreter for spec %r', spec)
proposed_paths = set()
env = os.environ if env is None else env
for interpreter, impl_must_match in propose_interpreters(spec, try_first_with, app_data, env):
key = interpreter.system_executable, impl_must_match
if key in proposed_paths:
continue
logging.info('proposed %s', interpreter)
if interpreter.satisfies(spec, impl_must_match):
logging.debug('accepted %s', interpreter)
return interpreter
proposed_paths.add(key)
# Current interpreter is removed
def propose_interpreters(spec, try_first_with, app_data, env=None):
# 0. try with first
env = os.environ if env is None else env
for py_exe in try_first_with:
path = os.path.abspath(py_exe)
try:
# Windows Store Python does not work with os.path.exists, but does for os.lstat
os.lstat(path)
except OSError:
pass
else:
yield PythonInfo.from_exe(os.path.abspath(path), app_data, env=env), True
# 1. if it's a path and exists
if spec.path is not None:
try:
# Windows Store Python does not work with os.path.exists, but does for os.lstat
os.lstat(spec.path)
except OSError:
if spec.is_abs:
raise
else:
yield PythonInfo.from_exe(os.path.abspath(spec.path), app_data, env=env), True
if spec.is_abs:
return
# finally just find on path, the path order matters (as the candidates are less easy to control by end user)
paths = get_paths(env)
tested_exes = set()
for pos, path in enumerate(paths):
path_str = str(path)
logging.debug(LazyPathDump(pos, path_str, env))
for candidate, match in possible_specs(spec):
found = check_path(candidate, path_str)
if found is not None:
exe = os.path.abspath(found)
if exe not in tested_exes:
tested_exes.add(exe)
interpreter = PathPythonInfo.from_exe(exe, app_data, raise_on_error=False, env=env)
if interpreter is not None:
yield interpreter, match