@@ -4,11 +4,11 @@ requires = ["setuptools"]
44
55[project ]
66authors = [
7- { name = " ticdenis" , email = " denisnavarroalcaide @outlook.es " },
7+ { name = " ticdenis" , email = " navarrodenis940503 @outlook.com " },
88 {
name =
" yasti4" ,
email =
" [email protected] " },
99]
1010maintainers = [
11- { name = " ticdenis" , email = " denisnavarroalcaide @outlook.es " }
11+ { name = " ticdenis" , email = " navarrodenis940503 @outlook.com " }
1212]
1313classifiers = [
1414 " Intended Audience :: Information Technology" ,
@@ -24,11 +24,11 @@ classifiers = [
2424 " Intended Audience :: Developers" ,
2525 " License :: OSI Approved :: MIT License" ,
2626 " Programming Language :: Python :: 3 :: Only" ,
27- " Programming Language :: Python :: 3.8" ,
2827 " Programming Language :: Python :: 3.9" ,
2928 " Programming Language :: Python :: 3.10" ,
3029 " Programming Language :: Python :: 3.11" ,
3130 " Programming Language :: Python :: 3.12" ,
31+ " Programming Language :: Python :: 3.13" ,
3232]
3333dependencies = []
3434description = " Simple and lightweight async console runner."
@@ -37,42 +37,44 @@ keywords = ["asyncio", "async", "aio", "cli", "console"]
3737license = { text = " MIT" }
3838name = " aiocli"
3939readme = " README.md"
40- requires-python = " >=3.8 "
40+ requires-python = " >=3.9 "
4141
4242[project .optional-dependencies ]
4343dev = [
44- ' pre-commit>=3.3.3 ' ,
44+ " pre-commit>=3.8.0 " ,
4545 ' tomli>=2.0.1; python_version<"3.11"' ,
46- ' types-toml>=0.10.8.7 ; python_version<"3.11"' ,
46+ ' types-toml>=0.10.8.20240310 ; python_version<"3.11"' ,
4747]
4848deploy = [
49- " build>=0.10.0 " ,
50- ' setuptools>=68 .1.2 ' ,
51- " twine>=4.0.2 " ,
52- " wheel>=0.41.1 " ,
49+ " build>=1.2.2 " ,
50+ " setuptools>=75 .1.0 " ,
51+ " twine>=5.1.1 " ,
52+ " wheel>=0.44.0 " ,
5353]
5454docs = [
55- " mkdocs>=1.5.2 " ,
56- " mkdocs-material>=9.1.21 " ,
55+ " mkdocs>=1.6.1 " ,
56+ " mkdocs-material>=9.5.37 " ,
5757]
5858fmt = [
59- ' black>=23.7.0 ' ,
60- ' isort>=5.12.0 ' ,
59+ " black>=24.8.0 " ,
60+ " isort>=5.13.2 " ,
6161]
6262security-analysis = [
63- " bandit>=1.7.5" ,
64- " liccheck>=0.9.1" ,
63+ " bandit>=1.7.4" ,
64+ " liccheck>=0.9.2" ,
65+ " setuptools>=75.1.0" , # https://github.com/dhatim/python-license-check/issues/114
6566]
6667static-analysis = [
67- ' mypy>=1.5.1 ' ,
68- " pylint>=2.17.5 " ,
68+ " mypy>=1.11.2 " ,
69+ " pylint>=3.3.1 " ,
6970]
7071test = [
71- " psutil>=5.9.5" ,
72- " pytest>=7.4.0" ,
73- " pytest-asyncio>=0.21.1" ,
74- " pytest-cov>=4.1.0" ,
75- " pytest-xdist>=3.3.1" ,
72+ " nest-asyncio>=1.6.0" ,
73+ " psutil>=6.0.0" ,
74+ " pytest>=8.3.3" ,
75+ " pytest-asyncio>=0.24.0" ,
76+ " pytest-cov>=5.0.0" ,
77+ " pytest-xdist>=3.6.1" ,
7678]
7779
7880[project .urls ]
@@ -89,6 +91,7 @@ include = ["aiocli*"]
8991"aiocli" = [" py.typed" ]
9092
9193[tool .bandit ]
94+ exclude_dirs = [" docs" , " docs_src" , " sample" , " var" ]
9295skips = [" B101" , " B311" ]
9396
9497[tool .black ]
@@ -122,9 +125,11 @@ cache_dir = "var/mypy"
122125[tool .pylint .master ]
123126jobs = " 0"
124127[tool .pylint .messages_control ]
125- disable = " C0103,C0114,C0115,C0116,C0205,C0209,C0301,E0401,E0611,E1135,E1136,R0801,R0902,R0903,R0904,R0913,R0914,R1704,R1725,W0108,W0212,W0235,W0236,W0603,W0611,W0622,W0703,W0707,W1202"
128+ disable = " C0103,C0114,C0115,C0116,C0205,C0209,C0301,E0401,E0611,E1135,E1136,R0801,R0902,R0903,R0904,R0913,R0914,R0917, R1704,R1725,R1731 ,W0108,W0212,W0235,W0236,W0603,W0611,W0622,W0703,W0707,W1202"
126129
127130[tool .pytest .ini_options ]
131+ asyncio_default_fixture_loop_scope = " function"
132+ asyncio_mode = " auto"
128133cache_dir = " var/pytest"
129134addopts = " -q -n auto -p no:warnings --no-cov-on-fail"
130135testpaths = [" tests" ]
@@ -143,7 +148,6 @@ unit-tests = "python3 -m pytest tests/unit"
143148integration-tests = " python3 -m pytest tests/integration"
144149functional-tests = " python3 -m pytest tests/functional"
145150coverage = " python3 -m pytest --cov --cov-report=html"
146- tox = " python3 -m pip install -U tox tox-gh-actions && tox"
147151clean = """ python3 -c \"
148152from glob import iglob
149153from shutil import rmtree
@@ -152,6 +156,47 @@ for pathname in ['./build', './*.egg-info', './dist', './var', '**/__pycache__']
152156 for path in iglob(pathname, recursive=True):
153157 rmtree(path, ignore_errors=True)
154158\" """
159+ check-dependency-update = """ python3 -c \"
160+ from contextlib import suppress
161+ from json import loads
162+ from re import match
163+ try:
164+ from tomllib import load # Python 3.11+
165+ except ModuleNotFoundError:
166+ try:
167+ from tomli import load
168+ except ModuleNotFoundError:
169+ from subprocess import run
170+ run(['python3 -m pip install -U tomli'], stdout=-3, shell=True)
171+ from tomli import load
172+ from urllib.request import urlopen
173+
174+ def get_latest_version(package_name, pypi_url = 'https://pypi.org'):
175+ with suppress(Exception), urlopen(f'{pypi_url}/pypi/{package_name}/json') as res:
176+ return loads(res.read().decode()).get('info', {}).get('version')
177+
178+ def parse_dependency(dep):
179+ result = match(r'([a-zA-Z0-9_-]+)(\\ [.*\\ ])?(?:([<>=!~]+)(.+))?', dep)
180+ return result.groups() if result else (dep, '', '', '')
181+
182+ def compare_deps(deps):
183+ for pkg, extras, op, ver in [parse_dependency(dep) for dep in deps]:
184+ if pkg and op and ver and (last := get_latest_version(pkg)):
185+ if (op == '==' and ver != last) or (op == '>=' and last > ver) or (op == '<=' and last < ver):
186+ yield (pkg + (extras or '') + ' (Current: ' + ver + ', Latest: ' + last + ')')
187+
188+ with open('pyproject.toml', 'rb') as f:
189+ pyproject = load(f).get('project', {})
190+ deps = compare_deps(pyproject.get('dependencies', []))
191+ opt_deps = {group: compare_deps(deps) for group, deps in pyproject.get('optional-dependencies', {}).items()}
192+ parsed_deps = '\\ n'.join(deps)
193+ parsed_opt_deps = [(f'[{opt_dep_group}]\\ n', '\\ n'.join(opt_deps[opt_dep_group])) for opt_dep_group in opt_deps]
194+ if not parsed_deps and not (''.join([v for _, v in parsed_opt_deps])):
195+ print('Already up-to-date.')
196+ else:
197+ print('# pyproject.toml\\ n[project.dependencies]\\ n{0}\\ n[project.optional-dependencies]{1}'.format(parsed_deps, ''.join([k + v for k, v in parsed_opt_deps])))
198+ exit(1)
199+ \" """
155200dev-server = """ python3 -c \"
156201from asyncio import CancelledError, TimeoutError as AsyncTimeoutError, get_event_loop, sleep, wait_for
157202from contextlib import suppress
@@ -183,25 +228,3 @@ async def run_development_server(timeout: int) -> None:
183228if __name__ >= '__main__':
184229 get_event_loop().run_until_complete(run_development_server(timeout=3600)) # 1h
185230\" """
186-
187- [tool .tox ]
188- legacy_tox_ini = """
189- [tox]
190- envlist = py38, py39, py310, py311, py312
191- isolated_build = True
192- skipsdist = True
193- skip_missing_interpreters = True
194- toxworkdir = var/tox
195-
196- [gh-actions]
197- python =
198- 3.8: py38
199- 3.9: py39
200- 3.10: py310
201- 3.11: py311
202- 3.12: py312
203-
204- [testenv]
205- deps = .[dev,deploy,docs,fmt,security-analysis,static-analysis,test]
206- commands = pytest
207- """
0 commit comments