Skip to content

Commit 2af1194

Browse files
Add release checklist for version bumps and PyPI links
1 parent e9f9d58 commit 2af1194

1 file changed

Lines changed: 173 additions & 0 deletions

File tree

RELEASE_CHECKLIST.md

Lines changed: 173 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,173 @@
1+
# Release Checklist
2+
3+
Use this checklist for every `ovvo-nns` version bump and PyPI/TestPyPI release.
4+
5+
## 1. Update every version reference
6+
7+
Update all authoritative and user-facing version locations:
8+
9+
- `pyproject.toml`: `[project].version`
10+
- `src/nns/__init__.py`: `__version__`
11+
- `README.md`: current-version table entry
12+
- `uv.lock`: regenerate with `uv lock`; do not hand-edit generated lockfile contents
13+
14+
Confirm they all agree:
15+
16+
```bash
17+
grep -n 'version = ' pyproject.toml
18+
grep -n '__version__' src/nns/__init__.py
19+
grep -n 'Current version' README.md
20+
grep -A3 'name = "ovvo-nns"' uv.lock
21+
```
22+
23+
## 2. Preserve complete files when editing
24+
25+
Never replace a file with a partial snippet when using the GitHub Contents API or another full-file update tool.
26+
27+
Before writing:
28+
29+
1. Fetch the complete current file.
30+
2. Change only the intended lines.
31+
3. Write the complete file back.
32+
4. Inspect the resulting diff for unintended deletions.
33+
34+
This is especially important for:
35+
36+
- `pyproject.toml`
37+
- `src/nns/__init__.py`
38+
- `README.md`
39+
- generated workflow and lock files
40+
41+
## 3. Make README links PyPI-safe
42+
43+
The README is embedded into the wheel and source distribution as package metadata. PyPI and TestPyPI render it outside the GitHub repository context.
44+
45+
Therefore, links in `README.md` must not rely on repository-relative targets such as:
46+
47+
```markdown
48+
[Forecasting example](examples/vignettes/09_forecasting.py)
49+
```
50+
51+
Use absolute URLs instead:
52+
53+
```markdown
54+
[Forecasting example](https://github.com/OVVO-Financial/NNS-python/blob/main/examples/vignettes/09_forecasting.py)
55+
```
56+
57+
Before every release, audit all Markdown links in `README.md` and convert repository-file links to absolute GitHub URLs. This includes:
58+
59+
- example scripts
60+
- vignette files
61+
- manifests
62+
- repository documentation files
63+
- images not already using absolute URLs
64+
65+
External documentation URLs may remain absolute links to the published documentation site.
66+
67+
## 4. Remember that uploaded metadata is immutable
68+
69+
PyPI and TestPyPI do not update an existing release page when the repository README changes.
70+
71+
Once a distribution version is uploaded, its long description and links are fixed for that uploaded artifact.
72+
73+
If a TestPyPI upload contains broken README links:
74+
75+
- fix the README in the repository;
76+
- bump to a new test version such as `1.5.0.post1` or the next patch version;
77+
- rebuild from a clean `dist/` directory;
78+
- upload the new version.
79+
80+
Do not expect the old TestPyPI page to change retroactively.
81+
82+
A production PyPI version cannot be replaced with different files under the same version number.
83+
84+
## 5. Regenerate the lockfile
85+
86+
After changing `pyproject.toml`:
87+
88+
```bash
89+
uv lock
90+
```
91+
92+
Verify the local package entry shows the new version:
93+
94+
```bash
95+
grep -A3 'name = "ovvo-nns"' uv.lock
96+
```
97+
98+
Commit the regenerated `uv.lock` with the version bump.
99+
100+
## 6. Run the full validation suite
101+
102+
Before building:
103+
104+
```bash
105+
uv sync --group dev
106+
uv run pytest
107+
uv run ruff check .
108+
uv run mypy
109+
```
110+
111+
Confirm all GitHub Actions jobs are green for the exact commit being released.
112+
113+
## 7. Build from a clean tree
114+
115+
```bash
116+
git pull origin main
117+
rm -rf dist build *.egg-info
118+
python -m build
119+
python -m twine check dist/*
120+
```
121+
122+
Confirm the generated filenames contain the intended version.
123+
124+
Inspect the wheel metadata if needed:
125+
126+
```bash
127+
python -m zipfile -l dist/ovvo_nns-<VERSION>-*.whl
128+
```
129+
130+
## 8. TestPyPI verification
131+
132+
Upload a unique test version to TestPyPI when validating packaging or README rendering:
133+
134+
```bash
135+
python -m twine upload --repository testpypi dist/*
136+
```
137+
138+
On the TestPyPI project page, manually verify:
139+
140+
- package version
141+
- README rendering
142+
- every README link
143+
- project URLs
144+
- installation instructions
145+
- code blocks and tables
146+
147+
Do not reuse a TestPyPI version that has already been uploaded.
148+
149+
## 9. Production upload
150+
151+
Only after CI, build checks, and TestPyPI validation pass:
152+
153+
```bash
154+
python -m twine upload dist/*
155+
```
156+
157+
Then verify installation from PyPI in a clean environment:
158+
159+
```bash
160+
python -m pip install --upgrade ovvo-nns==<VERSION>
161+
python -c "import nns; print(nns.__version__)"
162+
```
163+
164+
## 10. Tag the exact released commit
165+
166+
After confirming the release contents:
167+
168+
```bash
169+
git tag -a v<VERSION> -m "ovvo-nns <VERSION>"
170+
git push origin v<VERSION>
171+
```
172+
173+
The tag must point to the exact commit used to build the uploaded distributions.

0 commit comments

Comments
 (0)