pythonwrench 0.6.2__tar.gz → 0.6.4__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.
- pythonwrench-0.6.4/.github/workflows/test.yaml +194 -0
- pythonwrench-0.6.4/.gitignore +182 -0
- pythonwrench-0.6.4/.pre-commit-config.yaml +32 -0
- pythonwrench-0.6.4/.readthedocs.yaml +26 -0
- pythonwrench-0.6.4/CHANGELOG.md +201 -0
- pythonwrench-0.6.4/CITATION.cff +21 -0
- {pythonwrench-0.6.2/src/pythonwrench.egg-info → pythonwrench-0.6.4}/PKG-INFO +31 -28
- pythonwrench-0.6.4/docs/Makefile +20 -0
- pythonwrench-0.6.4/docs/conf.py +117 -0
- pythonwrench-0.6.4/docs/index.rst +174 -0
- pythonwrench-0.6.4/docs/make.bat +35 -0
- pythonwrench-0.6.4/docs/modules.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.abc.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.argparse.dataclass_.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.argparse.parsers.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.argparse.rst +16 -0
- pythonwrench-0.6.4/docs/pythonwrench.cast.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.checksum.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.collections.collections.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.collections.prop.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.collections.reducers.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.collections.rst +17 -0
- pythonwrench-0.6.4/docs/pythonwrench.concurrent.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.csv.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.dataclasses.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.datetime.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.difflib.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.disk_cache.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.enum.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.functools.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.hashlib.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.importlib.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.inspect.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.json.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.jsonl.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.logging.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.math.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.os.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.pickle.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.random.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.re.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.rst +50 -0
- pythonwrench-0.6.4/docs/pythonwrench.semver.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.serialization.csv.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.serialization.json.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.serialization.jsonl.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.serialization.pickle.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.serialization.rst +18 -0
- pythonwrench-0.6.4/docs/pythonwrench.time.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.typing.checks.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.typing.classes.rst +7 -0
- pythonwrench-0.6.4/docs/pythonwrench.typing.rst +16 -0
- pythonwrench-0.6.4/docs/pythonwrench.warnings.rst +7 -0
- pythonwrench-0.6.4/docs/update.bash +23 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/pyproject.toml +28 -21
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/__init__.py +27 -1
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/_core.py +49 -29
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/abc.py +1 -0
- pythonwrench-0.6.4/src/pythonwrench/argparse/__init__.py +81 -0
- pythonwrench-0.6.4/src/pythonwrench/argparse/dataclass_.py +284 -0
- pythonwrench-0.6.4/src/pythonwrench/argparse/parsers.py +619 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/cast.py +49 -13
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/checksum.py +55 -12
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/collections/collections.py +92 -25
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/collections/prop.py +7 -2
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/collections/reducers.py +70 -23
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/concurrent.py +3 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/dataclasses.py +8 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/disk_cache.py +29 -8
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/entrypoints/safe_rmdir.py +2 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/entrypoints/tree.py +5 -4
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/enum.py +6 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/functools.py +30 -10
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/hashlib.py +35 -14
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/importlib.py +11 -1
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/logging.py +8 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/math.py +11 -1
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/os.py +4 -2
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/random.py +6 -2
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/re.py +66 -45
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/semver.py +36 -5
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/serialization/_core.py +9 -3
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/serialization/csv.py +20 -5
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/serialization/json.py +9 -1
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/serialization/jsonl.py +9 -1
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/serialization/pickle.py +5 -1
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/typing/checks.py +48 -6
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/typing/classes.py +31 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/warnings.py +14 -4
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/tests/test_argparse.py +105 -24
- pythonwrench-0.6.4/tests/test_core.py +30 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/tests/test_importlib.py +1 -2
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/tests/test_typing.py +10 -2
- pythonwrench-0.6.4/uv.lock +4376 -0
- pythonwrench-0.6.2/PKG-INFO +0 -239
- pythonwrench-0.6.2/setup.cfg +0 -4
- pythonwrench-0.6.2/src/pythonwrench/argparse.py +0 -563
- pythonwrench-0.6.2/src/pythonwrench.egg-info/SOURCES.txt +0 -79
- pythonwrench-0.6.2/src/pythonwrench.egg-info/dependency_links.txt +0 -1
- pythonwrench-0.6.2/src/pythonwrench.egg-info/entry_points.txt +0 -10
- pythonwrench-0.6.2/src/pythonwrench.egg-info/requires.txt +0 -18
- pythonwrench-0.6.2/src/pythonwrench.egg-info/top_level.txt +0 -1
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/LICENSE +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/README.md +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/setup.py +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/__main__.py +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/collections/__init__.py +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/csv.py +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/datetime.py +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/difflib.py +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/entrypoints/info.py +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/inspect.py +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/json.py +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/jsonl.py +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/pickle.py +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/serialization/__init__.py +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/time.py +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/src/pythonwrench/typing/__init__.py +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/tests/test_abc.py +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/tests/test_cast.py +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/tests/test_checksum.py +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/tests/test_collections.py +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/tests/test_csv.py +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/tests/test_dataclasses.py +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/tests/test_difflib.py +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/tests/test_disk_cache.py +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/tests/test_entrypoints.py +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/tests/test_enum.py +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/tests/test_functools.py +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/tests/test_hashlib.py +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/tests/test_inspect.py +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/tests/test_json.py +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/tests/test_jsonl.py +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/tests/test_logging.py +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/tests/test_math.py +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/tests/test_os.py +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/tests/test_random.py +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/tests/test_readme.py +0 -0
- {pythonwrench-0.6.2 → pythonwrench-0.6.4}/tests/test_semver.py +0 -0
|
@@ -0,0 +1,194 @@
|
|
|
1
|
+
# Template: https://help.github.com/actions/language-and-framework-guides/using-python-with-github-actions
|
|
2
|
+
|
|
3
|
+
name: Python package using Pip
|
|
4
|
+
|
|
5
|
+
on:
|
|
6
|
+
push:
|
|
7
|
+
branches: [ main, dev** ]
|
|
8
|
+
pull_request:
|
|
9
|
+
branches: [ main, dev** ]
|
|
10
|
+
|
|
11
|
+
env:
|
|
12
|
+
CACHE_NUMBER: 0 # increase to reset cache manually
|
|
13
|
+
UV_NO_SYNC: 1
|
|
14
|
+
|
|
15
|
+
# Cancel workflow if a new push occurs
|
|
16
|
+
concurrency:
|
|
17
|
+
group: ${{ github.workflow }}-${{ github.event.pull_request.number || github.ref }}
|
|
18
|
+
# Never interrupt a main-branch publication between PyPI and GitHub.
|
|
19
|
+
cancel-in-progress: ${{ github.ref != 'refs/heads/main' }}
|
|
20
|
+
|
|
21
|
+
jobs:
|
|
22
|
+
build-and-test:
|
|
23
|
+
runs-on: ${{ matrix.os }}
|
|
24
|
+
|
|
25
|
+
strategy:
|
|
26
|
+
matrix:
|
|
27
|
+
os: [ubuntu-24.04]
|
|
28
|
+
python-version: ["3.8", "3.9", "3.10", "3.11", "3.12", "3.13", "3.14"]
|
|
29
|
+
include:
|
|
30
|
+
- os: windows-2022
|
|
31
|
+
python-version: "3.8"
|
|
32
|
+
- os: windows-latest
|
|
33
|
+
python-version: "3.14"
|
|
34
|
+
- os: macos-15
|
|
35
|
+
python-version: "3.8"
|
|
36
|
+
- os: macos-latest
|
|
37
|
+
python-version: "3.14"
|
|
38
|
+
|
|
39
|
+
steps:
|
|
40
|
+
# --- INSTALLATIONS ---
|
|
41
|
+
- name: Checkout repository
|
|
42
|
+
uses: actions/checkout@v5
|
|
43
|
+
|
|
44
|
+
- name: Install uv and set Python ${{ matrix.python-version }}
|
|
45
|
+
uses: astral-sh/setup-uv@v9.0.0
|
|
46
|
+
with:
|
|
47
|
+
python-version: ${{ matrix.python-version }}
|
|
48
|
+
enable-cache: true
|
|
49
|
+
cache-dependency-glob: "pyproject.toml"
|
|
50
|
+
|
|
51
|
+
- name: Install the project
|
|
52
|
+
run: |
|
|
53
|
+
uv sync --extra tests
|
|
54
|
+
|
|
55
|
+
# --- TESTS ---
|
|
56
|
+
- name: Print install info
|
|
57
|
+
run: |
|
|
58
|
+
uv run pythonwrench-info
|
|
59
|
+
|
|
60
|
+
- name: Check format with Ruff
|
|
61
|
+
run: |
|
|
62
|
+
uv run ruff check
|
|
63
|
+
|
|
64
|
+
- name: Test with coverage + pytest
|
|
65
|
+
run: |
|
|
66
|
+
uv run coverage run -m pytest -v
|
|
67
|
+
|
|
68
|
+
- name: Show coverage results
|
|
69
|
+
run: |
|
|
70
|
+
uv run coverage report -m
|
|
71
|
+
|
|
72
|
+
release-check:
|
|
73
|
+
name: Check whether a release is needed
|
|
74
|
+
if: github.event_name == 'push' && github.ref == 'refs/heads/main'
|
|
75
|
+
needs: build-and-test
|
|
76
|
+
runs-on: ubuntu-24.04
|
|
77
|
+
permissions:
|
|
78
|
+
contents: read
|
|
79
|
+
outputs:
|
|
80
|
+
version: ${{ steps.release.outputs.version }}
|
|
81
|
+
should-publish: ${{ steps.release.outputs.should-publish }}
|
|
82
|
+
|
|
83
|
+
steps:
|
|
84
|
+
- name: Checkout repository and tags
|
|
85
|
+
uses: actions/checkout@v5
|
|
86
|
+
with:
|
|
87
|
+
fetch-depth: 0
|
|
88
|
+
|
|
89
|
+
- name: Validate release metadata
|
|
90
|
+
id: release
|
|
91
|
+
shell: python
|
|
92
|
+
run: |
|
|
93
|
+
import os
|
|
94
|
+
import pathlib
|
|
95
|
+
import re
|
|
96
|
+
|
|
97
|
+
init_text = pathlib.Path("src/pythonwrench/__init__.py").read_text(encoding="utf-8")
|
|
98
|
+
version_match = re.search(
|
|
99
|
+
r'^__version__\s*=\s*["\'](\d+\.\d+\.\d+)["\']\s*$',
|
|
100
|
+
init_text,
|
|
101
|
+
flags=re.MULTILINE,
|
|
102
|
+
)
|
|
103
|
+
if version_match is None:
|
|
104
|
+
raise SystemExit(
|
|
105
|
+
"__version__ must be a stable X.Y.Z release in "
|
|
106
|
+
"src/pythonwrench/__init__.py"
|
|
107
|
+
)
|
|
108
|
+
|
|
109
|
+
version = version_match.group(1)
|
|
110
|
+
changelog = pathlib.Path("CHANGELOG.md").read_text(encoding="utf-8")
|
|
111
|
+
heading = rf"^## \[{re.escape(version)}\](?:[ \t]+[^\r\n]*)?$"
|
|
112
|
+
if re.search(heading, changelog, flags=re.MULTILINE) is None:
|
|
113
|
+
raise SystemExit(f"CHANGELOG.md has no release section for {version}")
|
|
114
|
+
|
|
115
|
+
tag_ref = pathlib.Path(".git/refs/tags") / f"v{version}"
|
|
116
|
+
tag_exists = tag_ref.exists()
|
|
117
|
+
if not tag_exists:
|
|
118
|
+
import subprocess
|
|
119
|
+
|
|
120
|
+
tag_exists = subprocess.run(
|
|
121
|
+
["git", "rev-parse", "--verify", "--quiet", f"refs/tags/v{version}"],
|
|
122
|
+
check=False,
|
|
123
|
+
).returncode == 0
|
|
124
|
+
|
|
125
|
+
with open(os.environ["GITHUB_OUTPUT"], "a", encoding="utf-8") as output:
|
|
126
|
+
print(f"version={version}", file=output)
|
|
127
|
+
print(f"should-publish={'false' if tag_exists else 'true'}", file=output)
|
|
128
|
+
|
|
129
|
+
if tag_exists:
|
|
130
|
+
print(f"v{version} already exists; publication will be skipped.")
|
|
131
|
+
else:
|
|
132
|
+
print(f"v{version} is ready to publish.")
|
|
133
|
+
|
|
134
|
+
publish:
|
|
135
|
+
name: Publish to PyPI and GitHub Releases
|
|
136
|
+
if: needs.release-check.outputs.should-publish == 'true'
|
|
137
|
+
needs: release-check
|
|
138
|
+
runs-on: ubuntu-24.04
|
|
139
|
+
environment:
|
|
140
|
+
name: pypi
|
|
141
|
+
url: https://pypi.org/project/pythonwrench/${{ needs.release-check.outputs.version }}/
|
|
142
|
+
permissions:
|
|
143
|
+
contents: write
|
|
144
|
+
id-token: write
|
|
145
|
+
env:
|
|
146
|
+
RELEASE_VERSION: ${{ needs.release-check.outputs.version }}
|
|
147
|
+
|
|
148
|
+
steps:
|
|
149
|
+
- name: Checkout tested commit
|
|
150
|
+
uses: actions/checkout@v5
|
|
151
|
+
|
|
152
|
+
- name: Install uv
|
|
153
|
+
uses: astral-sh/setup-uv@v9.0.0
|
|
154
|
+
|
|
155
|
+
- name: Build distributions
|
|
156
|
+
run: uv build
|
|
157
|
+
|
|
158
|
+
- name: Validate distributions
|
|
159
|
+
run: uvx twine check dist/*
|
|
160
|
+
|
|
161
|
+
- name: Extract release notes from changelog
|
|
162
|
+
shell: python
|
|
163
|
+
run: |
|
|
164
|
+
import os
|
|
165
|
+
import pathlib
|
|
166
|
+
import re
|
|
167
|
+
|
|
168
|
+
version = os.environ["RELEASE_VERSION"]
|
|
169
|
+
changelog = pathlib.Path("CHANGELOG.md").read_text(encoding="utf-8")
|
|
170
|
+
section = re.search(
|
|
171
|
+
rf"^## \[{re.escape(version)}\](?:[ \t]+[^\r\n]*)?\n(.*?)(?=^## \[|\Z)",
|
|
172
|
+
changelog,
|
|
173
|
+
flags=re.MULTILINE | re.DOTALL,
|
|
174
|
+
)
|
|
175
|
+
if section is None:
|
|
176
|
+
raise SystemExit(f"Could not extract changelog notes for {version}")
|
|
177
|
+
pathlib.Path("release-notes.md").write_text(
|
|
178
|
+
section.group(1).strip() + "\n",
|
|
179
|
+
encoding="utf-8",
|
|
180
|
+
)
|
|
181
|
+
|
|
182
|
+
- name: Publish distributions to PyPI
|
|
183
|
+
uses: pypa/gh-action-pypi-publish@release/v1
|
|
184
|
+
with:
|
|
185
|
+
skip-existing: true
|
|
186
|
+
|
|
187
|
+
- name: Create GitHub Release and tag
|
|
188
|
+
env:
|
|
189
|
+
GH_TOKEN: ${{ github.token }}
|
|
190
|
+
run: |
|
|
191
|
+
gh release create "v${RELEASE_VERSION}" dist/* \
|
|
192
|
+
--target "${GITHUB_SHA}" \
|
|
193
|
+
--title "v${RELEASE_VERSION}" \
|
|
194
|
+
--notes-file release-notes.md
|
|
@@ -0,0 +1,182 @@
|
|
|
1
|
+
# Byte-compiled / optimized / DLL files
|
|
2
|
+
__pycache__/
|
|
3
|
+
*.py[cod]
|
|
4
|
+
*$py.class
|
|
5
|
+
|
|
6
|
+
# C extensions
|
|
7
|
+
*.so
|
|
8
|
+
|
|
9
|
+
# Distribution / packaging
|
|
10
|
+
.Python
|
|
11
|
+
build/
|
|
12
|
+
develop-eggs/
|
|
13
|
+
dist/
|
|
14
|
+
downloads/
|
|
15
|
+
eggs/
|
|
16
|
+
.eggs/
|
|
17
|
+
lib/
|
|
18
|
+
lib64/
|
|
19
|
+
parts/
|
|
20
|
+
sdist/
|
|
21
|
+
var/
|
|
22
|
+
wheels/
|
|
23
|
+
share/python-wheels/
|
|
24
|
+
*.egg-info/
|
|
25
|
+
.installed.cfg
|
|
26
|
+
*.egg
|
|
27
|
+
MANIFEST
|
|
28
|
+
|
|
29
|
+
# PyInstaller
|
|
30
|
+
# Usually these files are written by a python script from a template
|
|
31
|
+
# before PyInstaller builds the exe, so as to inject date/other infos into it.
|
|
32
|
+
*.manifest
|
|
33
|
+
*.spec
|
|
34
|
+
|
|
35
|
+
# Installer logs
|
|
36
|
+
pip-log.txt
|
|
37
|
+
pip-delete-this-directory.txt
|
|
38
|
+
|
|
39
|
+
# Unit test / coverage reports
|
|
40
|
+
htmlcov/
|
|
41
|
+
.tox/
|
|
42
|
+
.nox/
|
|
43
|
+
.coverage
|
|
44
|
+
.coverage.*
|
|
45
|
+
.cache
|
|
46
|
+
nosetests.xml
|
|
47
|
+
coverage.xml
|
|
48
|
+
*.cover
|
|
49
|
+
*.py,cover
|
|
50
|
+
.hypothesis/
|
|
51
|
+
.pytest_cache/
|
|
52
|
+
cover/
|
|
53
|
+
|
|
54
|
+
# Translations
|
|
55
|
+
*.mo
|
|
56
|
+
*.pot
|
|
57
|
+
|
|
58
|
+
# Django stuff:
|
|
59
|
+
*.log
|
|
60
|
+
local_settings.py
|
|
61
|
+
db.sqlite3
|
|
62
|
+
db.sqlite3-journal
|
|
63
|
+
|
|
64
|
+
# Flask stuff:
|
|
65
|
+
instance/
|
|
66
|
+
.webassets-cache
|
|
67
|
+
|
|
68
|
+
# Scrapy stuff:
|
|
69
|
+
.scrapy
|
|
70
|
+
|
|
71
|
+
# Sphinx documentation
|
|
72
|
+
docs/_build/
|
|
73
|
+
|
|
74
|
+
# PyBuilder
|
|
75
|
+
.pybuilder/
|
|
76
|
+
target/
|
|
77
|
+
|
|
78
|
+
# Jupyter Notebook
|
|
79
|
+
.ipynb_checkpoints
|
|
80
|
+
|
|
81
|
+
# IPython
|
|
82
|
+
profile_default/
|
|
83
|
+
ipython_config.py
|
|
84
|
+
|
|
85
|
+
# pyenv
|
|
86
|
+
# For a library or package, you might want to ignore these files since the code is
|
|
87
|
+
# intended to run in multiple environments; otherwise, check them in:
|
|
88
|
+
# .python-version
|
|
89
|
+
|
|
90
|
+
# pipenv
|
|
91
|
+
# According to pypa/pipenv#598, it is recommended to include Pipfile.lock in version control.
|
|
92
|
+
# However, in case of collaboration, if having platform-specific dependencies or dependencies
|
|
93
|
+
# having no cross-platform support, pipenv may install dependencies that don't work, or not
|
|
94
|
+
# install all needed dependencies.
|
|
95
|
+
#Pipfile.lock
|
|
96
|
+
|
|
97
|
+
# UV
|
|
98
|
+
# Similar to Pipfile.lock, it is generally recommended to include uv.lock in version control.
|
|
99
|
+
# This is especially recommended for binary packages to ensure reproducibility, and is more
|
|
100
|
+
# commonly ignored for libraries.
|
|
101
|
+
#uv.lock
|
|
102
|
+
|
|
103
|
+
# poetry
|
|
104
|
+
# Similar to Pipfile.lock, it is generally recommended to include poetry.lock in version control.
|
|
105
|
+
# This is especially recommended for binary packages to ensure reproducibility, and is more
|
|
106
|
+
# commonly ignored for libraries.
|
|
107
|
+
# https://python-poetry.org/docs/basic-usage/#commit-your-poetrylock-file-to-version-control
|
|
108
|
+
#poetry.lock
|
|
109
|
+
|
|
110
|
+
# pdm
|
|
111
|
+
# Similar to Pipfile.lock, it is generally recommended to include pdm.lock in version control.
|
|
112
|
+
#pdm.lock
|
|
113
|
+
# pdm stores project-wide configurations in .pdm.toml, but it is recommended to not include it
|
|
114
|
+
# in version control.
|
|
115
|
+
# https://pdm.fming.dev/latest/usage/project/#working-with-version-control
|
|
116
|
+
.pdm.toml
|
|
117
|
+
.pdm-python
|
|
118
|
+
.pdm-build/
|
|
119
|
+
|
|
120
|
+
# PEP 582; used by e.g. github.com/David-OConnor/pyflow and github.com/pdm-project/pdm
|
|
121
|
+
__pypackages__/
|
|
122
|
+
|
|
123
|
+
# Celery stuff
|
|
124
|
+
celerybeat-schedule
|
|
125
|
+
celerybeat.pid
|
|
126
|
+
|
|
127
|
+
# SageMath parsed files
|
|
128
|
+
*.sage.py
|
|
129
|
+
|
|
130
|
+
# Environments
|
|
131
|
+
.env
|
|
132
|
+
.venv
|
|
133
|
+
env/
|
|
134
|
+
venv/
|
|
135
|
+
ENV/
|
|
136
|
+
env.bak/
|
|
137
|
+
venv.bak/
|
|
138
|
+
|
|
139
|
+
# Spyder project settings
|
|
140
|
+
.spyderproject
|
|
141
|
+
.spyproject
|
|
142
|
+
|
|
143
|
+
# Rope project settings
|
|
144
|
+
.ropeproject
|
|
145
|
+
|
|
146
|
+
# mkdocs documentation
|
|
147
|
+
/site
|
|
148
|
+
|
|
149
|
+
# mypy
|
|
150
|
+
.mypy_cache/
|
|
151
|
+
.dmypy.json
|
|
152
|
+
dmypy.json
|
|
153
|
+
|
|
154
|
+
# Pyre type checker
|
|
155
|
+
.pyre/
|
|
156
|
+
|
|
157
|
+
# pytype static type analyzer
|
|
158
|
+
.pytype/
|
|
159
|
+
|
|
160
|
+
# Cython debug symbols
|
|
161
|
+
cython_debug/
|
|
162
|
+
|
|
163
|
+
# PyCharm
|
|
164
|
+
# JetBrains specific template is maintained in a separate JetBrains.gitignore that can
|
|
165
|
+
# be found at https://github.com/github/gitignore/blob/main/Global/JetBrains.gitignore
|
|
166
|
+
# and can be added to the global gitignore or merged into this file. For a more nuclear
|
|
167
|
+
# option (not recommended) you can uncomment the following to ignore the entire idea folder.
|
|
168
|
+
#.idea/
|
|
169
|
+
|
|
170
|
+
# Ruff stuff:
|
|
171
|
+
.ruff_cache/
|
|
172
|
+
|
|
173
|
+
# PyPI configuration file
|
|
174
|
+
.pypirc
|
|
175
|
+
|
|
176
|
+
# Custom files/dirs
|
|
177
|
+
local_data
|
|
178
|
+
*.ows.swp*
|
|
179
|
+
results
|
|
180
|
+
scripts/cache/
|
|
181
|
+
.nfs0*
|
|
182
|
+
.vscode
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
# exclude: ""
|
|
2
|
+
|
|
3
|
+
repos:
|
|
4
|
+
# Formatting, Whitespace, etc
|
|
5
|
+
- repo: https://github.com/pre-commit/pre-commit-hooks
|
|
6
|
+
rev: v2.2.3
|
|
7
|
+
hooks:
|
|
8
|
+
- id: trailing-whitespace
|
|
9
|
+
- id: check-added-large-files
|
|
10
|
+
args: ['--maxkb=1000']
|
|
11
|
+
- id: check-ast
|
|
12
|
+
- id: check-json
|
|
13
|
+
- id: check-merge-conflict
|
|
14
|
+
- id: check-xml
|
|
15
|
+
- id: check-yaml
|
|
16
|
+
args: ['--unsafe'] # required because hyperpyyaml has specific constructor not supported by pyyaml (i.e. !apply)
|
|
17
|
+
- id: debug-statements
|
|
18
|
+
- id: end-of-file-fixer
|
|
19
|
+
- id: requirements-txt-fixer
|
|
20
|
+
- id: mixed-line-ending
|
|
21
|
+
args: ['--fix=no']
|
|
22
|
+
|
|
23
|
+
- repo: https://github.com/astral-sh/ruff-pre-commit
|
|
24
|
+
rev: v0.14.9
|
|
25
|
+
hooks:
|
|
26
|
+
- id: ruff
|
|
27
|
+
types_or: [python, pyi]
|
|
28
|
+
args: [--select, I, --fix]
|
|
29
|
+
- id: ruff-format
|
|
30
|
+
types_or: [python, pyi]
|
|
31
|
+
- id: ruff-check
|
|
32
|
+
args: [ --fix ]
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
# .readthedocs.yaml
|
|
2
|
+
# Read the Docs configuration file
|
|
3
|
+
# See https://docs.readthedocs.io/en/stable/config-file/v2.html for details
|
|
4
|
+
|
|
5
|
+
# Required
|
|
6
|
+
version: 2
|
|
7
|
+
|
|
8
|
+
# Set the version of Python and other tools you might need
|
|
9
|
+
build:
|
|
10
|
+
os: ubuntu-24.04
|
|
11
|
+
tools:
|
|
12
|
+
python: "3.13"
|
|
13
|
+
|
|
14
|
+
# Build documentation in the docs/ directory with Sphinx
|
|
15
|
+
sphinx:
|
|
16
|
+
configuration: docs/conf.py
|
|
17
|
+
|
|
18
|
+
# If using Sphinx, optionally build your docs in additional formats such as PDF
|
|
19
|
+
# formats:
|
|
20
|
+
# - pdf
|
|
21
|
+
python:
|
|
22
|
+
install:
|
|
23
|
+
- method: pip
|
|
24
|
+
path: .
|
|
25
|
+
extra_requirements:
|
|
26
|
+
- docs
|
|
@@ -0,0 +1,201 @@
|
|
|
1
|
+
# Change log
|
|
2
|
+
|
|
3
|
+
All notable changes to this project will be documented in this file.
|
|
4
|
+
|
|
5
|
+
## [0.6.4] 2026-08-17
|
|
6
|
+
### Added
|
|
7
|
+
- Function `parse_args_using_dataclass` can now handle multiple dataclass at once.
|
|
8
|
+
- Function `parse_args_using_dataclass` now has option `bool_action`.
|
|
9
|
+
|
|
10
|
+
|
|
11
|
+
## [0.6.3] 2026-08-06
|
|
12
|
+
### Added
|
|
13
|
+
- Handle `Enum`, `Path`, and add `register_parser_fn` decorator for `parse_to_type`.
|
|
14
|
+
- `isinstance_generic` now supports parametrized `Callable`.
|
|
15
|
+
|
|
16
|
+
### Modified
|
|
17
|
+
- Replace build backend `setuptools` by `hatchling`.
|
|
18
|
+
|
|
19
|
+
|
|
20
|
+
## [0.6.2] 2026-07-30
|
|
21
|
+
### Added
|
|
22
|
+
- `dataclassdict` decorator and `add_dict_method` function to create dataclass+dict classes.
|
|
23
|
+
|
|
24
|
+
### Modified
|
|
25
|
+
- `add_dataclass_fields_to_parser` now supports mixed union and literals types.
|
|
26
|
+
|
|
27
|
+
### Fixed
|
|
28
|
+
- Typing for `function_alias`, `deprecated_alias` and `deprecated_function` decorators.
|
|
29
|
+
|
|
30
|
+
|
|
31
|
+
## [0.6.1] 2026-07-25
|
|
32
|
+
### Added
|
|
33
|
+
- `list_parsing` argument value `"brackets"` to `add_dataclass_fields_to_parser`.
|
|
34
|
+
- `pre_fn` and `post_fn` args to `function_alias`, `deprecated_alias` and `deprecated_function`.
|
|
35
|
+
- `ModulePlacerholder` and `import_if_available`
|
|
36
|
+
|
|
37
|
+
### Fixed
|
|
38
|
+
- Minor compatibilities with python 3.8.
|
|
39
|
+
|
|
40
|
+
|
|
41
|
+
## [0.6.0] 2026-07-24
|
|
42
|
+
### Added
|
|
43
|
+
- Add `_fill_all_arguments` option to `filter_and_call`.
|
|
44
|
+
- Add `parse_args_using_dataclass` function to parse program arguments using dataclass.
|
|
45
|
+
|
|
46
|
+
### Modified
|
|
47
|
+
- Move CSV, JSON, JSONL and PICKLE functions to new `serialization` module.
|
|
48
|
+
- Default value for `key_mode` in `dict_list_to_list_dict` is now `"same"` to match `list_dict_to_dict_list`.
|
|
49
|
+
|
|
50
|
+
### Fixed
|
|
51
|
+
- `Ticker` class in global context.
|
|
52
|
+
- `is_special_form` and `is_parametrized` now supports objects with custom `__contains__`, like ndarray or DataFrames.
|
|
53
|
+
|
|
54
|
+
|
|
55
|
+
## [0.5.2] 2026-07-02
|
|
56
|
+
### Modified
|
|
57
|
+
- `lazy-loader` package is now optional.
|
|
58
|
+
|
|
59
|
+
### Fixed
|
|
60
|
+
- `Placeholder` and `requires_packages` in global context.
|
|
61
|
+
- `as_builtin` now support conversions of dataclasses attributes, without converting to dict with `dataclasses.asdict`.
|
|
62
|
+
|
|
63
|
+
|
|
64
|
+
## [0.5.1] 2026-06-19
|
|
65
|
+
### Added
|
|
66
|
+
- Argument `by` to `sorted_dict` function.
|
|
67
|
+
- `Ticker` class.
|
|
68
|
+
- `SupportsIter` alias of `Iterable`.
|
|
69
|
+
- `is_parameterized`, `is_collection_alias`, `is_special_form` functions.
|
|
70
|
+
|
|
71
|
+
### Modified
|
|
72
|
+
- Checksum can apply to `date`, `datetime`, parametrized types, collections aliases and special forms.
|
|
73
|
+
|
|
74
|
+
|
|
75
|
+
## [0.5.0] 2026-03-05
|
|
76
|
+
### Modified
|
|
77
|
+
- Change default store mode to `"outputs_only"` in disk cache.
|
|
78
|
+
- Change default `fn_name` to function name instead of fully qualified name in disk cache.
|
|
79
|
+
- Lazily load imports if `lazy_loader` package is available.
|
|
80
|
+
|
|
81
|
+
|
|
82
|
+
## [0.4.10] 2026-02-09
|
|
83
|
+
### Fixed
|
|
84
|
+
- Disk cache custom keywords arguments for cache filename.
|
|
85
|
+
|
|
86
|
+
|
|
87
|
+
## [0.4.9] 2026-02-06
|
|
88
|
+
### Fixed
|
|
89
|
+
- `Version` now ignores buildmetadata when comparing versions.
|
|
90
|
+
|
|
91
|
+
|
|
92
|
+
## [0.4.8] 2026-02-06
|
|
93
|
+
### Added
|
|
94
|
+
- `checksum_any` now supports `Enum` instances.
|
|
95
|
+
|
|
96
|
+
|
|
97
|
+
### Fixed
|
|
98
|
+
- Missing global typing imports.
|
|
99
|
+
|
|
100
|
+
|
|
101
|
+
## [0.4.7] 2026-02-01
|
|
102
|
+
### Modified
|
|
103
|
+
- Disk cache functions now detect saving backend when custom load/dump functions are provided.
|
|
104
|
+
|
|
105
|
+
### Fixed
|
|
106
|
+
- `Callable` in `isinstance_generic` check.
|
|
107
|
+
|
|
108
|
+
|
|
109
|
+
## [0.4.6] 2026-01-09
|
|
110
|
+
### Added
|
|
111
|
+
- `cache_fname_fmt` can now be a custom callable formatter.
|
|
112
|
+
|
|
113
|
+
|
|
114
|
+
## [0.4.5] 2026-01-09
|
|
115
|
+
### Fixed
|
|
116
|
+
- Documentation build with constraint `sphinx<9.0.0`.
|
|
117
|
+
|
|
118
|
+
|
|
119
|
+
## [0.4.4] 2026-01-09
|
|
120
|
+
### Added
|
|
121
|
+
- `SizedGenerator` class wrapper.
|
|
122
|
+
- `executor_kwds` argument to `ThreadPoolExecutorHelper` class.
|
|
123
|
+
- `cache_fname_fmt` argument in `disk_cache` now supports inputs arguments values to name the cache file.
|
|
124
|
+
|
|
125
|
+
|
|
126
|
+
## [0.4.3] 2025-12-13
|
|
127
|
+
### Added
|
|
128
|
+
- `as_builtin` now supports `datetime.date` instances.
|
|
129
|
+
- `check_only_first` argument in `isinstance_generic` function.
|
|
130
|
+
- `filter_with_patterns` function.
|
|
131
|
+
- `skipfiles`, `include` and `sort` to `tree_iter` function.
|
|
132
|
+
- `SupportsGetitem` protocols now has `T_Index` typevar set to `Any` instead of `int` by default.
|
|
133
|
+
- `SupportsGetitem2`, `SupportsGetitemLen2` and `SupportsGetitemIterLen2` protocols with generic parameters in reversed order to match `Mapping[key, value]` order.
|
|
134
|
+
- `ThreadPoolExecutorHelper` class.
|
|
135
|
+
- `SupportsMatmul` typing class.
|
|
136
|
+
- `reduce_matmul` function.
|
|
137
|
+
|
|
138
|
+
|
|
139
|
+
## [0.4.2] 2025-10-16
|
|
140
|
+
### Fixed
|
|
141
|
+
- `get_argnames` and `filter_and_call` functions when argument `fn` contains arguments with default values.
|
|
142
|
+
|
|
143
|
+
|
|
144
|
+
## [0.4.1] 2025-09-11
|
|
145
|
+
### Added
|
|
146
|
+
- `SupportsGetitem` protocol.
|
|
147
|
+
- All `SupportGetitem`-based protocols now accept a second generic to specify idx type.
|
|
148
|
+
- `seed` option to `randstr` function.
|
|
149
|
+
|
|
150
|
+
### Modified
|
|
151
|
+
- `checksum_any` computation with `set` and `frozenset` objects no longer require to sort elements.
|
|
152
|
+
|
|
153
|
+
### Fixed
|
|
154
|
+
- Default value for `T_Index` typevar for protocol that specify `__getitem__` method.
|
|
155
|
+
- `reload_editable_submodules` when no editable submodule is imported.
|
|
156
|
+
|
|
157
|
+
|
|
158
|
+
## [0.4.0] 2025-07-18
|
|
159
|
+
### Added
|
|
160
|
+
- `duplicate_list` function to duplicate elements in a list.
|
|
161
|
+
- `loads`, `save`, `read` functions for CSV, JSON and PICKLE.
|
|
162
|
+
- JSONL file format support.
|
|
163
|
+
- `str_to_type` and `parse_to` functions to convert any argparse argument to builtin value.
|
|
164
|
+
- `requires_packages` decorator to avoid calling a function that requires an optional dependency.
|
|
165
|
+
|
|
166
|
+
### Modified
|
|
167
|
+
- `deprecated_function` decorator can be used without parenthesis.
|
|
168
|
+
|
|
169
|
+
### Fixed
|
|
170
|
+
- `disk_cache_decorator` typing.
|
|
171
|
+
- `priority` argument in `register` method of `_FunctionRegistry` class.
|
|
172
|
+
- `get_argnames` returns when function contains local variables.
|
|
173
|
+
|
|
174
|
+
|
|
175
|
+
## [0.3.0] 2025-06-29
|
|
176
|
+
### Added
|
|
177
|
+
- `check_args_type` decorator.
|
|
178
|
+
|
|
179
|
+
### Modified
|
|
180
|
+
- `as_builtin` now converts `collections.Counter` instances.
|
|
181
|
+
|
|
182
|
+
### Fixed
|
|
183
|
+
- `as_builtin` now converts correctly `Mapping` instances.
|
|
184
|
+
- `register_checksum_fn` now accepts `priority` arg.
|
|
185
|
+
|
|
186
|
+
|
|
187
|
+
## [0.2.0] 2025-06-25
|
|
188
|
+
### Added
|
|
189
|
+
- Python 3.8 support.
|
|
190
|
+
- `T_BuiltinNumber` and `T_BuiltinScalar` are covariant by default.
|
|
191
|
+
- `SupportsLen` protocol.
|
|
192
|
+
- `randstr` now support a range of sizes.
|
|
193
|
+
- `as_builtin` function to convert object to built-in equivalent recursively.
|
|
194
|
+
|
|
195
|
+
### Modified
|
|
196
|
+
- `disk_cache_decorator` now supports custom saving backend fns.
|
|
197
|
+
|
|
198
|
+
|
|
199
|
+
## [0.1.0] 2025-06-21
|
|
200
|
+
### Added
|
|
201
|
+
- Initial modules from `pyoutil` module contained in [torchoutil](https://github.com/Labbeti/torchoutil) project.
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
# -*- coding: utf-8 -*-
|
|
2
|
+
|
|
3
|
+
cff-version: 1.2.0
|
|
4
|
+
title: pythonwrench
|
|
5
|
+
message: 'If you use this software, please cite it as below.'
|
|
6
|
+
type: software
|
|
7
|
+
authors:
|
|
8
|
+
- given-names: Étienne
|
|
9
|
+
family-names: Labbé
|
|
10
|
+
email: labbeti.pub@gmail.com
|
|
11
|
+
affiliation: IRIT
|
|
12
|
+
orcid: 'https://orcid.org/0000-0002-7219-5463'
|
|
13
|
+
repository-code: 'https://github.com/Labbeti/pythonwrench/'
|
|
14
|
+
abstract: Python library with tools for typing, manipulating collections, and more!
|
|
15
|
+
keywords:
|
|
16
|
+
- python
|
|
17
|
+
- tools
|
|
18
|
+
- utilities
|
|
19
|
+
license: MIT
|
|
20
|
+
version: 0.6.4
|
|
21
|
+
date-released: '2026-08-17'
|