Nim用のGitHub Actionsを作ってみた

# まえがき

setup-nim-actionというNim用のGitHub Actionsを自作してみました。
使い方、作った経緯などについて書きます。

# リポジトリ

作ったActionのコードは以下のリポジトリに全て存在します。
[setup-nim-action - GitHub](https://github.com/jiro4989/setup-nim-action)

# 使い方

`.github/workflows/`配下に以下のようなYAMLを書くだけです。
`uses: jiro4989/setup-nim-action@v1`を付け足すだけでGitHub ActionsのCI環境上でのNim環境の構築は完了します。

```yml
name: Build and test Nim

on: [push]

jobs:
  build:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v1
      - uses: jiro4989/setup-nim-action@v1
      - name: Build
        run: nimble build -Y
      - name: Test
        run: nimble test -Y
```

インストールするNimのバージョンを固定したい場合は`nim-version`を指定します。
デフォルトは`stable`です。

```yml
    - uses: jiro4989/setup-nim-action@v1
      with:
        nim-version: 1.0.2
```

**2019/11/18 追記**

公式が提供しているcache Actionを使えばさらに高速化できます。
4, 5分かかっていたビルドが1分で終わるようになりました。

```yml
    steps:
    - uses: actions/checkout@v1
    - name: Cache choosenim
      id: cache-choosenim
      uses: actions/cache@v1
      with:
        path: ~/.choosenim
        key: ${{ runner.os }}-choosenim-stable
    - name: Cache nimble
      id: cache-nimble
      uses: actions/cache@v1
      with:
        path: ~/.nimble
        key: ${{ runner.os }}-nimble-stable
    - uses: jiro4989/setup-nim-action@v1
    - name: Build
      run: nimble build -Y
    - name: Test
      run: nimble test -Y
```

# 実装

以下のシェルの実行をTypeScriptで書いただけです。

```bash
export PATH=$HOME/.nimble/bin:$PATH
curl https://nim-lang.org/choosenim/init.sh -sSf > init.sh
sh init.sh -y
choosenim update stable
```

初めてのAction作成だったのですが、日本語のドキュメント用意されていたおかげで作成にはあまり苦労しませんでした。
以下のページを参考にしました。

* [アクションのビルド - GitHubヘルプ](https://help.github.com/ja/actions/automating-your-workflow-with-github-actions/building-actions)

ActionはJavaScriptとDockerを使って作れるみたいです。
将来的にネイティブバイナリを生成してGitHub Releasesにアップできるようにもしたかったので、Dockerは使わないことにしました。
よって、JavaScriptを使って実装することにしました。

公式のActionもGitHub上に公開されています。
僕のやりたいことと近いことをやっているActionがないか探していた所、Goのセットアップ用のActionが見つかりました。

* [setup-go - GitHub](https://github.com/actions/setup-go)

こちらはTypeScriptで実装されています。
とてもわかりやすかったので、こちらを参考に実装することにしました。

# CI上での動作

TypeScript何もわからなかったのですが、雰囲気でTypeScriptで実装してJSにトランスコンパイルして動作するようにできました。
以下はsetup-nim-actionを動かしているCIのログです。

* https://github.com/jiro4989/setup-nim-action/actions

setup-nim-actionリポジトリでsetup-nim-actionを実行して、自作の別リポジトリのコマンドをビルドして動作するようにできました。
windows (Windows Server), macOS, linuxでもビルドできてるみたいなので、クロスプラットホームで動くようにもできました。

# 作った経緯

僕は普段TravisCIを使用しています。
しかしTravisCIはNim用のCI環境を提供していません。
よって、Nimの環境構築はリポジトリ毎に自分でインストール設定を定義しないといけません。

TravisCIはYAMLファイルでCI設定を定義します。
ファイルのコピーで設定を使い回せるとはいえ、同じ設定が複数のリポジトリに複製されるのは良いものではないと思います。
この問題をActionsの自作によって解決できるのでは、と考えました。

また、Nim用のActionは存在しないようだったので、自分が作って共有することで、他のNim開発者の開発の助けになるのでは、と考えました。

# 作った感想

Actionを自作して共有できるGitHub Actionsに感動しました。

登場したての新しいプログラミング言語の場合、CIサービス提供側が環境を用意できないことも多いです。
GitHub Actionsなら、Actionを探して、無ければ自作して共有できます。
新しいプログラミング言語のCI環境をいち早く楽に構築できるようになります。
自分以外の開発者も楽できるようになるので、GitHub Actionsもっと普及してほしいなと思いました。

# まとめ

以下の内容について書きました。

* Nim用のGitHub Actionsを自作した
* `uses: jiro4989/setup-nim-action@v1`を付け足すだけで使える
* CI環境のWindows, Mac, Linuxでも動く

僕はつい最近GitHub Actionsを使い始めたばかりですが、しばらくこれを使ってみようと思います。
そのうちGitHub Actionsで各プラットフォーム向けにバイナリを生成する方法について記事を書くかもしれません。

参考までに、以前僕が書いた、Nimのコードから各プラットフォーム向けにバイナリを生成するCI環境構築の記事リンクを以下に記載します。

* [Nimのコードから実行可能バイナリをTravisとAppVeyorで各プラットフォーム向けに生成してGitHub Releasesへリリースする](https://qiita.com/jiro4989/items/e4eba5be550094d904c4)

以上です。