From fff4a234a4bb9aa2cab3b2329dacc15cd089a513 Mon Sep 17 00:00:00 2001 From: Christine Dodrill Date: Sun, 31 May 2020 17:47:09 -0400 Subject: [PATCH] blog: gitea-release post (#160) --- blog/gitea-release-tool-2020-05-31.markdown | 202 ++++++++++++++++++++ 1 file changed, 202 insertions(+) create mode 100644 blog/gitea-release-tool-2020-05-31.markdown diff --git a/blog/gitea-release-tool-2020-05-31.markdown b/blog/gitea-release-tool-2020-05-31.markdown new file mode 100644 index 0000000..9ec47b5 --- /dev/null +++ b/blog/gitea-release-tool-2020-05-31.markdown @@ -0,0 +1,202 @@ +--- +title: "gitea-release Tool Announcement" +date: "2020-05-31" +tags: + - gitea + - rust + - release +--- + +# gitea-release Tool Announcement + +I'm a big fan of automating things that can possibly be automated. One of the +biggest pains that I've consistently had is creating/tagging releases of +software. This has been a very manual process for me. I have to write up +changelogs, bump versions and then replicate the changelog/versions in the web +UI of whatever git forge the project in question is using. This works great at +smaller scales, but can quickly become a huge pain in the butt when this needs +to be done more often. Today I've written a small tool to help me automate this +going forward, it is named +[`gitea-release`](https://tulpa.dev/cadey/gitea-release). This is one of my +largest Rust projects to date and something I am incredibly happy with. I will +be using it going forward for all of my repos on my gitea instance +[tulpa.dev](https://tulpa.dev). + +`gitea-release` is a spiritual clone of the tool [`github-release`][ghrelease], +but optimized for my workflow. The biggest changes are that it works on +[gitea][gitea] repos instead of github repos, is written in Rust instead of Go +and it automatically scrapes release notes from `CHANGELOG.md` as well as +reading the version of the software from `VERSION`. + +[ghrelease]: https://github.com/github-release/github-release +[gitea]: https://gitea.io + +## CHANGELOG.md and VERSION files + +The `CHANGELOG.md` file is based on the [Keep a Changelog][kacl] format, but +modified slightly to make it easier for this tool. Here is an example changelog +that this tool accepts: + +[kacl]: https://keepachangelog.com/en/1.0.0/ + +```markdown +# Changelog +All notable changes to this project will be documented in this file. + +The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/), +and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html). + +## 0.1.0 + +### FIXED + +- Refrobnicate the spurious rilkefs + +## 0.0.1 + +First release, proof of concept. +``` + +When a release is created for version 0.1.0, this tool will make the description +of the release about as follows: + +``` +### FIXED + +- Refrobnicate the spurious rilkefs +``` + +This allows the changelog file to be the ultimate source of truth for release +notes with this tool. + +The `VERSION` file plays into this as well. The `VERSION` file MUST be a single +line containing a [semantic version][semver] string. This allows the `VERSION` +file to be the ultimate source of truth for software version data with this +tool. + +[semver]: https://semver.org/spec/v2.0.0.html + +## Release Process + +When this tool is run with the `release` subcommand, the following actions take place: + +- The `VERSION` file is read and loaded as the desired tag for the repo +- The `CHANGELOG.md` file is read and the changes for the `VERSION` are + cherry-picked out of the file +- The git repo is checked to see if that tag already exists + - If the tag exists, the tool exits and does nothing +- If the tag does not exist, it is created (with the changelog fragment as the + body of the tag) and pushed to the gitea server using the supplied gitea token +- A gitea release is created using the changelog fragment and the release name + is generated from the `VERSION` string + +## Automation of the Automation + +This tool works perfectly well locally, but this doesn't make it fully +automated from the gitea repo. I use [drone][drone] as a CI/CD tool for my gitea +repos. Drone has a very convenient and simple to use [plugin +system][droneplugin] that was easy to integrate with [structopt][structopt]. + +[drone]: https://drone.io +[droneplugin]: https://docs.drone.io/plugins/overview/ +[structopt]: https://crates.io/crates/structopt + +I created a drone plugin at `xena/gitea-release` that can be configured as a +pipeline step in your `.drone.yml` like this: + +```yaml +kind: pipeline +name: ci/release +steps: + - name: whatever unit testing step + # ... + - name: auto-release + image: xena/gitea-release:0.2.5 + settings: + auth_username: cadey + changelog_path: ./CHANGELOG.md + gitea_server: https://tulpa.dev + gitea_token: + from_secret: GITEA_TOKEN + when: + event: + - push + branch: + - master +``` + +This allows me to bump the `VERSION` and `CHANGELOG.md`, then push that commit +to git and a new release will automatically be created. You can see an example +of this in action with [the drone build history of the gitea-release +repo](https://drone.tulpa.dev/cadey/gitea-release). You can also how the +`CHANGELOG.md` file grows with the [CHANGELOG of +gitea-release](https://tulpa.dev/cadey/gitea-release/src/branch/master/CHANGELOG.md). + +Once the release is pushed to gitea, you can then use drone to trigger +deployment commands. For example here is the deployment pipeline used to +automatically update the docker image for the gitea-release tool: + +```yaml +kind: pipeline +name: docker +steps: + - name: build docker image + image: "monacoremo/nix:2020-04-05-05f09348-circleci" + environment: + USER: root + commands: + - cachix use xe + - nix-build docker.nix + - cp $(readlink result) /result/docker.tgz + volumes: + - name: image + path: /result + when: + event: + - tag + + - name: push docker image + image: docker:dind + volumes: + - name: image + path: /result + - name: dockersock + path: /var/run/docker.sock + commands: + - docker load -i /result/docker.tgz + - echo $DOCKER_PASSWORD | docker login -u $DOCKER_USERNAME --password-stdin + - docker push xena/gitea-release + environment: + DOCKER_USERNAME: + from_secret: DOCKER_USERNAME + DOCKER_PASSWORD: + from_secret: DOCKER_PASSWORD + when: + event: + - tag + +volumes: + - name: image + temp: {} + - name: dockersock + host: + path: /var/run/docker.sock +``` + +This pipeline will use [Nix](https://nixos.org/nix) to build the docker image, +load it into a Docker daemon and then log into the Docker Hub and push it. This +can then be used to do whatever you want. It may also be a good idea to push a +docker image for every commit and then re-label the tagged commits, but this +wasn't implemented in this repo. + +--- + +I hope this tool will be useful. I will accept feedback over [any contact +method](/contact). If you want to contribute directly to the project, please +feel free to create [issues](https://tulpa.dev/cadey/gitea-release/issues) or +[pull requests](https://tulpa.dev/cadey/gitea-release/pulls). If you don't want +to create an account on my git server, get me the issue details or code diffs +somehow and I will do everything I can to fix issues and integrate code. I just +want to make this tool better however I can. + +Be well.