Table of contents
Open Table of contents
TL;DR
arm64 アーキテクチャを利用すればアプリケーションのコストパフォーマンスが上がることが期待できます。
しかし、AWS から提供されている Go のランタイム go1.x
は arm64 環境に対応していません。
そこで、この記事では Go で書いた AWS Lambda function を Amazon Linux 2, arm64 環境にデプロイするにはどうすれば良いのかを紹介します。
2023-08-27 追記: AWS Lambda での Go 1.x ランタイムのサポート終了が発表されたので、カスタムランタイムへの移行が必要になりましたね。この記事は実質カスタムランタイムへの移行方法となっているのでもしかしたら参考になるかもしれません。
この記事の背景
最近ではコストパフォーマンスを考えて、クラウドリソースのアーキテクチャを arm64 環境に移行することが増えてきました。
自分はよく、Serverless framework を利用して、AWS Lambda 上に Go で書いた API をデプロイしていたのですが、利用していた go1.x
ランタイムは x86_64
しか対応していません。
別言語 (Python や Node.js) であれば、アーキテクチャを変更するだけで良かったのですが、Go はそうはいきませんでした。 しかし、Go はシングルバイナリを生成することができるので、Lambda のカスタムランタイムで実行することができるはずだと思いました。
そこで調べたり、試したりした結果、Lambda のカスタムランタイムで実行することができたので、その方法を紹介します。
実際 arm64 は安いのか
こちらを御覧ください。塵も積もれば山となるってやつですね。
Lambda のカスタムランタイムとは
利用目的でいうと、Lambda のカスタムランタイムは、Lambda がサポートしていない言語で書かれたコードを実行するために利用するランタイムです。
OS の選択肢には、Amazon Linux, Amazon Linux 2 があります。 このうち、Amazon Linux 2 が arm64 環境に対応していますので、今回はこちらを利用します。
参考: カスタム Lambda ランタイム - AWS Lambda
カスタムランタイムの使用
Lambad のカスタムランタイムドキュメントには、以下のように書かれています。
カスタムランタイムを使用するには、関数のランタイムを provided.al2 に設定します。ランタイムは、関数のデプロイパッケージ、またはレイヤーに含めることができます。
bootstrap という名前のファイルがデプロイパッケージにある場合、Lambda はそのファイルを実行します。そのファイルがない場合、Lambda は関数のレイヤーにランタイムがないかどうかを確認します。ブートストラップファイルが見つからないか、実行可能でない場合、関数は呼び出し時にエラーを返します。
つまり、以下 2 つを満たせば Go の関数を arm64 環境にデプロイできそうです。
- ✅ ランタイムを provided.al2 に設定する (もちろん、アーキテクチャは arm64 に設定する)
- ✅ デプロイパッケージに bootstrap という名前のファイルを含める
ではやっていきましょう 👀
Serverless Framework で al2 arm64 を設定する
以下のように設定します。
provider:
name: aws
runtime: provided.al2
architecture: arm64
見てわかる通り、公式ドキュメントの識別子と同じなのでそのまんまの設定やなといった感じですね。これで 1 つ目の条件は満たせました。
Package 指定を変更する
package 設定のセクションで artifact
を指定するとパッケージング動作を上書きすることが可能です。
ここに、bootstrap という名前のファイルを含んだ function.zip を指定します。
参考: package
functions の下に書くと、その関数のみに設定を適用することができます。今回は functions 下に設定を書いてみます。
functions:
hello:
handler: bootstrap
package:
artifact: bin/function.zip
events:
- httpApi:
method: GET
path: /hello
ビルドスクリプトは適当に Makefile で書いています。
.PHONY: build
build:
GOOS=linux GOARCH=arm64 go build -o bin/bootstrap cmd/lambda/main.go
.PHONY: zip
zip: build
zip -j bin/function.zip bin/bootstrap
make zip
を実行すると、build と zip が実行されて、bin/function.zip
が生成されます。
これで 2 つ目の条件も満たせました 🎉
あとは、sls deploy でデプロイすれば、arm64 環境で動く Lambda function がデプロイされます!
おわりに
今回は、Go で書いた AWS Lambda function を Amazon Linux 2, arm64 環境にデプロイする方法を紹介しました。
ちょっと前に、フレームワークの公式ドキュメントを読むのが成長にスキルアップにつながる的な投稿を見たのですが、今回のはまさしく公式ドキュメントを読んで身につけた知見です。 また、実際には何回か試行錯誤したので、その過程もスキルアップに重要な要素なんだろうなと実感しました。
TODO: サンプルリポジトリを作ってリンクを貼る