Wrapping cargo publish
Rust is not only a really interesting and productive language, it also has a great toolchain with Cargo and rustup. I’ve been doing some personal wok in Rust for a little while, and as others warned me it took a while to get used to having such a picky compiler (like programming in Ada again!) but once you understand a little more about what’s going on it’s pretty easy to make that thin happy.
So, having started a fun little project or two (see crates.io) I started getting a little frustrated with the Cargo publish step. The tool is great, but orchestrating the steps to ensure the publish step is clean wasn’t becoming the habit it needed to be. I had to remember:
- Make sure the build is really clean before you start.
- Make sure the version number is correct and consistent between
Cargo.toml
,README.me
, and any other files that may embed it. - Publish.
- IF publish was successful, then tag the Git repo with the same version number from step 2.
So, I wrote a wrapper, it isn’t exactly rocket surgery, but it saves me the headache of realizing I tagged Git first but the publish failed and I need to do another commit and reset the tags. Or, publishing, feeling good and realizing I didn’t update the history in the readme file.
Script
I simply named it cargopub
, but here it is.
#!/usr/bin/env bash
if [[ "$1" == "" ]] ; then
echo "Error: a version message is required as first parameter" >&2
exit 1
fi
pushd $(git rev-parse --show-toplevel)
if ! cargo clean && cargo fmt -- --check && cargo test && cargo doc --no-deps ; then
echo "Error: failed cargo pre-requisite steps" >&2
exit 2
fi
if [[ -e Cargo.toml ]] ; then
VER=$(grep "^version = " Cargo.toml | egrep -o "[0-9\.]+(\-[a-zA-Z0-9\-_]+)?")
echo "Info: about to publish version $VER"
if [[ -e README.md ]] ; then
if ! grep -q "\*\*$VER\*\*" README.md; then
echo "Error: version not listed in README.md" >&2
exit 3
fi
fi
if cargo publish; then
git tag -a "v$VER" -m "$1"
git push --tags --no-verify
popd
else
echo "Error: cargo publish command failed" >&2
exit 4
fi
else
echo "Error: no cargo file; are you in the right place?" >&2
exit 5
fi