Version Branches

Using version branches is a variation on git-based dependencies which entails keeping parallel, intact code revision histories in separate git branches, and anchoring the dependencies in Cargo.toml to those "version branches" instead of a "general" branch like "dev" or "master":

For instance, imagine there is a crate, my-private-crate, currently at version "0.1.7". You want to make a breaking change to the code, but allow another crate, private-crate-the-sequel to continue depending on the version "0.1.7" release.

A new branch will be created in the my-private-crate repository, i.e.

$ cd ~/src/my-private-crate
$ git checkout -b v0.2.x

Breaking changes to my-private-crate can be pushed to the v0.2.x branch, leaving the version "0.1.7" "release" intact on the v0.1.x branch. If there is an important bug- or hot-fix, it should be made to both v0.1.x and v0.2.x branches.

Now private-crate-the-sequel can depend on the old "0.1.7" version, while a third crate, private-crate-triple-threat, can depend on a newly "released" version "0.2.0-rc.1" of my-private-crate:

# Cargo.toml for private-crate-the-sequel

[dependencies.my-private-crate]
git = "ssh://my-repo.com/my-private-crate.git"
branch = "0.1.x"
# Cargo.toml for private-crate-triple-threat

[dependencies.my-private-crate]
git = "ssh://my-repo.com/my-private-crate.git"
branch = "0.2.x" # <- note: newer branch

Allows Multiple Version Coexistence, at a Cost

The chief benefit of this technique is that different versions of a crate can be used simultaneously as dependencies, which is difficult or error-prone when anchoring the dependency to a "general" branch like "dev" or "master".

A downside of this approach is that it requires quite a bit of maintenance and care to cultivate useful version branches. Unlike publishing a crate version, which is a discrete, intentional act done at a moment when the code is verified (via cargo publish) to be in a good state, version branches are always subject to possible "errant" pushes, in which incomplete and/or non-compiling code is pushed to the branch, potentially leaving other crates themselves unable to build after pulling in those errant changes.

In general, my experience using this technique is, it's more work than setting up a private registry server, especially since the work never ends, yet works less well than a private registry in subtle but important ways.