Cutting a release ships an updated Python wheel to PyPI and an updated
Rust crate to crates.io. Both ports must remain byte-for-byte compatible
with the published testvectors/v1.json, so the release is gated on
the cross-language test suite passing.
We follow semver. The protocol-version field (v: 1 in the wire
format) is independent from the package version:
- Protocol major bump — incompatible wire format. v1 verifiers
must reject v2 pins. Triggers a
vectorpinmajor-version bump. - Protocol minor bump — additive changes (new optional fields,
new dtype identifiers, new signature algorithms with new
identifiers). Old verifiers continue to verify old pins. Triggers
a
vectorpinminor-version bump. - Package patch bump — bug fixes, dependency updates, doc-only changes. No protocol change.
Run all of these and only proceed when each is clean.
# 1. Python: lint + tests
source venv/bin/activate
ruff check .
pytest -v
# 2. Rust: fmt + clippy + tests
cd rust
cargo fmt --all -- --check
cargo clippy -j2 --all-targets -- -D warnings
cargo test -j2 --workspace
cd ..
# 3. Regenerate cross-language test vectors and confirm no drift
python scripts/generate_test_vectors.py
git diff --quiet testvectors/ # must be silent-
Update the version field in three places. Bump
pyproject.toml[project] version,rust/Cargo.toml[workspace.package] version, and theversion:field inCITATION.cff. They must match. -
Update
CHANGELOG.md. Add a section for the new version describing what changed since the previous release. Include the release date inYYYY-MM-DDform. -
Commit the version bump as a single commit.
git commit -am "Release vX.Y.Z" -
Tag the commit.
git tag -a vX.Y.Z -m "VectorPin vX.Y.Z" git push origin main vX.Y.Z -
Build and publish the Python package.
pip install --upgrade build twine python -m build # produces dist/vectorpin-X.Y.Z-*.whl and *.tar.gz twine check dist/* twine upload dist/* -
Publish the Rust crate.
cd rust/vectorpin cargo publish --dry-run # verify it would publish cleanly cargo publish cd ../.. -
Create the GitHub release. The tag from step 4 will appear in the GitHub UI; convert it to a release with the changelog entry as the release notes. Attach
dist/vectorpin-X.Y.Z.tar.gzfor users who want a self-contained source archive. -
Update the companion preprint's
refs.bibto reference the tagged release if the paper is being revised.
- Watch for PyPI / crates.io install issues for ~24 hours.
- Open follow-up issues for any planned next-version work that this release deferred.
- If the protocol changed, tag the corresponding
testvectors/release on the same git SHA so external implementations can fetch the correct fixtures.
If a published version contains a security or correctness bug:
# PyPI
twine yank vectorpin --version X.Y.Z --reason "<short reason>"
# crates.io
cargo yank --version X.Y.Z
Yanked versions remain installable via exact pin (so existing
deployments don't break), but new resolutions skip them. Always
release a fixed X.Y.Z+1 immediately and update the changelog with
the yank notice.