Automate the gem release process

Automate the gem release process

To automate the Ruby gem release process, we will only need to configure two things, the GitHub Actions workflow, and using conventional commit messages.

Does this sound interesting? Come and let’s dig into it.

Before we begin, note that in a previous article we talked about How to Create a Ruby Gem and Release It Manually opens a new window that may be a good starting point in the release field.

Through this article we will use the ombu_labs-auth opens a new window gem as an example.

GitHub Actions

In order to use GitHub Actions we need to host our gem in the GitHub opens a new window platform.

To make each piece easier to digest, I’ll split the GitHub Action in three steps:

  1. Step 1. Use release-please-action

In a nutshell, after we merge a PR into the main branch it will trigger the release workflow and identify (according to the commit message) if it should create a new proposal release PR or just update the CHANGELOG.md in an existing proposal release PR.

Updating the CHANGELOG.md is optional and there are more configuration options you can use if needed opens a new window .

Update Release Snippet

- name: Update Release PR
  uses: google-github-actions/release-please-action@v3
  id: release # we will use this ID later on.
  with:
    release-type: ruby
    package-name: ombu_labs-auth
    version-file: "lib/ombu_labs/auth/version.rb"
- name: Checkout
  uses: actions/checkout@v3
  if: steps.release.outputs.release_created
- name: Set Up Ruby
  uses: ruby/setup-ruby@v1
  with:
    bundle-cache: true
  if: steps.release.outputs.release_created
- name: Bundle Install
  run: bundle install
  if: steps.release.outputs.release_created

Notice we use the id keyword to name this step as release (you can use your preferred name as an ID, just make sure to update it in the whole workflow), it is used to check the release_created value to know which step we should run and which one we should not.

  1. Step 2. Publishes to GitHub opens a new window

When visiting the gem’s main page in GitHub, have you seen a section called Releases in the sidebar? Well, that is the section that this will update.

Publish to GitHub Snippet

- name: Publish to GitHub
  run: |
    mkdir -p $HOME/.gem
    touch $HOME/.gem/credentials
    chmod 0600 $HOME/.gem/credentials
    printf -- "---\n:github: ${GEM_HOST_API_KEY}\n" > $HOME/.gem/credentials
    gem build *.gemspec
    gem push --KEY github --host https://rubygems.pkg.github.com/${OWNER} *.gem
  env:
    GEM_HOST_API_KEY: "Bearer $"
    OWNER: $
  if: $

Note that you don’t need to set the GITHUB_TOKEN nor the reporitory_owner used for the env variables, GitHub provides those values.

  1. Step 3. Publish to RubyGems opens a new window

First we need to have an account in RubyGems and create a token for our gem, if you don’t have it yet, follow the next steps.

Steps to Generate a RubyGems Key

Steps to Add the RubyGems Key into GitHub

  • Go to your repo’s settings.
  • In the security section, click Secrets and variables, then click Actions.
  • Once there, click the New repository secret button, add a name (in our case it is RUBYGEMS_AUTH_TOKEN) and paste the generated token.
  • Click the Add secret button to save it.

Publish to RubyGems Snippet

- name: Publish to RubyGems
  run: |
    mkdir -p $HOME/.gem
    touch $HOME/.gem/credentials
    chmod 0600 $HOME/.gem/credentials
    printf -- "---\n:rubygems_api_key: ${GEM_HOST_API_KEY}\n" > $HOME/.gem/credentials
    gem build *.gemspec
    gem push *.gem
  env:
    GEM_HOST_API_KEY: secrets.RUBYGEMS_AUTH_TOKEN
  if: steps.release.outputs.release_created

Again, the env section requires the RUBYGEMS_AUTH_TOKEN secret. In this case we should add it as explained in the steps to add the RubyGems key into GitHub.

Conventional Commit Message

I may spend some time writting the conventional commit specifications, rules, and examples. I’ll let the official page opens a new window do that work.

From my perspective this is probably the most complicated part of automating the release process because we tend to forget about writing the commit message under the convention rules. We can use some tools opens a new window to remind us to write conventional commits though.

Writing conventional commit messages help us on having a good explanation in the CHANGELOG.md file and triggering the release workflow.

Conclusion

Personally, I fell in love with this way of releasing gems. The benefits of implementing this automation are good enough to start doing it. I’ll mention some of them.

Generate the Changelog Automatically

  • This is invaluable because if we do it by hand, I’m pretty sure at some point, we are going to forget to update something in the CHANGELOG.md file.

  • The CHANGELOG.md file is well-structured depending on what change was made.

Let’s imagine we added a new feature. It will create a Features section, add the type, add a short description, and add the link to the PR where we introduce this feature. Isn’t that amazing?

Ex.

Features

  Authentication: Configure the devise gem (#34) (535bd6b), closes #31

Continuous delivery

  • Bumping a new version won’t require tons of effort. Even though it’s a MINOR change you will be comfortable doing it with a single click.

  • It brings flexibility, if you change your computer often, forget about having to configure your computer with the credentials in RubyGems since those are in already in the GitHub Action.

Aware of the next release

  • Since it creates a proposal PR for the next version, everyone can see what is included in the next version even though it hasn’t released yet.

And finally, to make copy/paste easy, here you have the release workflow template opens a new window .

Learn as if you will live forever, live like you will die tomorrow. — Mahatma Gandhi

Get the book