cargo-generate: The Consultant's Secret Superpower

Mike Burns

We have two teams dedicated to new apps, so it’s no surprise that we’re drawn to Rust’s cargo-generate tool.

The project’s documentation is a good starting point. We’d like to pass on some guidelines and lessons we’ve learned while using it.

Always specify the cargo-generate version

Get it right before it’s a problem: require a minimal cargo-generate version from the start. This way you’ll detect incompatibilities as you go, and it will prevent colleagues from being bitten by missing features or version mismatches.

[template]
cargo_generate_version = ">=0.18.0"

Use sub-directories

Another technique to get right from the start: the git repo should not be the template base. This way you can add all the metadata to the git repo root without worrying about explicitly excluding the files.

Make a directory called template and stuff the cargo-generate.toml in there.

Schedule CI

The documentation explains how, but does not emphasize: you should do this. Automatically using the template once a week is a simple way to be alerted to problems. Knowing that the template has issues ahead of time means you can build that into the setup time for the next project without any surprises.

Generate a setup script and README documentation

The setup script defines the structure for all future one-off scripts in the generated project. We use the xtask pattern, so the cargo xtask setup task comes defined by our templates.

The generated README documents how to set up the project by running the setup script.

Push what you can into libraries

The generator is used once, so if you need a change after the project has been created then the generator is of no help. As much as possible, use the generator to define a structure for your project, but not the specifics.

Put another way, you actually want your template to change very little. Every time you make a change, consider whether there’s a way to apply it to existing apps instead.

The template is company policy

It’s one thing to say “we use cargo workspaces”, but it’s another thing to codify it into the actual tool you use to create apps. This has some implications.

The git repo and its pull requests serve as a record of decisions. We encourage you to make heavy use of that as a place to record the story of why a change is made, what factors lead to that decision, and what the other options were.

The discussion and decisions require an important factor: buy-in. We want to ensure that our developers want to use our templates. They should see it as better than starting from scratch, and it should provide them with tools that they understand and appreciate. The governance of the template repo plays a critical role in advancing that agenda.

Generalize

These lessons come not just from cargo-generate but also from our years spent working on Suspenders and also time spent on an internal Django template. For other consultants switching to Rust, remember the lessons you’ve learned elsewhere and see how they do (or don’t!) fit in the new context.