turbo-editors/turbo-rustpublic Fork 0
v1.0.1
Commits
Clone
git clone https://git.rickub.com/turbo-editors/turbo-rust.git
git clone ssh://git@rickub.com/turbo-editors/turbo-rust.git

Host key fingerprint (ed25519): SHA256:iycHnxEyq0Q7uyVpB7JlznP0G7JrTPXLYRcAU5CSLhc — verify it before your first connect.

📦 Turbo Rust 713ea5c · on v1.0.1 · k33g · 12h ago
make-a-release.md · 103 lines · 5.4 KBmarkdown
Blame HistoryOpen raw

How to make a release

This guide shows how to cut a release so that the editor reports its own version correctly. It assumes you can push to the repository.

Check what you are about to release

make version
v0.1.0-14-g88a4c38 (88a4c38)

Fourteen commits past v0.1.0. A -dirty on the end means you have uncommitted changes — commit or stash them first, or the release will carry that suffix for ever.

Tag it

git tag -a v0.2.0 -m "v0.2.0"
git push origin v0.2.0

The tag is what the version comes from, so it has to exist before you build anything you intend to hand out. Annotated (-a) rather than lightweight, because git describe prefers annotated tags.

Build the release binary

make build
./bin/turbo-rust -version
Turbo Rust 0.2.0 (88a4c38, built 2026-08-31T18:04:05Z)

No -14-g… suffix: you are exactly on the tag. That is what tells you the tag took.

Check the About box

Start the editor and press Alt-H, then A.

Turbo Rust 0.2.0

A Turbo C-style editor for Rust,
written in Go.

Commit: 88a4c38
Built:  2026-08-31 18:04 UTC
Theme:  Turbo Classic

Or use the scripts and let the workflow publish

That is the way a release is actually cut. Put the version and its one-line description in release.env — it is gitignored, so CI never sees it:

TAG="v1.0.0"
ABOUT="Turbo Rust"

Then run one script:

./01-release.tag.sh

It runs make check, refuses a tag already taken locally or on origin, refuses a go.mod carrying a replace directive, commits anything outstanding, pushes the branch, and only then tags and pushes the tag. That order matters: a tag pushed before the branch points at a commit the remote has never seen, and a tag created before a failed push is left behind for somebody to find.

That is the last thing you run by hand. Pushing the tag starts .github/workflows/release.yml; follow it on the repository's Actions tab. It runs the suite, cross-compiles the binaries with ./02-build-releases.sh — the same script you can run on your machine — and creates the release page with them: the tag's message, the go install line, links to the documentation at that tag, one binary per platform, the SHA256SUMS and the README that describes the downloads.

The job publishes with its own GITHUB_TOKEN, which is the only credential Rickub's release API accepts — a personal token is refused. There is nothing to configure and no secret to keep, which is why the old 02-release.publish.sh and 04-release.upload-binaries.sh are gone.

02-build-releases.sh cross-compiles every platform and stamps TAG itself, by overriding the Makefile's version: make ldflags VERSION=v1.0.0. The release is v1.0.0, so that is what its binaries say — whatever git describe would have answered, and whether or not the tag has been created yet. It then runs the staged binary for this machine and checks it reports the version, which is the only proof that what ships carries it.

You can see what the workflow will publish without publishing anything, or build the binaries by hand:

./02-build-releases.sh v1.0.0     # writes release/v1.0.0/, pushes nothing

With no argument it reads TAG from release.env; the workflow has no release.env, so it passes the tag it was started by.

The suite includes tests that run 01-release.tag.sh against a throwaway clone. They skip themselves when TURBO_RUST_RELEASING is set, which the script exports before calling make check — removing that line makes a release recurse until something runs out. The workflow sets the same variable for its own go test step.

Variants

  • You install rather than distribute a binary. make install and scripts/install.sh stamp the same way, so an installed editor names the commit it came from. There is nothing extra to do.
  • Someone installs with go install. go install rickub.com/turbo-editors/turbo-rust@v0.2.0 reports 0.2.0 from the module version, with no commit and no build date. That is the Go tool's own record; nothing needs stamping.
  • You tagged the wrong commit. If the tag has not been pushed, delete it (git tag -d v1.0.0), tag the right one, and rebuild. Once it is on origin, do not move it: the module proxy has cached go install …@v1.0.0 and the release page already carries binaries with that number, which is why 01-release.tag.sh refuses a tag that exists. Bump TAG and release again.
  • About says devel. The binary was built with a plain go build . rather than through make. Nothing is wrong with it; it simply has no tag stamped, because the Go build system does not read git tags. Use make build.
  • About says unknown. Nothing named the build at all — a cargo run, or a build from a directory with no git history. Use make build from the checkout.
  • You have no git at all, having downloaded a source archive. make build still works and the binary reports unknown. Pass the version yourself if you need one:
    go build -ldflags "-X 'rickub.com/turbo-editors/turbo-rust/internal/version.stamp=v0.2.0'" -o bin/turbo-rust .
    

See also

  1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
# How to make a release

This guide shows how to cut a release so that the editor reports its own version correctly. It assumes you can push to the repository.

## Check what you are about to release

```sh
make version
```

```
v0.1.0-14-g88a4c38 (88a4c38)
```

Fourteen commits past `v0.1.0`. A `-dirty` on the end means you have uncommitted changes — commit or stash them first, or the release will carry that suffix for ever.

## Tag it

```sh
git tag -a v0.2.0 -m "v0.2.0"
git push origin v0.2.0
```

The tag is what the version comes from, so it has to exist before you build anything you intend to hand out. Annotated (`-a`) rather than lightweight, because `git describe` prefers annotated tags.

## Build the release binary

```sh
make build
./bin/turbo-rust -version
```

```
Turbo Rust 0.2.0 (88a4c38, built 2026-08-31T18:04:05Z)
```

No `-14-g…` suffix: you are exactly on the tag. That is what tells you the tag took.

## Check the About box

Start the editor and press `Alt-H`, then `A`.

```
Turbo Rust 0.2.0

A Turbo C-style editor for Rust,
written in Go.

Commit: 88a4c38
Built:  2026-08-31 18:04 UTC
Theme:  Turbo Classic
```

## Or use the scripts and let the workflow publish

That is the way a release is actually cut. Put the version and its one-line description in `release.env` — it is gitignored, so CI never sees it:

```sh
TAG="v1.0.0"
ABOUT="Turbo Rust"
```

Then run one script:

```sh
./01-release.tag.sh
```

It runs `make check`, refuses a tag already taken locally or on `origin`, refuses a `go.mod` carrying a `replace` directive, commits anything outstanding, pushes the branch, and only then tags and pushes the tag. That order matters: a tag pushed before the branch points at a commit the remote has never seen, and a tag created before a failed push is left behind for somebody to find.

That is the last thing you run by hand. Pushing the tag starts `.github/workflows/release.yml`; follow it on the repository's Actions tab. It runs the suite, cross-compiles the binaries with `./02-build-releases.sh` — the same script you can run on your machine — and creates the release page with them: the tag's message, the `go install` line, links to the documentation **at that tag**, one binary per platform, the `SHA256SUMS` and the README that describes the downloads.

The job publishes with its own `GITHUB_TOKEN`, which is the only credential Rickub's release API accepts — a personal token is refused. There is nothing to configure and no secret to keep, which is why the old `02-release.publish.sh` and `04-release.upload-binaries.sh` are gone.

`02-build-releases.sh` cross-compiles every platform and **stamps `TAG` itself**, by overriding the Makefile's version: `make ldflags VERSION=v1.0.0`. The release *is* `v1.0.0`, so that is what its binaries say — whatever `git describe` would have answered, and whether or not the tag has been created yet. It then runs the staged binary for this machine and checks it reports the version, which is the only proof that what ships carries it.

You can see what the workflow will publish without publishing anything, or build the binaries by hand:

```sh
./02-build-releases.sh v1.0.0     # writes release/v1.0.0/, pushes nothing
```

With no argument it reads `TAG` from `release.env`; the workflow has no `release.env`, so it passes the tag it was started by.

The suite includes tests that run `01-release.tag.sh` against a throwaway clone. They skip themselves when `TURBO_RUST_RELEASING` is set, which the script exports before calling `make check` — removing that line makes a release recurse until something runs out. The workflow sets the same variable for its own `go test` step.

## Variants

- **You install rather than distribute a binary.** `make install` and `scripts/install.sh` stamp the same way, so an installed editor names the commit it came from. There is nothing extra to do.
- **Someone installs with `go install`.** `go install rickub.com/turbo-editors/turbo-rust@v0.2.0` reports `0.2.0` from the module version, with no commit and no build date. That is the Go tool's own record; nothing needs stamping.
- **You tagged the wrong commit.** If the tag has not been pushed, delete it (`git tag -d v1.0.0`), tag the right one, and rebuild. Once it is on `origin`, do not move it: the module proxy has cached `go install …@v1.0.0` and the release page already carries binaries with that number, which is why `01-release.tag.sh` refuses a tag that exists. Bump `TAG` and release again.
- **About says `devel`.** The binary was built with a plain `go build .` rather than through `make`. Nothing is wrong with it; it simply has no tag stamped, because the Go build system does not read git tags. Use `make build`.
- **About says `unknown`.** Nothing named the build at all — a `cargo run`, or a build from a directory with no git history. Use `make build` from the checkout.
- **You have no git at all**, having downloaded a source archive. `make build` still works and the binary reports `unknown`. Pass the version yourself if you need one:
  ```sh
  go build -ldflags "-X 'rickub.com/turbo-editors/turbo-rust/internal/version.stamp=v0.2.0'" -o bin/turbo-rust .
  ```

## See also

- Every source of the number, and what each build reports: [The version number](../reference/versioning.md)
- Why there is no version constant in the source: [Design decisions](../explanation/design-decisions.md#the-version-is-a-property-of-the-build-not-of-the-source)
- Installing onto your PATH: [How to install and build Turbo Rust](install.md)