【GitHub Actions】self-hosted runnerでsetup-pythonアクションを使用したらエラーでハマった話
こんにちは、CX事業本部の若槻です。
GitHub Actionsには、CIのジョブ実行をGitHub上ではなく任意のサーバー上で行えるようにするself-hosted runnersという機能があります。
Self-hosted runners offer more control of hardware, operating system, and software tools than GitHub-hosted runners provide. With self-hosted runners, you can choose to create a custom hardware configuration with more processing power or memory to run larger jobs, install software available on your local network, and choose an operating system not offered by GitHub-hosted runners. Self-hosted runners can be physical, virtual, in a container, on-premises, or in a cloud.
今回は、このself-hosted runnerでsetup-python
アクションを使用しようとした際にエラーとなりハマった話をご紹介します。
setup-python
アクションとは
setup-python
アクションとは、GitHubが公式提供しているGitHub Actionsで利用可能なアクションの一つです。GitHubマーケットプレイスでは現在最新版として「setup-python V2」が公開されています。
This action sets up a Python environment for use in actions by:
- optionally installing and adding to PATH a version of Python that is already installed in the tools cache
- downloading, installing and adding to PATH an available version of Python from GitHub Releases (actions/python-versions) if a specific version is not available in the tools cache
- failing if a specific version of Python is not preinstalled or available for download
- registering problem matchers for error output
上記要約すると、setup-python
アクションは次の方法でジョブ実行時に使用するPython環境をセットアップするとのことです。
- オプションで、tools cacheに既にインストールされているバージョンのPythonをインストールしてPATHに追加する
- tools cacheで特定のバージョンが利用できない場合、GitHubリリース(
actions/python-versions
)から利用可能なバージョンのPythonをダウンロード、インストール、およびPATHに追加する - 特定のバージョンのPythonがプレインストールされていないかダウンロードできない場合は失敗する
使い方は、「setup-python V2」を使いたい場合はGitHub Actionsのコンフィグの中でuses: actions/setup-python@v2
と指定することにより使用できます。
steps: - uses: actions/checkout@v2 - uses: actions/setup-python@v2 with: python-version: '3.x' # Version range or exact version of a Python version to use, using SemVer's version range syntax architecture: 'x64' # optional x64 or x86. Defaults to x64 if not specified - run: python my_script.py
setup-python
アクションをself-hosted runnerで使用してみる
前提環境
self-hosted runnerを実行させる環境にはAWS Cloud9を利用しました。Cloud9のsettingは下記のようになります。
- Environment type:EC2
- Platform:Amazon Linux
ドキュメントを読む
GitHubのドキュメントを読むと、setup-python
アクションをself-hosted runnerで使用する際の必要な設定事項について記載がありました。
少々長いですが、原文と和訳を次に記載します。
原文
If you would like to use setup-python and a self-hosted runner, there are a few extra things you need to make sure are set up so that new versions of Python can be downloaded and configured on your runner.
Linux
- The Python packages that are downloaded from
actions/python-versions
are originally compiled from source in/opt/hostedtoolcache/
with the --enable-shared flag, which makes them non-relocatable. - Create an environment variable called
AGENT_TOOLSDIRECTORY
and set it to/opt/hostedtoolcache
. This controls where the runner downloads and installs tools.- In the same shell that your runner is using, type
export AGENT_TOOLSDIRECTORY=/opt/hostedtoolcache
- A more permanent way of setting the environment variable is to create a .env file in the same directory as your runner and to add
AGENT_TOOLSDIRECTORY=/opt/hostedtoolcache
. This ensures the variable is always set if your runner is configured as a service.
- In the same shell that your runner is using, type
- Create a directory called
hostedtoolcache
inside/opt
. - The user starting the runner must have write permission to the
/opt/hostedtoolcache
directory. It is not possible to start the Linux runner withsudo
and the/opt
directory usually requires root privileges to write to. Check the current user and group that the runner belongs to by typingls -l
inside the runners root directory. - The runner can be granted write access to the /opt/hostedtoolcache directory using a few techniques:
- The user starting the runner is the owner, and the owner has write permission
- The user starting the runner is in the owning group, and the owning group has write permission
- All users have write permission
- One quick way to grant access is to change the user and group of /opt/hostedtoolcache to be the same as the runners using
chown
sudo chown runner-user:runner-group opt/hostedtoolcache/
- If your runner is configured as a service and you run into problems, make sure the user that the service is running as is correct. For more information, you can check the status of your self-hosted runner.
和訳
setup-pythonとセルフホストランナーを使用したい場合は、新しいバージョンのPythonをダウンロードしてランナーに構成できるように設定する必要がある追加の事項がいくつかあります。
actions/python-versions
からダウンロードされたPythonパッケージは、元々ソースから/opt/hostedtoolcache/
に--enable-sharedフラグを付けてコンパイルされているため、再配置できません。AGENT_TOOLSDIRECTORY
という環境変数を作成し、それを/opt/hostedtoolcache
に設定します。これは、ランナーがツールをダウンロードしてインストールする場所を制御します。- ランナーが使用しているのと同じシェルで、
export AGENT_TOOLSDIRECTORY=/opt/hostedtoolcache
と入力します - 環境変数を設定するより永続的な方法は、ランナーと同じディレクトリに.envファイルを作成し、
AGENT_TOOLSDIRECTORY=/opt/hostedtoolcache
を追加することです。これにより、ランナーがサービスとして構成されている場合、変数が常に設定されます。
- ランナーが使用しているのと同じシェルで、
/opt
内にhostedtoolcache
というディレクトリを作成します。- ランナーを開始するユーザーには、
/opt/hostedtoolcache
ディレクトリへの書き込み権限が必要です。 Linuxランナーをsudo
で起動することはできません。/opt
ディレクトリには通常、書き込みにroot権限が必要です。ランナーのルートディレクトリにls -l
と入力して、ランナーが属する現在のユーザーとグループを確認します。- ランナーを開始したユーザーが所有者であり、所有者に書き込み権限がある
- ランナーを開始したユーザーは所有グループに属しており、所有グループには書き込み権限があります
- すべてのユーザーに書き込み権限があります
- アクセスを許可する簡単な方法の1つは、
/opt/hostedtoolcache
のユーザーとグループを、ランナーと同じになるようにchown
を使用して変更することです。sudo chown runner-user:runner-group opt/hostedtoolcache/
- ランナーがサービスとして構成されているときに問題が発生した場合は、サービスが正しく実行されていることをユーザーに確認してください。詳細については、セルフホストランナーのステータスを確認できます。
今回行うこととしたsetup-python
アクション向けの設定
以上の記載を参考に、self-hosted runnerを実行する環境でsetup-python
アクション向けに今回は次の設定を行うことにします。
- ランナーと同じディレクトリに.envファイルを作成し、
AGENT_TOOLSDIRECTORY=/opt/hostedtoolcache
を追加する /opt
内にhostedtoolcache
ディレクトリを作成する/opt/hostedtoolcache
のユーザーとグループを、ランナーと同じになるようにchown
を使用して変更する
設定をする
self-hosted runner自体の設定
まずCloud9上でself-hosted runner自体の設定をします。
GitHub Actionsを利用したいRepositoryのページで、[Settings]タブ - [Actions]で[Add runner]をクリックします。
表示される[Download]と[Configure]のコマンドを控えます。
AWS Cloud9のコンソールを開き、控えたコマンドを実行していきます。
まずactions runnerのツールをダウンロードして展開します。
$ mkdir actions-runner && cd actions-runner $ curl -O -L https://github.com/actions/runner/releases/download/v2.262.1/actions-runner-linux-x64-2.262.1.tar.gz $ tar xzf ./actions-runner-linux-x64-2.262.1.tar.gz
./config.sh
を実行してRunnerのGitHubへの登録を行います。
$ ./config.sh --url https://github.com/{user}/{repo} --token XXXXXXXXXXXXXXXX
setup-python
アクション向けの設定
次に同環境でsetup-python
アクション向けの設定を行います。
actions-runner/.env
ファイルにAGENT_TOOLSDIRECTORY=/opt/hostedtoolcache
を追記します。
LANG=en_US.UTF-8 JAVA_HOME=/usr/lib/jvm/java NVM_BIN=/home/ec2-user/.nvm/versions/node/v10.16.0/bin NVM_PATH=/home/ec2-user/.nvm/versions/node/v10.16.0/lib/node AGENT_TOOLSDIRECTORY=/opt/hostedtoolcache
/opt
配下にhostedtoolcache
ディレクトリを作成します。
$ mkdir /opt/hostedtoolcache
/opt/hostedtoolcache
のユーザーとグループを、ランナーと同じになるように chown
を使用して変更します。
$ ls -l actions-runner/run.sh -rwxr-xr-x 1 ec2-user ec2-user 1666 May 21 20:37 actions-runner/run.sh $ sudo chown ec2-user:ec2-user /opt/hostedtoolcache/
self-hosted runnerでsetup-python
アクションを実行するとエラーとなった
それではここまでで設定した環境でself-hosted runnerによりsetup-python
アクションを実行してみます。
まずランナーを起動させます。./run.sh
を実行し、プロンプトにListening for Jobs
と表示されれば、self-hosted runnersがアクティブになり、CIが実行可能な状態となっています。
$ actions-runner/run.sh √ Connected to GitHub 2020-06-10 11:22:59Z: Listening for Jobs
ソースコードのGitHub Actionsのコンフィグは次のようになります。setup-python
アクションを使用してPython環境を作成するだけのworkflowとなります。
name: Workflow on: push: jobs: cicd: runs-on: self-hosted steps: - uses: actions/setup-python@v2
ソースコードのcommitをGitHubにpushします。するとGitHub ActionsのWorkflow画面でジョブ実行が開始されます。
少し経つとactions/setup-python@v2
の実行でエラーとなりジョブが失敗しました。
エラーの出力は以下のようになりました。
Run actions/setup-python@v2 with: python-version: 3.x token: *** Version 3.x was not found in the local cache ##[error]Version 3.x with arch x64 not found The list of all available versions can be found here: https://raw.githubusercontent.com/actions/python-versions/master/versions-manifest.json
切り分け
切り分けとして、Actionsのコンフィグを編集していくつかのパターンでCIを実行させてみます。
GitHub-hosted runnerで実行した場合
以下のようにjobのruns-on
をubuntu-latest
に変更してGitHub-hosted runnerで実行されるようにしてみます。
name: Workflow on: push: jobs: cicd: runs-on: ubuntu-latest steps: - uses: actions/setup-python@v2
この場合はCI実行は成功しました。
self-hosted runnerでsetup-go
アクションを実行した場合
次に、以下のようにjobで実行するstepをuses: actions/setup-go@v2
に変更して、go環境の作成がself-hosted runnerで実行されるようにしてみます。
name: Workflow on: push: jobs: cicd: runs-on: self-hosted steps: - uses: actions/setup-go@v2
この場合もCI実行は成功しました。
以上の切り分けにより、self-hosted runnerとsetup-python
アクションの組み合わせの時に何かしらの問題が発生しているようです。(もちろん他の条件が影響している可能性もあります)
類似の事象が報告されている
出力されたエラーログVersion 3.x was not found in the local cache
などでググってみると、actions/setup-python Repositoryで前月(2020/5)に以下のissueがopenされていました。
内容は今回遭遇した事象と状況もエラー内容も類似しています。ただし、issue内ではいくつかのユーザーが「/opt/hostedtoolcache
配下にPythonがインストールされているにも関わらずCI実行が失敗する」と報告していますが、私の環境ではエラー発生後にも/opt/hostedtoolcache
配下にはPythonのインストールはされておらず空のままでした。
ただし今回と類似の事象のissueであるのには変わりないため、こちらの対応を待ってみたいと思います。
代替案
今回のエラーを回避する代替案はいくつか考えられますが、CIの要件によって取りうる方法は違ってくるかと思います。
- Python環境の作成に
setup-python
アクションを使用する必要性がない場合
job内でsetup-python
アクションを使用しなければ、self-hosted runnerの実行環境にすでにインストールされているPythonがjob実行に使用されます。
ただし、複数種類のバージョンのPythonを利用する場合はjob実行ごとのバージョン切り替えを工夫する必要があるかと思います。
また、ドキュメント[Using Python without setup-python]にある通り、GitHubとしてはPython環境が必要な場合はsetup-python
アクションを使用するのが推奨とのことです。
- Self-hosted runnerを使用する必要性がない場合
Amazon Linuxなど、GitHub-hosted runnerで用意されていないOS環境(現在用意されているのはUbuntu、Mac、Windowsのみ)でjobを実行したい場合は、job内で任意のDockerイメージから起動したコンテナ上でCIを実施するという方法が考えられます。
おわりに
GitHub Actionsのself-hosted runnerでsetup-python
アクションを使用しようとした際にエラーとなりハマった話でした。
ハードウェア的な制約や要件などが特になければ、代替案でも示した「job内で任意のDockerイメージから起動したコンテナ上でCIを実施する」方法が個人的にはスマートではないかと思っています。次回以降にこの方法を検証した結果をご紹介したいと思います。
以上