quickpub 1.0.1__tar.gz → 1.0.2__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {quickpub-1.0.1/quickpub.egg-info → quickpub-1.0.2}/PKG-INFO +1 -1
- {quickpub-1.0.1 → quickpub-1.0.2}/pyproject.toml +1 -1
- {quickpub-1.0.1 → quickpub-1.0.2}/quickpub/__init__.py +1 -2
- {quickpub-1.0.1 → quickpub-1.0.2}/quickpub/__main__.py +76 -55
- {quickpub-1.0.1 → quickpub-1.0.2}/quickpub/enforcers.py +2 -2
- quickpub-1.0.2/quickpub/functions.py +72 -0
- {quickpub-1.0.1 → quickpub-1.0.2}/quickpub/qa.py +32 -21
- quickpub-1.0.2/quickpub/strategies/__init__.py +6 -0
- quickpub-1.0.2/quickpub/strategies/build_strategy.py +16 -0
- quickpub-1.0.2/quickpub/strategies/implementations/__init__.py +9 -0
- quickpub-1.0.1/quickpub/managers/implementations/conda.py → quickpub-1.0.2/quickpub/strategies/implementations/conda_python_version_manager_strategy.py +4 -4
- quickpub-1.0.2/quickpub/strategies/implementations/git_upload_strategy.py +26 -0
- quickpub-1.0.1/quickpub/runnables/implementations/mypy.py → quickpub-1.0.2/quickpub/strategies/implementations/mypy_qa_strategy.py +4 -4
- quickpub-1.0.1/quickpub/runnables/implementations/pylint.py → quickpub-1.0.2/quickpub/strategies/implementations/pylint_qa_strategy.py +4 -4
- quickpub-1.0.2/quickpub/strategies/implementations/pypirc_upload_strategy.py +44 -0
- quickpub-1.0.2/quickpub/strategies/implementations/pytest_qa_strategy.py +1 -0
- quickpub-1.0.2/quickpub/strategies/implementations/setuptools_build_strategy.py +21 -0
- {quickpub-1.0.1/quickpub/managers → quickpub-1.0.2/quickpub/strategies}/implementations/system_interpreter.py +3 -3
- quickpub-1.0.1/quickpub/runnables/implementations/unittest.py → quickpub-1.0.2/quickpub/strategies/implementations/unittest_qa_strategy.py +3 -3
- quickpub-1.0.1/quickpub/managers/python_manager.py → quickpub-1.0.2/quickpub/strategies/python_version_manager_strategy.py +4 -3
- quickpub-1.0.1/quickpub/runnables/base_runner.py → quickpub-1.0.2/quickpub/strategies/quality_assurance_strategy.py +44 -11
- quickpub-1.0.2/quickpub/strategies/quickpub_strategy.py +10 -0
- quickpub-1.0.2/quickpub/strategies/upload_strategy.py +16 -0
- {quickpub-1.0.1 → quickpub-1.0.2}/quickpub/structures/__init__.py +0 -1
- {quickpub-1.0.1 → quickpub-1.0.2/quickpub.egg-info}/PKG-INFO +1 -1
- quickpub-1.0.2/quickpub.egg-info/SOURCES.txt +40 -0
- quickpub-1.0.1/quickpub/functions.py +0 -209
- quickpub-1.0.1/quickpub/managers/__init__.py +0 -2
- quickpub-1.0.1/quickpub/managers/implementations/__init__.py +0 -2
- quickpub-1.0.1/quickpub/runnables/__init__.py +0 -2
- quickpub-1.0.1/quickpub/runnables/configurable.py +0 -20
- quickpub-1.0.1/quickpub/runnables/has_optional_executable.py +0 -32
- quickpub-1.0.1/quickpub/runnables/implementations/__init__.py +0 -4
- quickpub-1.0.1/quickpub/runnables/implementations/pytest.py +0 -2
- quickpub-1.0.1/quickpub/runnables/runnable.py +0 -11
- quickpub-1.0.1/quickpub/structures/additional_configuration.py +0 -15
- quickpub-1.0.1/quickpub.egg-info/SOURCES.txt +0 -40
- {quickpub-1.0.1 → quickpub-1.0.2}/LICENSE +0 -0
- {quickpub-1.0.1 → quickpub-1.0.2}/MANIFEST.in +0 -0
- {quickpub-1.0.1 → quickpub-1.0.2}/README.md +0 -0
- {quickpub-1.0.1 → quickpub-1.0.2}/quickpub/classifiers.py +0 -0
- {quickpub-1.0.1 → quickpub-1.0.2}/quickpub/files.py +0 -0
- {quickpub-1.0.1 → quickpub-1.0.2}/quickpub/proxy.py +0 -0
- {quickpub-1.0.1 → quickpub-1.0.2}/quickpub/py.typed +0 -0
- {quickpub-1.0.1 → quickpub-1.0.2}/quickpub/structures/bound.py +0 -0
- {quickpub-1.0.1 → quickpub-1.0.2}/quickpub/structures/dependency.py +0 -0
- {quickpub-1.0.1 → quickpub-1.0.2}/quickpub/structures/version.py +0 -0
- {quickpub-1.0.1 → quickpub-1.0.2}/quickpub/validators.py +0 -0
- {quickpub-1.0.1 → quickpub-1.0.2}/quickpub.egg-info/dependency_links.txt +0 -0
- {quickpub-1.0.1 → quickpub-1.0.2}/quickpub.egg-info/requires.txt +0 -0
- {quickpub-1.0.1 → quickpub-1.0.2}/quickpub.egg-info/top_level.txt +0 -0
- {quickpub-1.0.1 → quickpub-1.0.2}/setup.cfg +0 -0
- {quickpub-1.0.1 → quickpub-1.0.2}/setup.py +0 -0
|
@@ -1,11 +1,12 @@
|
|
|
1
1
|
import argparse
|
|
2
|
-
from typing import Optional, Union, List
|
|
2
|
+
from typing import Optional, Union, List, Any
|
|
3
3
|
from danielutils import warning, file_exists, error
|
|
4
4
|
|
|
5
|
+
from quickpub import SystemInterpreter
|
|
6
|
+
from strategies import BuildStrategy, UploadStrategy, QualityAssuranceStrategy, PythonVersionManagerStrategy
|
|
5
7
|
from .validators import validate_version, validate_python_version, validate_keywords, validate_dependencies, \
|
|
6
8
|
validate_source
|
|
7
|
-
from .
|
|
8
|
-
from .structures import Version, AdditionalConfiguration, Dependency
|
|
9
|
+
from .structures import Version, Dependency
|
|
9
10
|
from .files import create_toml, create_setup, create_manifest
|
|
10
11
|
from .classifiers import *
|
|
11
12
|
from .enforcers import enforce_local_correct_version, enforce_pypirc_exists, exit_if, enforce_remote_correct_version
|
|
@@ -19,6 +20,12 @@ def publish(
|
|
|
19
20
|
author_email: str,
|
|
20
21
|
description: str,
|
|
21
22
|
homepage: str,
|
|
23
|
+
|
|
24
|
+
build_strategies: List[BuildStrategy],
|
|
25
|
+
upload_strategies: List[UploadStrategy],
|
|
26
|
+
quality_assurance_strategies: Optional[List[QualityAssuranceStrategy]] = None,
|
|
27
|
+
python_version_manager_strategy: PythonVersionManagerStrategy = SystemInterpreter(),
|
|
28
|
+
|
|
22
29
|
explicit_src_folder_path: Optional[str] = None,
|
|
23
30
|
version: Optional[Union[Version, str]] = None,
|
|
24
31
|
readme_file_path: str = "./README.md",
|
|
@@ -28,25 +35,35 @@ def publish(
|
|
|
28
35
|
|
|
29
36
|
keywords: Optional[List[str]] = None,
|
|
30
37
|
dependencies: Optional[List[Union[str, Dependency]]] = None,
|
|
31
|
-
|
|
38
|
+
demo: bool = False,
|
|
39
|
+
|
|
40
|
+
config: Optional[Any] = None,
|
|
32
41
|
) -> None:
|
|
33
|
-
"""The main function
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
42
|
+
"""The main function for publishing a package. It performs all necessary steps to prepare and publish the package.
|
|
43
|
+
|
|
44
|
+
:param name: The name of the package.
|
|
45
|
+
:param author: The name of the author.
|
|
46
|
+
:param author_email: The email of the author.
|
|
47
|
+
:param description: A short description of the package.
|
|
48
|
+
:param homepage: The homepage URL for the package (e.g., GitHub repository).
|
|
49
|
+
:param quality_assurance_strategies: Strategies for quality assurance.
|
|
50
|
+
:param build_strategies: Strategies for building the package.
|
|
51
|
+
:param upload_strategies: Strategies for uploading the package.
|
|
52
|
+
:param python_version_manager_strategy: Strategy for managing Python versions. Defaults to SystemInterpreter().
|
|
53
|
+
:param explicit_src_folder_path: The path to the source code of the package. Defaults to the current working directory/<name>.
|
|
54
|
+
:param version: The version for the new distribution. Defaults to "0.0.1".
|
|
55
|
+
:param readme_file_path: The path to the README file. Defaults to "./README.md".
|
|
56
|
+
:param license_file_path: The path to the license file. Defaults to "./LICENSE".
|
|
57
|
+
:param min_python: The minimum Python version required for the package. Defaults to the Python version running this script.
|
|
58
|
+
:param keywords: A list of keywords describing areas of interest for the package. Defaults to None.
|
|
59
|
+
:param dependencies: A list of dependencies for the package. Defaults to None.
|
|
60
|
+
:param demo: Whether to perform checks without making any changes. Defaults to False.
|
|
61
|
+
:param config: Reserved for future use. Defaults to None.
|
|
62
|
+
|
|
63
|
+
Returns:
|
|
64
|
+
None
|
|
65
|
+
"""
|
|
66
|
+
|
|
50
67
|
enforce_pypirc_exists()
|
|
51
68
|
explicit_src_folder_path = validate_source(name, explicit_src_folder_path)
|
|
52
69
|
if explicit_src_folder_path != f"./{name}":
|
|
@@ -55,16 +72,27 @@ def publish(
|
|
|
55
72
|
exit_if(not file_exists(readme_file_path), f"Could not find readme file at {readme_file_path}")
|
|
56
73
|
exit_if(not file_exists(license_file_path), f"Could not find license file at {license_file_path}")
|
|
57
74
|
version = validate_version(version)
|
|
58
|
-
|
|
75
|
+
if not demo:
|
|
76
|
+
enforce_local_correct_version(name, version)
|
|
59
77
|
min_python = validate_python_version(min_python) # type:ignore
|
|
60
78
|
keywords = validate_keywords(keywords)
|
|
61
79
|
validated_dependencies: List[Dependency] = validate_dependencies(dependencies)
|
|
62
80
|
enforce_remote_correct_version(name, version)
|
|
63
81
|
|
|
82
|
+
if quality_assurance_strategies is None:
|
|
83
|
+
quality_assurance_strategies = []
|
|
64
84
|
try:
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
85
|
+
res = qa(
|
|
86
|
+
python_version_manager_strategy,
|
|
87
|
+
quality_assurance_strategies,
|
|
88
|
+
name,
|
|
89
|
+
explicit_src_folder_path,
|
|
90
|
+
validated_dependencies
|
|
91
|
+
)
|
|
92
|
+
if not res:
|
|
93
|
+
error(f"quickpub.publish exited early as '{name}' "
|
|
94
|
+
"did not pass quality assurance step, see above "
|
|
95
|
+
"logs to pass this step.")
|
|
68
96
|
raise SystemExit(1)
|
|
69
97
|
except SystemExit as e:
|
|
70
98
|
raise e
|
|
@@ -93,15 +121,11 @@ def publish(
|
|
|
93
121
|
min_python=min_python
|
|
94
122
|
)
|
|
95
123
|
create_manifest(name=name)
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
)
|
|
102
|
-
commit(
|
|
103
|
-
version=version
|
|
104
|
-
)
|
|
124
|
+
if not demo:
|
|
125
|
+
for build_strategy in build_strategies:
|
|
126
|
+
build_strategy.execute_strategy()
|
|
127
|
+
for upload_strategy in upload_strategies:
|
|
128
|
+
upload_strategy.execute_strategy(name=name, version=version)
|
|
105
129
|
|
|
106
130
|
|
|
107
131
|
def parse_args():
|
|
@@ -124,25 +148,22 @@ def parse_args():
|
|
|
124
148
|
return parser.parse_args()
|
|
125
149
|
|
|
126
150
|
|
|
127
|
-
def main():
|
|
128
|
-
args = parse_args()
|
|
129
|
-
|
|
130
|
-
publish(
|
|
131
|
-
name=args.name,
|
|
132
|
-
author=args.author,
|
|
133
|
-
author_email=args.author_email,
|
|
134
|
-
description=args.description,
|
|
135
|
-
homepage=args.homepage,
|
|
136
|
-
explicit_src_folder_path=args.explicit_src_folder_path,
|
|
137
|
-
version=args.version,
|
|
138
|
-
readme_file_path=args.readme_file_path,
|
|
139
|
-
license_file_path=args.license_file_path,
|
|
140
|
-
min_python=args.min_python,
|
|
141
|
-
keywords=args.keywords,
|
|
142
|
-
dependencies=args.dependencies,
|
|
143
|
-
config=args.config
|
|
144
|
-
)
|
|
145
|
-
|
|
146
|
-
|
|
147
151
|
if __name__ == '__main__':
|
|
148
|
-
|
|
152
|
+
print("CLI is not currently supported")
|
|
153
|
+
# args = parse_args()
|
|
154
|
+
#
|
|
155
|
+
# publish(
|
|
156
|
+
# name=args.name,
|
|
157
|
+
# author=args.author,
|
|
158
|
+
# author_email=args.author_email,
|
|
159
|
+
# description=args.description,
|
|
160
|
+
# homepage=args.homepage,
|
|
161
|
+
# explicit_src_folder_path=args.explicit_src_folder_path,
|
|
162
|
+
# version=args.version,
|
|
163
|
+
# readme_file_path=args.readme_file_path,
|
|
164
|
+
# license_file_path=args.license_file_path,
|
|
165
|
+
# min_python=args.min_python,
|
|
166
|
+
# keywords=args.keywords,
|
|
167
|
+
# dependencies=args.dependencies,
|
|
168
|
+
# config=args.config
|
|
169
|
+
# )
|
|
@@ -21,7 +21,7 @@ def _remove_suffix(s: str, suffix: str) -> str:
|
|
|
21
21
|
:return: modified string
|
|
22
22
|
"""
|
|
23
23
|
if get_python_version() >= (3, 9):
|
|
24
|
-
return s.removesuffix(suffix)
|
|
24
|
+
return s.removesuffix(suffix) # type:ignore
|
|
25
25
|
return _remove_prefix(s[::-1], suffix[::-1])[::-1]
|
|
26
26
|
|
|
27
27
|
|
|
@@ -33,7 +33,7 @@ def _remove_prefix(s: str, prefix: str) -> str:
|
|
|
33
33
|
:return:
|
|
34
34
|
"""
|
|
35
35
|
if get_python_version() >= (3, 9):
|
|
36
|
-
return s.removeprefix(prefix)
|
|
36
|
+
return s.removeprefix(prefix) # type:ignore
|
|
37
37
|
|
|
38
38
|
if s.startswith(prefix):
|
|
39
39
|
return s[len(prefix):]
|
|
@@ -0,0 +1,72 @@
|
|
|
1
|
+
import sys
|
|
2
|
+
from typing import Optional, Literal
|
|
3
|
+
from danielutils import info
|
|
4
|
+
|
|
5
|
+
from .enforcers import exit_if
|
|
6
|
+
from .structures import Version
|
|
7
|
+
import quickpub.proxy
|
|
8
|
+
|
|
9
|
+
|
|
10
|
+
def build(
|
|
11
|
+
*,
|
|
12
|
+
verbose: bool = True
|
|
13
|
+
) -> None:
|
|
14
|
+
if verbose:
|
|
15
|
+
info("Creating new distribution...")
|
|
16
|
+
ret, stdout, stderr = quickpub.proxy.cm("python", "setup.py", "sdist")
|
|
17
|
+
exit_if(
|
|
18
|
+
ret != 0,
|
|
19
|
+
stderr.decode(encoding="utf8")
|
|
20
|
+
)
|
|
21
|
+
|
|
22
|
+
|
|
23
|
+
def upload(
|
|
24
|
+
*,
|
|
25
|
+
name: str,
|
|
26
|
+
version: Version,
|
|
27
|
+
verbose: bool = True
|
|
28
|
+
) -> None:
|
|
29
|
+
if verbose:
|
|
30
|
+
info("Uploading")
|
|
31
|
+
ret, stdout, stderr = quickpub.proxy.cm("twine", "upload", "--config-file", ".pypirc",
|
|
32
|
+
f"dist/{name}-{version}.tar.gz")
|
|
33
|
+
exit_if(
|
|
34
|
+
ret != 0,
|
|
35
|
+
f"Failed uploading the package to pypi. Try running the following command manually:\n\ttwine upload --config-file .pypirc dist/{name}-{version}.tar.gz"
|
|
36
|
+
)
|
|
37
|
+
|
|
38
|
+
|
|
39
|
+
def commit(
|
|
40
|
+
*,
|
|
41
|
+
version: Version,
|
|
42
|
+
verbose: bool = True
|
|
43
|
+
) -> None:
|
|
44
|
+
if verbose:
|
|
45
|
+
info("Git")
|
|
46
|
+
info("\tStaging")
|
|
47
|
+
ret, stdout, stderr = quickpub.proxy.cm("git add .")
|
|
48
|
+
exit_if(
|
|
49
|
+
ret != 0,
|
|
50
|
+
stderr.decode(encoding="utf8")
|
|
51
|
+
)
|
|
52
|
+
if verbose:
|
|
53
|
+
info("\tCommitting")
|
|
54
|
+
ret, stdout, stderr = quickpub.proxy.cm(f"git commit -m \"updated to version {version}\"")
|
|
55
|
+
exit_if(
|
|
56
|
+
ret != 0,
|
|
57
|
+
stderr.decode(encoding="utf8")
|
|
58
|
+
)
|
|
59
|
+
if verbose:
|
|
60
|
+
info("\tPushing")
|
|
61
|
+
ret, stdout, stderr = quickpub.proxy.cm("git push")
|
|
62
|
+
exit_if(
|
|
63
|
+
ret != 0,
|
|
64
|
+
stderr.decode(encoding="utf8")
|
|
65
|
+
)
|
|
66
|
+
|
|
67
|
+
|
|
68
|
+
__all__ = [
|
|
69
|
+
"build",
|
|
70
|
+
"upload",
|
|
71
|
+
"commit",
|
|
72
|
+
]
|
|
@@ -4,8 +4,9 @@ from functools import wraps
|
|
|
4
4
|
from typing import Optional, ContextManager, List, Callable, Tuple, Dict, Union
|
|
5
5
|
from danielutils import AttrContext, LayeredCommand, AsciiProgressBar, ColoredText, ProgressBarPool, TemporaryFile
|
|
6
6
|
|
|
7
|
-
from
|
|
8
|
-
from .
|
|
7
|
+
from quickpub import QualityAssuranceStrategy
|
|
8
|
+
from .strategies import PythonVersionManagerStrategy # pylint: disable=relative-beyond-top-level
|
|
9
|
+
from .structures import Dependency, Version, Bound # pylint: disable=relative-beyond-top-level
|
|
9
10
|
from .enforcers import exit_if # pylint: disable=relative-beyond-top-level
|
|
10
11
|
|
|
11
12
|
try:
|
|
@@ -53,7 +54,7 @@ def global_import_sanity_check(package_name: str, executor: LayeredCommand, is_s
|
|
|
53
54
|
VERSION_REGEX: re.Pattern = re.compile(r"^\d+\.\d+\.\d+$")
|
|
54
55
|
|
|
55
56
|
|
|
56
|
-
def validate_dependencies(python_manager:
|
|
57
|
+
def validate_dependencies(python_manager: PythonVersionManagerStrategy, required_dependencies: List[Dependency],
|
|
57
58
|
executor: LayeredCommand,
|
|
58
59
|
env_name: str, err_print_func: Callable) -> None:
|
|
59
60
|
"""
|
|
@@ -92,13 +93,22 @@ def validate_dependencies(python_manager: PythonManager, required_dependencies:
|
|
|
92
93
|
err_func=err_print_func)
|
|
93
94
|
|
|
94
95
|
|
|
95
|
-
def create_progress_bar_pool(
|
|
96
|
+
def create_progress_bar_pool(python_version_manager: PythonVersionManagerStrategy,
|
|
97
|
+
quality_assurance_strategies: List[QualityAssuranceStrategy]) -> ProgressBarPool:
|
|
96
98
|
return ProgressBarPool(
|
|
97
99
|
AsciiProgressBar,
|
|
98
100
|
2,
|
|
99
101
|
individual_options=[
|
|
100
|
-
dict(
|
|
101
|
-
|
|
102
|
+
dict(
|
|
103
|
+
iterator=python_version_manager,
|
|
104
|
+
desc="Envs",
|
|
105
|
+
total=len(python_version_manager.requested_envs)
|
|
106
|
+
),
|
|
107
|
+
dict(
|
|
108
|
+
iterator=quality_assurance_strategies or [],
|
|
109
|
+
desc="Runners",
|
|
110
|
+
total=len(quality_assurance_strategies or [])
|
|
111
|
+
),
|
|
102
112
|
]
|
|
103
113
|
)
|
|
104
114
|
|
|
@@ -112,18 +122,19 @@ def create_pool_print_error(pool: ProgressBarPool):
|
|
|
112
122
|
return func
|
|
113
123
|
|
|
114
124
|
|
|
115
|
-
def qa(
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
125
|
+
def qa(
|
|
126
|
+
python_version_manager: PythonVersionManagerStrategy,
|
|
127
|
+
quality_assurance_strategies: List[QualityAssuranceStrategy],
|
|
128
|
+
package_name: str,
|
|
129
|
+
src_folder_path: Optional[str],
|
|
130
|
+
dependencies: list
|
|
131
|
+
) -> bool:
|
|
132
|
+
from .strategies import SystemInterpreter
|
|
119
133
|
result = True
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
python_manager = SystemInterpreter()
|
|
125
|
-
is_system_interpreter = True
|
|
126
|
-
pool = create_progress_bar_pool(config, python_manager)
|
|
134
|
+
if python_version_manager is None:
|
|
135
|
+
python_version_manager = SystemInterpreter()
|
|
136
|
+
is_system_interpreter = isinstance(python_version_manager, SystemInterpreter)
|
|
137
|
+
pool = create_progress_bar_pool(python_version_manager, quality_assurance_strategies)
|
|
127
138
|
pool_err = create_pool_print_error(pool)
|
|
128
139
|
with MultiContext(
|
|
129
140
|
AttrContext(LayeredCommand, 'class_flush_stdout', False),
|
|
@@ -137,7 +148,7 @@ def qa(package_name: str, config: Optional[AdditionalConfiguration], src_folder_
|
|
|
137
148
|
with executor:
|
|
138
149
|
executor._prev_instance = base
|
|
139
150
|
try:
|
|
140
|
-
validate_dependencies(
|
|
151
|
+
validate_dependencies(python_version_manager, dependencies, executor, env_name, pool_err)
|
|
141
152
|
except SystemExit:
|
|
142
153
|
result = False
|
|
143
154
|
continue
|
|
@@ -154,7 +165,7 @@ def qa(package_name: str, config: Optional[AdditionalConfiguration], src_folder_
|
|
|
154
165
|
src_folder_path,
|
|
155
166
|
executor,
|
|
156
167
|
use_system_interpreter=is_system_interpreter,
|
|
157
|
-
raise_on_fail=
|
|
168
|
+
raise_on_fail=python_version_manager.exit_on_fail,
|
|
158
169
|
print_func=pool_err,
|
|
159
170
|
env_name=env_name
|
|
160
171
|
)
|
|
@@ -168,8 +179,8 @@ def qa(package_name: str, config: Optional[AdditionalConfiguration], src_folder_
|
|
|
168
179
|
f"Failed running '{runner.__class__.__name__}' on env '{env_name}'. "
|
|
169
180
|
f"Try manually: '{manual_command}'.")
|
|
170
181
|
pool.write(f"\tCaused by '{e.__cause__ or e}'")
|
|
171
|
-
if
|
|
172
|
-
raise e
|
|
182
|
+
if python_version_manager.exit_on_fail:
|
|
183
|
+
raise RuntimeError() from e
|
|
173
184
|
return result
|
|
174
185
|
|
|
175
186
|
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
from abc import abstractmethod
|
|
2
|
+
|
|
3
|
+
from .quickpub_strategy import QuickpubStrategy
|
|
4
|
+
|
|
5
|
+
|
|
6
|
+
class BuildStrategy(QuickpubStrategy):
|
|
7
|
+
def __init__(self, verbose: bool = True) -> None:
|
|
8
|
+
self.verbose = verbose
|
|
9
|
+
|
|
10
|
+
@abstractmethod
|
|
11
|
+
def execute_strategy(self, *args, **kwargs) -> None: ...
|
|
12
|
+
|
|
13
|
+
|
|
14
|
+
__all__ = [
|
|
15
|
+
"BuildStrategy"
|
|
16
|
+
]
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
from .pypirc_upload_strategy import *
|
|
2
|
+
from .git_upload_strategy import *
|
|
3
|
+
from .setuptools_build_strategy import *
|
|
4
|
+
from .mypy_qa_strategy import *
|
|
5
|
+
from .pylint_qa_strategy import *
|
|
6
|
+
from .pytest_qa_strategy import *
|
|
7
|
+
from .unittest_qa_strategy import *
|
|
8
|
+
from .conda_python_version_manager_strategy import *
|
|
9
|
+
from .system_interpreter import *
|
|
@@ -1,15 +1,15 @@
|
|
|
1
1
|
from typing import Tuple, Optional, Set, Iterator, List
|
|
2
2
|
from danielutils import LayeredCommand, warning
|
|
3
3
|
|
|
4
|
-
from ..
|
|
4
|
+
from ..python_version_manager_strategy import PythonVersionManagerStrategy
|
|
5
5
|
|
|
6
6
|
|
|
7
|
-
class
|
|
7
|
+
class CondaPythonVersionManagerStrategy(PythonVersionManagerStrategy):
|
|
8
8
|
def get_python_executable_name(self) -> str:
|
|
9
9
|
return "python"
|
|
10
10
|
|
|
11
11
|
def __init__(self, env_names: List[str]) -> None:
|
|
12
|
-
|
|
12
|
+
PythonVersionManagerStrategy.__init__(self, requested_envs=env_names, explicit_versions=[], exit_on_fail=True)
|
|
13
13
|
self._cached_available_envs: Optional[Set[str]] = None
|
|
14
14
|
|
|
15
15
|
def get_available_envs(self) -> Set[str]:
|
|
@@ -33,5 +33,5 @@ class CondaPythonManager(PythonManager):
|
|
|
33
33
|
|
|
34
34
|
|
|
35
35
|
__all__ = [
|
|
36
|
-
'
|
|
36
|
+
'CondaPythonVersionManagerStrategy',
|
|
37
37
|
]
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
from danielutils import info
|
|
2
|
+
|
|
3
|
+
from ..upload_strategy import UploadStrategy
|
|
4
|
+
|
|
5
|
+
class GitUploadStrategy(UploadStrategy):
|
|
6
|
+
def execute_strategy(self, version: str, **kwargs) -> None:
|
|
7
|
+
from quickpub.proxy import cm
|
|
8
|
+
from quickpub.enforcers import exit_if
|
|
9
|
+
if self.verbose:
|
|
10
|
+
info("Git")
|
|
11
|
+
info("\tStaging")
|
|
12
|
+
ret, stdout, stderr = cm("git add .")
|
|
13
|
+
exit_if(ret != 0, stderr.decode(encoding="utf8"))
|
|
14
|
+
if self.verbose:
|
|
15
|
+
info("\tCommitting")
|
|
16
|
+
ret, stdout, stderr = cm(f"git commit -m \"updated to version {version}\"")
|
|
17
|
+
exit_if(ret != 0, stderr.decode(encoding="utf8"))
|
|
18
|
+
if self.verbose:
|
|
19
|
+
info("\tPushing")
|
|
20
|
+
ret, stdout, stderr = cm("git push")
|
|
21
|
+
exit_if(ret != 0, stderr.decode(encoding="utf8"))
|
|
22
|
+
|
|
23
|
+
|
|
24
|
+
__all__ = [
|
|
25
|
+
"GitUploadStrategy",
|
|
26
|
+
]
|
|
@@ -3,10 +3,10 @@ from typing import Optional, List
|
|
|
3
3
|
|
|
4
4
|
from danielutils import LayeredCommand
|
|
5
5
|
|
|
6
|
-
from ..
|
|
6
|
+
from ..quality_assurance_strategy import QualityAssuranceStrategy
|
|
7
7
|
|
|
8
8
|
|
|
9
|
-
class MypyRunner(
|
|
9
|
+
class MypyRunner(QualityAssuranceStrategy):
|
|
10
10
|
def _install_dependencies(self, base: LayeredCommand) -> None:
|
|
11
11
|
with base:
|
|
12
12
|
base("pip install pylint")
|
|
@@ -23,8 +23,8 @@ class MypyRunner(BaseRunner):
|
|
|
23
23
|
|
|
24
24
|
def __init__(self, bound: str = "<15", configuration_path: Optional[str] = None,
|
|
25
25
|
executable_path: Optional[str] = None) -> None:
|
|
26
|
-
|
|
27
|
-
|
|
26
|
+
QualityAssuranceStrategy.__init__(self, name="mypy", bound=bound, configuration_path=configuration_path,
|
|
27
|
+
executable_path=executable_path)
|
|
28
28
|
|
|
29
29
|
def _calculate_score(self, ret, lines: List[str], verbose: bool = False) -> float:
|
|
30
30
|
from ...enforcers import exit_if
|
|
@@ -3,10 +3,10 @@ from typing import Optional, List
|
|
|
3
3
|
|
|
4
4
|
from danielutils import LayeredCommand
|
|
5
5
|
|
|
6
|
-
from
|
|
6
|
+
from strategies.quality_assurance_strategy import QualityAssuranceStrategy
|
|
7
7
|
|
|
8
8
|
|
|
9
|
-
class PylintRunner(
|
|
9
|
+
class PylintRunner(QualityAssuranceStrategy):
|
|
10
10
|
def _install_dependencies(self, base: LayeredCommand) -> None:
|
|
11
11
|
with base:
|
|
12
12
|
base("pip install pylint")
|
|
@@ -15,8 +15,8 @@ class PylintRunner(BaseRunner):
|
|
|
15
15
|
|
|
16
16
|
def __init__(self, bound: str = ">=0.8", configuration_path: Optional[str] = None,
|
|
17
17
|
executable_path: Optional[str] = None) -> None:
|
|
18
|
-
|
|
19
|
-
|
|
18
|
+
QualityAssuranceStrategy.__init__(self, name="pylint", bound=bound, configuration_path=configuration_path,
|
|
19
|
+
executable_path=executable_path)
|
|
20
20
|
|
|
21
21
|
def _build_command(self, target: str, use_system_interpreter: bool = False) -> str:
|
|
22
22
|
command: str = self.get_executable()
|
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
import re
|
|
2
|
+
|
|
3
|
+
from danielutils import file_exists, info
|
|
4
|
+
|
|
5
|
+
from ..upload_strategy import UploadStrategy
|
|
6
|
+
|
|
7
|
+
|
|
8
|
+
class PypircUploadStrategy(UploadStrategy):
|
|
9
|
+
REGEX_PATTERN: re.Pattern = re.compile(
|
|
10
|
+
r"\[distutils\]\nindex-servers =\n pypi\n testpypi\n\n\[pypi\]\nusername = __token__\npassword = .+\n\n\[testpypi\]\nusername = __token__\npassword = .+\n")
|
|
11
|
+
|
|
12
|
+
def execute_strategy(self, *, name: str, version: str, **kwargs) -> None:
|
|
13
|
+
from quickpub.proxy import cm
|
|
14
|
+
from quickpub.enforcers import exit_if
|
|
15
|
+
self._validate_file_exists()
|
|
16
|
+
self._validate_file_contents()
|
|
17
|
+
if self.verbose:
|
|
18
|
+
info("Uploading")
|
|
19
|
+
ret, stdout, stderr = cm("twine", "upload", "--config-file", ".pypirc",
|
|
20
|
+
f"dist/{name}-{version}.tar.gz")
|
|
21
|
+
exit_if(
|
|
22
|
+
ret != 0,
|
|
23
|
+
f"Failed uploading the package to pypi. Try running the following command manually:\n\ttwine upload --config-file .pypirc dist/{name}-{version}.tar.gz"
|
|
24
|
+
)
|
|
25
|
+
|
|
26
|
+
def _validate_file_exists(self) -> None:
|
|
27
|
+
if not file_exists(self.pypirc_file_path):
|
|
28
|
+
raise RuntimeError(f"{self.__class__.__name__} can't find pypirc file at '{self.pypirc_file_path}'")
|
|
29
|
+
|
|
30
|
+
def _validate_file_contents(self) -> None:
|
|
31
|
+
with open(self.pypirc_file_path, "r", encoding="utf8") as f:
|
|
32
|
+
text = f.read()
|
|
33
|
+
if not self.REGEX_PATTERN.match(text):
|
|
34
|
+
raise RuntimeError(
|
|
35
|
+
f"{self.__class__.__name__} checked the contents of '{self.pypirc_file_path}' and it failed to match the following regex: {self.REGEX_PATTERN.pattern}")
|
|
36
|
+
|
|
37
|
+
def __init__(self, pypirc_file_path: str = "./.pypirc", verbose: bool = False) -> None:
|
|
38
|
+
super().__init__(verbose)
|
|
39
|
+
self.pypirc_file_path = pypirc_file_path
|
|
40
|
+
|
|
41
|
+
|
|
42
|
+
__all__ = [
|
|
43
|
+
"PypircUploadStrategy"
|
|
44
|
+
]
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
# TODO
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
from danielutils import info
|
|
2
|
+
|
|
3
|
+
from ..build_strategy import BuildStrategy
|
|
4
|
+
|
|
5
|
+
|
|
6
|
+
class SetuptoolsBuildStrategy(BuildStrategy):
|
|
7
|
+
def execute_strategy(self, *args, **kwargs) -> None:
|
|
8
|
+
from quickpub.proxy import cm
|
|
9
|
+
from quickpub.enforcers import exit_if
|
|
10
|
+
if self.verbose:
|
|
11
|
+
info("Creating new distribution...")
|
|
12
|
+
ret, stdout, stderr = cm("python", "setup.py", "sdist")
|
|
13
|
+
exit_if(
|
|
14
|
+
ret != 0,
|
|
15
|
+
stderr.decode(encoding="utf8")
|
|
16
|
+
)
|
|
17
|
+
|
|
18
|
+
|
|
19
|
+
__all__ = [
|
|
20
|
+
"SetuptoolsBuildStrategy",
|
|
21
|
+
]
|
|
@@ -3,15 +3,15 @@ from typing import Set, Tuple, Iterator
|
|
|
3
3
|
|
|
4
4
|
from danielutils import LayeredCommand
|
|
5
5
|
|
|
6
|
-
from .. import
|
|
6
|
+
from ..python_version_manager_strategy import PythonVersionManagerStrategy
|
|
7
7
|
|
|
8
8
|
|
|
9
|
-
class SystemInterpreter(
|
|
9
|
+
class SystemInterpreter(PythonVersionManagerStrategy):
|
|
10
10
|
def get_python_executable_name(self) -> str:
|
|
11
11
|
return sys.executable
|
|
12
12
|
|
|
13
13
|
def __init__(self) -> None:
|
|
14
|
-
|
|
14
|
+
PythonVersionManagerStrategy.__init__(self, requested_envs=["system"], explicit_versions=[], exit_on_fail=True)
|
|
15
15
|
|
|
16
16
|
def __iter__(self) -> Iterator[Tuple[str, LayeredCommand]]:
|
|
17
17
|
return iter([("system", LayeredCommand(""))])
|
|
@@ -3,10 +3,10 @@ import os
|
|
|
3
3
|
from typing import Optional, List
|
|
4
4
|
from danielutils import get_current_working_directory, set_current_working_directory, LayeredCommand, warning
|
|
5
5
|
|
|
6
|
-
from
|
|
6
|
+
from strategies.quality_assurance_strategy import QualityAssuranceStrategy
|
|
7
7
|
|
|
8
8
|
|
|
9
|
-
class UnittestRunner(
|
|
9
|
+
class UnittestRunner(QualityAssuranceStrategy):
|
|
10
10
|
def _install_dependencies(self, base: LayeredCommand) -> None:
|
|
11
11
|
return None
|
|
12
12
|
|
|
@@ -23,7 +23,7 @@ class UnittestRunner(BaseRunner):
|
|
|
23
23
|
RATING_PATTERN: re.Pattern = re.compile(r".*?([\d\.\/]+)")
|
|
24
24
|
|
|
25
25
|
def __init__(self, target: Optional[str] = "./tests", bound: str = ">=0.8") -> None:
|
|
26
|
-
|
|
26
|
+
QualityAssuranceStrategy.__init__(self, name="unittest", bound=bound, target=target)
|
|
27
27
|
self._cwd = ""
|
|
28
28
|
|
|
29
29
|
def _build_command(self, src: str, *args, use_system_interpreter: bool = False) -> str:
|