Refactoring
to
maintainability

Blog moved to Sourcehut

2020-11-24
Tooling

In the beginning

On the 18th of December I will be doing an F# post for the F# Advent Calendar. That is something that I am quite looking forward to. I have thought about doing it before, but then, having so many good F# devs on it is a bit daunting.

Anyway, I thought to myself … maybe lets write something before that (especially as I haven’t written in a while). Suddenly I remembered that travis org is going the way of the Dodo, so I needed to make sure a replacement was in place. And by pure coincidence my ex-colleague Cyril mentioned on twitter the next day or so that he had finally migrated repos to Sourcehut. It was a sign (if you were to believe in them).

I have known Sourcehut for a while. The fact that they had Mercurial repos was of great interest to me. But as per the First Rule of Motion I wasn’t really making the effort to move anything to Sourcehut. But now … now I had a compelling reason. So, I added 2FA (good), added my SSH (good) and proceeded to move the repo (which was the easy part) and then it was time to use their build system. And this last part … needs more than one sentence.

The git repo

If you look at what the git handling offers, clearly has less options than other providers like Github and Gitlab. Nothing wrong with that, though. At the moment I think is going towards a different audience.

You have five views when you go into your repo:

Other than that, is git, so no surprises there.

Building and config file

It seems you have to ways of getting your build going, one is to upload a manifest file on its own, or to upload a manifest file inside your repo. I haven’t tried the first option yet, though maybe is useful for doing multiple repos at the same time? Which you can do with the manifest file on a repo, anyway (or at least seems so)

This manifest file is called .build.yml (so you can guess it, uses yaml files), but you can also have a directory called .build and have multiple yaml files inside. Each file represents a build manifest and you can have up to 4 builds from the single repo/manifest running (if you have more, 4 are selected randomly)

Inside you can declare an image to use, from the ones provided by Sourcehut. If you are thinking that this means no docker images, you are right. It makes sense to me, you avoid having to either download or cache images. Another consequence is that you don’t have an infinite number of OS to use, but rather a subset of *nix systems. Then you can indicate which packages from the distribution you are using you want to install from the official repositories.

I will talk in the following sections about secrets and environment variables, so I will skip now to tasks. You can create multiple tasks, but at the moment this seems only for convenience. They are run in the order declared. So there is no fanciness like you can find on CircleCi. The tasks are shell commands, which they run with set -x (all executed commands are printed) and set -e (breaks the script as soon as a failure is found)

All in all, this was relatively easy to setup. Nothing ornate.

Secrets and environment variables

So separate sections for these two, because I want you to pay extra attention to them.

First, secrets. You can upload SSH keys, PGP keys and files. There is no information if that is stored encrypted or not (I would imagine is so). Secondly, for all of them you get a UUID that you use to indicate which secrets you want to use on that particular build … because secrets are global to your account. SSH keys get saved on the .ssh directory with filename of the UUID (see example below), and for files you can provide both the filename that will be used and the permissions of the file (following the numeric style of *nix systems)

Environment variables are set on the build file, so are local to the build. They are set using a key/value system (as expected). Currently my only gripe with them is that by default they are not encrypted. So if you want to encrypt … you will need to do some manual work (encrypt on your side, add them encrypted to the build file, then decrypt as part of the task). That is cumbersome. Which is why I add the values that I would have added to them as individual files (I know, not ideal, but I wanted to get my build done as quickly as possible).

Interesting point to raise: I was having issues with SSH keys. It seems it was related to some issue with the OpenSSH client that has been present for the last 2 years, in which you need the private and public key together to be able to use the private key. This error never showed on my Travis CI builds … which means (maybe? probably?) that Travis is using an OpenSSH client that is two years out of date.

My take

At the moment Sourcehut is rather simple, there aren’t too many options or features. And I like that. I think the audience to which this is marketed is individual developers, which as it happens is what I want to use it for. As a repo and build system for a company … currently I wouldn’t use it (they are still labeled as alpha, anyway). I have yet to investigate how to do the patchsets, which I don’t expect them to be like Github or Gitlab (I expect they are closer to raw git patchsets, or just that). And probably some kind of grouping/teams would be needed in the long term.

I am liking what I have seen so far, and probably will get some more use from me. Furthermore, I do want to say that I am currently paying to Sourcehut, because I will like it to succeed.

Full Example

This is the build that I currently have for this blog.

image: alpine/latest
packages:
  - rsync
  - ruby-dev
  - ruby
secrets:
  - c16e2650-d2ea-412d-ad18-440d8d7072b1
  - 8bac4674-6b3e-4e59-b3dc-55f2c9379e59
  - 1d71a936-fb16-48f0-98d9-81423c09560b
  - 05f8ecf8-15d0-47bd-86a3-7c0e174e89a0
  - 4dc8ab93-7814-4d2b-949c-d4eb3475dc92
tasks:
  - install: |
      sudo gem install bundle
      cd twoormore
      bundle update --bundler
      bundle install
  - script: |
      cd twoormore
      bundle exec rake build
  - deploy: |
      cd twoormore
      DEPLOY_USER=`cat ~/.deploy_user`
      DEPLOY_HOST=`cat ~/.deploy_host`
      DEPLOY_DIRECTORY=`cat ~/.deploy_directory`
      ln -s ~/.ssh/4dc8ab93-7814-4d2b-949c-d4eb3475dc92 ~/.ssh/id_rsa.pub
      echo -e "Host $DEPLOY_HOST\n\tStrictHostKeyChecking no\n" >> ~/.ssh/config
      rsync -r --quiet --delete-after _site/* $DEPLOY_USER@$DEPLOY_HOST:$DEPLOY_DIRECTORY

Return to Index

Unless otherwise stated, all posts are my own and not associated with any other particular person or company.

For all code - MIT license
All other text - Creative Commons Attribution-ShareAlike 4.0 International License
Creative Commons BY-SA license image