omdev 0.0.0.dev31__py3-none-any.whl → 0.0.0.dev33__py3-none-any.whl
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.
Potentially problematic release.
This version of omdev might be problematic. Click here for more details.
- omdev/.manifests.json +122 -1
- omdev/__about__.py +8 -0
- omdev/amalg/__main__.py +7 -0
- omdev/amalg/amalg.py +4 -4
- omdev/cexts/_boilerplate.cc +1 -1
- omdev/cexts/cmake.py +5 -0
- omdev/cexts/magic.py +1 -1
- omdev/classdot.py +6 -0
- omdev/cli/__init__.py +1 -0
- omdev/cli/__main__.py +4 -0
- omdev/cli/main.py +59 -0
- omdev/cli/types.py +7 -0
- omdev/interp/__main__.py +7 -0
- omdev/interp/cli.py +13 -5
- omdev/interp/pyenv.py +54 -12
- omdev/manifests/__init__.py +2 -0
- omdev/{manifests.py → manifests/build.py} +29 -60
- omdev/manifests/load.py +149 -0
- omdev/manifests/types.py +16 -0
- omdev/precheck/precheck.py +6 -0
- omdev/pyproject/__main__.py +7 -0
- omdev/pyproject/cli.py +1 -1
- omdev/pyproject/pkg.py +93 -2
- omdev/pyproject/reqs.py +1 -1
- omdev/scripts/interp.py +65 -17
- omdev/scripts/pyproject.py +157 -18
- omdev/toml/writer.py +8 -1
- omdev/tools/dockertools.py +6 -0
- omdev/tools/gittools.py +6 -0
- omdev/tools/piptools.py +6 -0
- omdev/tools/sqlrepl.py +6 -0
- {omdev-0.0.0.dev31.dist-info → omdev-0.0.0.dev33.dist-info}/METADATA +2 -2
- {omdev-0.0.0.dev31.dist-info → omdev-0.0.0.dev33.dist-info}/RECORD +37 -29
- omdev-0.0.0.dev33.dist-info/entry_points.txt +2 -0
- {omdev-0.0.0.dev31.dist-info → omdev-0.0.0.dev33.dist-info}/LICENSE +0 -0
- {omdev-0.0.0.dev31.dist-info → omdev-0.0.0.dev33.dist-info}/WHEEL +0 -0
- {omdev-0.0.0.dev31.dist-info → omdev-0.0.0.dev33.dist-info}/top_level.txt +0 -0
omdev/manifests/load.py
ADDED
|
@@ -0,0 +1,149 @@
|
|
|
1
|
+
# ruff: noqa: UP006 UP007
|
|
2
|
+
import dataclasses as dc
|
|
3
|
+
import importlib.machinery
|
|
4
|
+
import importlib.metadata
|
|
5
|
+
import importlib.resources
|
|
6
|
+
import json
|
|
7
|
+
import typing as ta
|
|
8
|
+
|
|
9
|
+
from .types import Manifest
|
|
10
|
+
|
|
11
|
+
|
|
12
|
+
##
|
|
13
|
+
|
|
14
|
+
|
|
15
|
+
class ManifestLoader:
|
|
16
|
+
def __init__(
|
|
17
|
+
self,
|
|
18
|
+
*,
|
|
19
|
+
module_remap: ta.Optional[ta.Mapping[str, str]] = None,
|
|
20
|
+
) -> None:
|
|
21
|
+
super().__init__()
|
|
22
|
+
|
|
23
|
+
self._module_remap = module_remap or {}
|
|
24
|
+
self._module_reverse_remap = {v: k for k, v in self._module_remap.items()}
|
|
25
|
+
|
|
26
|
+
self._cls_cache: ta.Dict[str, type] = {}
|
|
27
|
+
self._raw_cache: ta.Dict[str, ta.Optional[ta.Sequence[Manifest]]] = {}
|
|
28
|
+
|
|
29
|
+
@classmethod
|
|
30
|
+
def from_entry_point(
|
|
31
|
+
cls,
|
|
32
|
+
globals: ta.Mapping[str, ta.Any], # noqa
|
|
33
|
+
*,
|
|
34
|
+
module_remap: ta.Optional[ta.Mapping[str, str]] = None,
|
|
35
|
+
**kwargs: ta.Any,
|
|
36
|
+
) -> 'ManifestLoader':
|
|
37
|
+
rm: ta.Dict[str, str] = {}
|
|
38
|
+
|
|
39
|
+
if module_remap:
|
|
40
|
+
rm.update(module_remap)
|
|
41
|
+
|
|
42
|
+
if '__name__' in globals and '__spec__' in globals:
|
|
43
|
+
name: str = globals['__name__']
|
|
44
|
+
spec: importlib.machinery.ModuleSpec = globals['__spec__']
|
|
45
|
+
if '__main__' not in rm and name == '__main__':
|
|
46
|
+
rm[spec.name] = '__main__'
|
|
47
|
+
|
|
48
|
+
return cls(module_remap=rm, **kwargs)
|
|
49
|
+
|
|
50
|
+
def load_cls(self, key: str) -> type:
|
|
51
|
+
try:
|
|
52
|
+
return self._cls_cache[key]
|
|
53
|
+
except KeyError:
|
|
54
|
+
pass
|
|
55
|
+
|
|
56
|
+
if not key.startswith('$'):
|
|
57
|
+
raise Exception(f'Bad key: {key}')
|
|
58
|
+
|
|
59
|
+
parts = key[1:].split('.')
|
|
60
|
+
pos = next(i for i, p in enumerate(parts) if p[0].isupper())
|
|
61
|
+
|
|
62
|
+
mod_name = '.'.join(parts[:pos])
|
|
63
|
+
mod_name = self._module_remap.get(mod_name, mod_name)
|
|
64
|
+
mod = importlib.import_module(mod_name)
|
|
65
|
+
|
|
66
|
+
obj: ta.Any = mod
|
|
67
|
+
for ca in parts[pos:]:
|
|
68
|
+
obj = getattr(obj, ca)
|
|
69
|
+
|
|
70
|
+
cls = obj
|
|
71
|
+
if not isinstance(cls, type):
|
|
72
|
+
raise TypeError(cls)
|
|
73
|
+
|
|
74
|
+
self._cls_cache[key] = cls
|
|
75
|
+
return cls
|
|
76
|
+
|
|
77
|
+
def load_raw(self, pkg_name: str) -> ta.Optional[ta.Sequence[Manifest]]:
|
|
78
|
+
try:
|
|
79
|
+
return self._raw_cache[pkg_name]
|
|
80
|
+
except KeyError:
|
|
81
|
+
pass
|
|
82
|
+
|
|
83
|
+
t = importlib.resources.files(pkg_name).joinpath('.manifests.json')
|
|
84
|
+
if not t.is_file():
|
|
85
|
+
self._raw_cache[pkg_name] = None
|
|
86
|
+
return None
|
|
87
|
+
|
|
88
|
+
src = t.read_text('utf-8')
|
|
89
|
+
obj = json.loads(src)
|
|
90
|
+
if not isinstance(obj, (list, tuple)):
|
|
91
|
+
raise TypeError(obj)
|
|
92
|
+
|
|
93
|
+
lst: ta.List[Manifest] = []
|
|
94
|
+
for e in obj:
|
|
95
|
+
m = Manifest(**e)
|
|
96
|
+
|
|
97
|
+
m = dc.replace(m, module=pkg_name + m.module)
|
|
98
|
+
|
|
99
|
+
[(key, value_dct)] = m.value.items()
|
|
100
|
+
if not key.startswith('$'):
|
|
101
|
+
raise Exception(f'Bad key: {key}')
|
|
102
|
+
if key.startswith('$.'):
|
|
103
|
+
key = f'${pkg_name}{key[1:]}'
|
|
104
|
+
m = dc.replace(m, value={key: value_dct})
|
|
105
|
+
|
|
106
|
+
lst.append(m)
|
|
107
|
+
|
|
108
|
+
self._raw_cache[pkg_name] = lst
|
|
109
|
+
return lst
|
|
110
|
+
|
|
111
|
+
def load(
|
|
112
|
+
self,
|
|
113
|
+
*pkg_names: str,
|
|
114
|
+
only: ta.Optional[ta.Iterable[type]] = None,
|
|
115
|
+
) -> ta.Sequence[Manifest]:
|
|
116
|
+
only_keys: ta.Optional[ta.Set]
|
|
117
|
+
if only is not None:
|
|
118
|
+
only_keys = set()
|
|
119
|
+
for cls in only:
|
|
120
|
+
if not (isinstance(cls, type) and dc.is_dataclass(cls)):
|
|
121
|
+
raise TypeError(cls)
|
|
122
|
+
mod_name = cls.__module__
|
|
123
|
+
mod_name = self._module_reverse_remap.get(mod_name, mod_name)
|
|
124
|
+
only_keys.add(f'${mod_name}.{cls.__qualname__}')
|
|
125
|
+
else:
|
|
126
|
+
only_keys = None
|
|
127
|
+
|
|
128
|
+
lst: ta.List[Manifest] = []
|
|
129
|
+
for pn in pkg_names:
|
|
130
|
+
for manifest in (self.load_raw(pn) or []):
|
|
131
|
+
[(key, value_dct)] = manifest.value.items()
|
|
132
|
+
if only_keys is not None and key not in only_keys:
|
|
133
|
+
continue
|
|
134
|
+
|
|
135
|
+
cls = self.load_cls(key)
|
|
136
|
+
value = cls(**value_dct)
|
|
137
|
+
|
|
138
|
+
manifest = dc.replace(manifest, value=value)
|
|
139
|
+
lst.append(manifest)
|
|
140
|
+
|
|
141
|
+
return lst
|
|
142
|
+
|
|
143
|
+
ENTRY_POINT_GROUP = 'omlish.manifests'
|
|
144
|
+
|
|
145
|
+
def discover(self) -> ta.Sequence[str]:
|
|
146
|
+
return [
|
|
147
|
+
ep.value
|
|
148
|
+
for ep in importlib.metadata.entry_points(group=self.ENTRY_POINT_GROUP)
|
|
149
|
+
]
|
omdev/manifests/types.py
ADDED
omdev/precheck/precheck.py
CHANGED
|
@@ -2,6 +2,7 @@
|
|
|
2
2
|
Tiny pre-commit
|
|
3
3
|
|
|
4
4
|
TODO:
|
|
5
|
+
- ! manifests
|
|
5
6
|
- global config
|
|
6
7
|
- global analyses - FilesWithShebang
|
|
7
8
|
- shebang files have no relative imports
|
|
@@ -26,6 +27,7 @@ import typing as ta
|
|
|
26
27
|
|
|
27
28
|
from omlish import logs
|
|
28
29
|
|
|
30
|
+
from ..cli import CliModule
|
|
29
31
|
from .base import Precheck
|
|
30
32
|
from .base import PrecheckContext
|
|
31
33
|
from .git import GitBlacklistPrecheck
|
|
@@ -85,6 +87,10 @@ def _build_parser() -> argparse.ArgumentParser:
|
|
|
85
87
|
return parser
|
|
86
88
|
|
|
87
89
|
|
|
90
|
+
# @omlish-manifest
|
|
91
|
+
_CLI_MODULE = CliModule('precheck', __name__)
|
|
92
|
+
|
|
93
|
+
|
|
88
94
|
def _main(argv: ta.Sequence[str] | None = None) -> None:
|
|
89
95
|
logs.configure_standard_logging('INFO')
|
|
90
96
|
|
omdev/pyproject/__main__.py
CHANGED
omdev/pyproject/cli.py
CHANGED
omdev/pyproject/pkg.py
CHANGED
|
@@ -295,7 +295,15 @@ class PyprojectPackageGenerator(BasePyprojectPackageGenerator):
|
|
|
295
295
|
**extras,
|
|
296
296
|
}
|
|
297
297
|
|
|
298
|
-
|
|
298
|
+
if (eps := prj.pop('entry_points', None)):
|
|
299
|
+
pyp_dct['project.entry-points'] = {TomlWriter.Literal(f"'{k}'"): v for k, v in eps.items()} # type: ignore # noqa
|
|
300
|
+
|
|
301
|
+
if (scs := prj.pop('scripts', None)):
|
|
302
|
+
pyp_dct['project.scripts'] = scs
|
|
303
|
+
|
|
304
|
+
prj.pop('cli_scripts', None)
|
|
305
|
+
|
|
306
|
+
##
|
|
299
307
|
|
|
300
308
|
st = dict(specs.setuptools)
|
|
301
309
|
pyp_dct['tool.setuptools'] = st
|
|
@@ -379,6 +387,13 @@ class PyprojectPackageGenerator(BasePyprojectPackageGenerator):
|
|
|
379
387
|
pkg_suffix='-cext',
|
|
380
388
|
).gen(opts)
|
|
381
389
|
|
|
390
|
+
if self.build_specs().pyproject.get('cli_scripts'):
|
|
391
|
+
_PyprojectCliPackageGenerator(
|
|
392
|
+
self._dir_name,
|
|
393
|
+
self._pkgs_root,
|
|
394
|
+
pkg_suffix='-cli',
|
|
395
|
+
).gen(opts)
|
|
396
|
+
|
|
382
397
|
return ret
|
|
383
398
|
|
|
384
399
|
|
|
@@ -420,7 +435,13 @@ class _PyprojectCextPackageGenerator(BasePyprojectPackageGenerator):
|
|
|
420
435
|
prj = specs.pyproject
|
|
421
436
|
prj['dependencies'] = [f'{prj["name"]} == {prj["version"]}']
|
|
422
437
|
prj['name'] += self._pkg_suffix
|
|
423
|
-
|
|
438
|
+
for k in [
|
|
439
|
+
'optional_dependencies',
|
|
440
|
+
'entry_points',
|
|
441
|
+
'scripts',
|
|
442
|
+
'cli_scripts',
|
|
443
|
+
]:
|
|
444
|
+
prj.pop(k, None)
|
|
424
445
|
|
|
425
446
|
pyp_dct['project'] = prj
|
|
426
447
|
|
|
@@ -483,3 +504,73 @@ class _PyprojectCextPackageGenerator(BasePyprojectPackageGenerator):
|
|
|
483
504
|
|
|
484
505
|
with open(os.path.join(self._pkg_dir(), 'setup.py'), 'w') as f:
|
|
485
506
|
f.write(fc.setup_py)
|
|
507
|
+
|
|
508
|
+
|
|
509
|
+
##
|
|
510
|
+
|
|
511
|
+
|
|
512
|
+
class _PyprojectCliPackageGenerator(BasePyprojectPackageGenerator):
|
|
513
|
+
|
|
514
|
+
#
|
|
515
|
+
|
|
516
|
+
@dc.dataclass(frozen=True)
|
|
517
|
+
class FileContents:
|
|
518
|
+
pyproject_dct: ta.Mapping[str, ta.Any]
|
|
519
|
+
|
|
520
|
+
@cached_nullary
|
|
521
|
+
def file_contents(self) -> FileContents:
|
|
522
|
+
specs = self.build_specs()
|
|
523
|
+
|
|
524
|
+
#
|
|
525
|
+
|
|
526
|
+
pyp_dct = {}
|
|
527
|
+
|
|
528
|
+
pyp_dct['build-system'] = {
|
|
529
|
+
'requires': ['setuptools'],
|
|
530
|
+
'build-backend': 'setuptools.build_meta',
|
|
531
|
+
}
|
|
532
|
+
|
|
533
|
+
prj = specs.pyproject
|
|
534
|
+
prj['dependencies'] = [f'{prj["name"]} == {prj["version"]}']
|
|
535
|
+
prj['name'] += self._pkg_suffix
|
|
536
|
+
for k in [
|
|
537
|
+
'optional_dependencies',
|
|
538
|
+
'entry_points',
|
|
539
|
+
'scripts',
|
|
540
|
+
]:
|
|
541
|
+
prj.pop(k, None)
|
|
542
|
+
|
|
543
|
+
pyp_dct['project'] = prj
|
|
544
|
+
|
|
545
|
+
if (scs := prj.pop('cli_scripts', None)):
|
|
546
|
+
pyp_dct['project.scripts'] = scs
|
|
547
|
+
|
|
548
|
+
#
|
|
549
|
+
|
|
550
|
+
st = dict(specs.setuptools)
|
|
551
|
+
pyp_dct['tool.setuptools'] = st
|
|
552
|
+
|
|
553
|
+
for k in [
|
|
554
|
+
'cexts',
|
|
555
|
+
|
|
556
|
+
'find_packages',
|
|
557
|
+
'package_data',
|
|
558
|
+
'manifest_in',
|
|
559
|
+
]:
|
|
560
|
+
st.pop(k, None)
|
|
561
|
+
|
|
562
|
+
pyp_dct['tool.setuptools.packages.find'] = {
|
|
563
|
+
'include': [],
|
|
564
|
+
}
|
|
565
|
+
|
|
566
|
+
#
|
|
567
|
+
|
|
568
|
+
return self.FileContents(
|
|
569
|
+
pyp_dct,
|
|
570
|
+
)
|
|
571
|
+
|
|
572
|
+
def _write_file_contents(self) -> None:
|
|
573
|
+
fc = self.file_contents()
|
|
574
|
+
|
|
575
|
+
with open(os.path.join(self._pkg_dir(), 'pyproject.toml'), 'w') as f:
|
|
576
|
+
TomlWriter(f).write_root(fc.pyproject_dct)
|
omdev/pyproject/reqs.py
CHANGED
omdev/scripts/interp.py
CHANGED
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
# noinspection DuplicatedCode
|
|
3
3
|
# @omlish-lite
|
|
4
4
|
# @omlish-script
|
|
5
|
-
# @
|
|
5
|
+
# @omlish-amalg-output ../interp/cli.py
|
|
6
6
|
# ruff: noqa: N802 UP006 UP007 UP036
|
|
7
7
|
"""
|
|
8
8
|
TODO:
|
|
@@ -1796,16 +1796,14 @@ class RunningInterpProvider(InterpProvider):
|
|
|
1796
1796
|
"""
|
|
1797
1797
|
TODO:
|
|
1798
1798
|
- custom tags
|
|
1799
|
+
- 'aliases'
|
|
1800
|
+
- https://github.com/pyenv/pyenv/pull/2966
|
|
1801
|
+
- https://github.com/pyenv/pyenv/issues/218 (lol)
|
|
1802
|
+
- probably need custom (temp?) definition file
|
|
1803
|
+
- *or* python-build directly just into the versions dir?
|
|
1799
1804
|
- optionally install / upgrade pyenv itself
|
|
1800
1805
|
- new vers dont need these custom mac opts, only run on old vers
|
|
1801
|
-
|
|
1802
|
-
TODO opts:
|
|
1803
|
-
- --enable-loadable-sqlite-extensions LDFLAGS="-L/opt/homebrew/opt/sqlite/lib" CPPFLAGS="-I/opt/homebrew/opt/sqlite/include"
|
|
1804
|
-
- --enable-shared
|
|
1805
|
-
- --enable-optimizations
|
|
1806
|
-
- --enable-profiling ?
|
|
1807
|
-
- --enable-ipv6 ?
|
|
1808
|
-
""" # noqa
|
|
1806
|
+
"""
|
|
1809
1807
|
|
|
1810
1808
|
|
|
1811
1809
|
##
|
|
@@ -1899,8 +1897,33 @@ class PyenvInstallOpts:
|
|
|
1899
1897
|
)
|
|
1900
1898
|
|
|
1901
1899
|
|
|
1902
|
-
|
|
1900
|
+
# TODO: https://github.com/pyenv/pyenv/blob/master/plugins/python-build/README.md#building-for-maximum-performance
|
|
1901
|
+
DEFAULT_PYENV_INSTALL_OPTS = PyenvInstallOpts(
|
|
1902
|
+
opts=[
|
|
1903
|
+
'-s',
|
|
1904
|
+
'-v',
|
|
1905
|
+
'-k',
|
|
1906
|
+
],
|
|
1907
|
+
conf_opts=[
|
|
1908
|
+
'--enable-loadable-sqlite-extensions',
|
|
1909
|
+
|
|
1910
|
+
# '--enable-shared',
|
|
1911
|
+
|
|
1912
|
+
'--enable-optimizations',
|
|
1913
|
+
'--with-lto',
|
|
1914
|
+
|
|
1915
|
+
# '--enable-profiling', # ?
|
|
1916
|
+
|
|
1917
|
+
# '--enable-ipv6', # ?
|
|
1918
|
+
],
|
|
1919
|
+
cflags=[
|
|
1920
|
+
# '-march=native',
|
|
1921
|
+
# '-mtune=native',
|
|
1922
|
+
],
|
|
1923
|
+
)
|
|
1924
|
+
|
|
1903
1925
|
DEBUG_PYENV_INSTALL_OPTS = PyenvInstallOpts(opts=['-g'])
|
|
1926
|
+
|
|
1904
1927
|
THREADED_PYENV_INSTALL_OPTS = PyenvInstallOpts(conf_opts=['--disable-gil'])
|
|
1905
1928
|
|
|
1906
1929
|
|
|
@@ -1999,6 +2022,7 @@ class PyenvVersionInstaller:
|
|
|
1999
2022
|
opts: ta.Optional[PyenvInstallOpts] = None,
|
|
2000
2023
|
interp_opts: InterpOpts = InterpOpts(),
|
|
2001
2024
|
*,
|
|
2025
|
+
install_name: ta.Optional[str] = None,
|
|
2002
2026
|
no_default_opts: bool = False,
|
|
2003
2027
|
pyenv: Pyenv = Pyenv(),
|
|
2004
2028
|
) -> None:
|
|
@@ -2019,6 +2043,7 @@ class PyenvVersionInstaller:
|
|
|
2019
2043
|
self._version = version
|
|
2020
2044
|
self._opts = opts
|
|
2021
2045
|
self._interp_opts = interp_opts
|
|
2046
|
+
self._given_install_name = install_name
|
|
2022
2047
|
|
|
2023
2048
|
self._no_default_opts = no_default_opts
|
|
2024
2049
|
self._pyenv = pyenv
|
|
@@ -2033,6 +2058,8 @@ class PyenvVersionInstaller:
|
|
|
2033
2058
|
|
|
2034
2059
|
@cached_nullary
|
|
2035
2060
|
def install_name(self) -> str:
|
|
2061
|
+
if self._given_install_name is not None:
|
|
2062
|
+
return self._given_install_name
|
|
2036
2063
|
return self._version + ('-debug' if self._interp_opts.debug else '')
|
|
2037
2064
|
|
|
2038
2065
|
@cached_nullary
|
|
@@ -2052,11 +2079,26 @@ class PyenvVersionInstaller:
|
|
|
2052
2079
|
v += ' ' + os.environ[k]
|
|
2053
2080
|
env[k] = v
|
|
2054
2081
|
|
|
2055
|
-
|
|
2056
|
-
self._pyenv.exe(),
|
|
2057
|
-
'install',
|
|
2082
|
+
conf_args = [
|
|
2058
2083
|
*self._opts.opts,
|
|
2059
2084
|
self._version,
|
|
2085
|
+
]
|
|
2086
|
+
|
|
2087
|
+
if self._given_install_name is not None:
|
|
2088
|
+
full_args = [
|
|
2089
|
+
os.path.join(check_not_none(self._pyenv.root()), 'plugins', 'python-build', 'bin', 'python-build'),
|
|
2090
|
+
*conf_args,
|
|
2091
|
+
self.install_dir(),
|
|
2092
|
+
]
|
|
2093
|
+
else:
|
|
2094
|
+
full_args = [
|
|
2095
|
+
self._pyenv.exe(),
|
|
2096
|
+
'install',
|
|
2097
|
+
*conf_args,
|
|
2098
|
+
]
|
|
2099
|
+
|
|
2100
|
+
subprocess_check_call(
|
|
2101
|
+
*full_args,
|
|
2060
2102
|
env=env,
|
|
2061
2103
|
)
|
|
2062
2104
|
|
|
@@ -2414,9 +2456,13 @@ def _list_cmd(args) -> None:
|
|
|
2414
2456
|
|
|
2415
2457
|
|
|
2416
2458
|
def _resolve_cmd(args) -> None:
|
|
2417
|
-
|
|
2459
|
+
if args.provider:
|
|
2460
|
+
p = INTERP_PROVIDER_TYPES_BY_NAME[args.provider]()
|
|
2461
|
+
r = InterpResolver([(p.name, p)])
|
|
2462
|
+
else:
|
|
2463
|
+
r = DEFAULT_INTERP_RESOLVER
|
|
2418
2464
|
s = InterpSpecifier.parse(args.version)
|
|
2419
|
-
print(check_not_none(r.resolve(s)).exe)
|
|
2465
|
+
print(check_not_none(r.resolve(s, install=bool(args.install))).exe)
|
|
2420
2466
|
|
|
2421
2467
|
|
|
2422
2468
|
def _build_parser() -> argparse.ArgumentParser:
|
|
@@ -2426,12 +2472,14 @@ def _build_parser() -> argparse.ArgumentParser:
|
|
|
2426
2472
|
|
|
2427
2473
|
parser_list = subparsers.add_parser('list')
|
|
2428
2474
|
parser_list.add_argument('version')
|
|
2429
|
-
parser_list.add_argument('--debug', action='store_true')
|
|
2475
|
+
parser_list.add_argument('-d', '--debug', action='store_true')
|
|
2430
2476
|
parser_list.set_defaults(func=_list_cmd)
|
|
2431
2477
|
|
|
2432
2478
|
parser_resolve = subparsers.add_parser('resolve')
|
|
2433
2479
|
parser_resolve.add_argument('version')
|
|
2434
|
-
parser_resolve.add_argument('
|
|
2480
|
+
parser_resolve.add_argument('-p', '--provider')
|
|
2481
|
+
parser_resolve.add_argument('-d', '--debug', action='store_true')
|
|
2482
|
+
parser_resolve.add_argument('-i', '--install', action='store_true')
|
|
2435
2483
|
parser_resolve.set_defaults(func=_resolve_cmd)
|
|
2436
2484
|
|
|
2437
2485
|
return parser
|