Cargo

The Rust build tool.

See also Link-Time Optimization and the Rust Performance Book.

[profile.release]
lto = true  # "thin" also works

Error messages

Git

Fix problems with git:

export CARGO_NET_GIT_FETCH_WITH_CLI=true

OpenSSL

https://nixos.wiki/wiki/Rust#Building_Rust_crates_that_require_external_system_libraries

Static linking

rustup target add x86_64-unknown-linux-musl
cargo build --target=x86_64-unknown-linux-musl

CI

Use Cargo.lock

Consider passing --locked to Cargo in CI.

From https://doc.rust-lang.org/cargo/commands/cargo-install.html:

By default, the Cargo.lock file that is included with the package will be ignored. This means that Cargo will recompute which versions of dependencies to use, possibly using newer versions that have been released since the package was published. The --locked flag can be used to force Cargo to use the packaged Cargo.lock file if it is available. This may be useful for ensuring reproducible builds, to use the exact same set of dependencies that were available when the package was published. It may also be useful if a newer version of a dependency is published that no longer builds on your system, or has other problems. The downside to using --locked is that you will not receive any fixes or updates to any dependency.

This is appropriate for use in CI, which should default to reproducible builds to prevent failures unrelated to the changes in the codebase.

Example:

   test:
    runs-on: ubuntu-latest
    steps:
    - uses: actions/checkout@v3
    - run: cargo build --locked
    - run: cargo test --locked

Worked example

https://github.com/langston-barrett/mdlynx/tree/main/.github/workflows

Statically linked binaries

Here's an example of building and publishing statically linked binaries in Github Actions:

env:
  # The NAME makes it easier to copy/paste snippets from other CI configs
  NAME: TODO

jobs:
  release:
    runs-on: ubuntu-latest
    steps:
    - uses: actions/checkout@v3

    - name: Deps
      run: |
        sudo apt-get install -y musl-tools
        rustup target add x86_64-unknown-linux-musl

    - name: Build static executable
      run: |
        cargo build  --release --target=x86_64-unknown-linux-musl
        cp target/x86_64-unknown-linux-musl/release/${NAME} .