初めてGoの開発案件にアサインされたのですが、前担当から引き継いだGoのバージョンが1.10なのに対して今回の開発では1.18だったので色々戸惑いました。
その際Go Modulesって何?となって調べたので備忘録。
Go Modules
- Go1.11以降で利用できる依存パッケージ管理ツール。
- go mod init [モジュールパス] と go mod tidyでgo.modとgo.sumを作成してソースコード内でimportに記載してる外部パッケージのダウンロードと依存関係の処理を行ってくれる。
- Go1.10まではGOPATH モード (GOPATH mode)でコード管理を行なっており、コード管理とビルドをGOPATHで指定されたディレクトリ下で行っていた。Go1.11以降はモジュール対応モード (module-aware mode)を使用することで任意のディレクトリでコード管理とビルドが行えるようになった。
前提
- Go 1.18
- 環境変数GO111MODULEは on 又は未指定
- MacOS Monterey 12.5.1
ハンズオン
-
開発用ディレクトリでgo.modファイルの初期化を行う (go mod init)
zsh$ go mod init example.com/testgo //GitHubで公開するの場合 $ go mod init github.com/(GitHubユーザ名)/(リポジトリ名) go: creating new go.mod: module example/testgo go: to add module requirements and sums: go mod tidy
example.com/の部分は適宜変更する。
このソースを外部モジュールとして使用しないのであれば入れなくてもよい。ちなみにこの時点ではgo.modの中身は以下の記載のみ。
go.modmodule example.com/testgo go 1.18
-
コードを書く
とりあえずテスト用として以下のコードを使用。
AWS LambdaでHello Worldするサンプルコードです。main.gopackage main import ( "github.com/aws/aws-lambda-go/lambda" ) func hello() (string, error) { return "Hello ƛ!", nil } func main() { // Make the handler available for Remote Procedure Call by AWS Lambda lambda.Start(hello) }
-
モジュールをインストールする(go mod tidy)
zsh$ go mod tidy go: finding module for package github.com/aws/aws-lambda-go/lambda go: found github.com/aws/aws-lambda-go/lambda in github.com/aws/aws-lambda-go v1.34.1
ソースコード内でimportに記載したパスからLambdaモジュールがインストールされ、go.modにLambdaモジュールの情報が追記されます。
go.sumには依存先モジュールのチェックサム用のハッシュが記載されており、基本的に編集する必要はないです。go.modmodule example.com/testgo go 1.19 require github.com/aws/aws-lambda-go v1.34.1
-
モジュールを追加してみる
logrusを追加します。
main.gopackage main import ( "github.com/aws/aws-lambda-go/lambda" "github.com/sirupsen/logrus" //add ) func hello() (string, error) { logrus.Info("Hello ƛ!") //add return "Hello ƛ!", nil } func main() { // Make the handler available for Remote Procedure Call by AWS Lambda lambda.Start(hello) }
go mod tidyで更新すると
zsh$ go mod tidy go: finding module for package github.com/sirupsen/logrus go: found github.com/sirupsen/logrus in github.com/sirupsen/logrus v1.9.0
go.modmodule example.com/testgo go 1.18 require ( github.com/aws/aws-lambda-go v1.34.1 github.com/sirupsen/logrus v1.9.0 ) require golang.org/x/sys v0.0.0-20220715151400-c0bba94af5f8 // indirect
追加されてますね。
ちなみにgo getでモジュールをインストールしてもgo.modに自動追加されます。
こっちの方が使うケースが多いかもしれません。 -
動作確認
zsh$ GOOS=linux GOARCH=amd64 go build -o testgo #lambda対応でzipにする $ zip testgo.zip testgo
AWSコンソール画面上での操作は省略。
Lambdaへzip化したバイナリファイルをアップしてテストします。
成功しました。
おまけ
depからの移行
私のケースでは前任者がdepを使用していた為Go Modulesへの移行が必要でした。
特に面倒な作業は必要なく、Gopkg.lockが存在する状態でgo mod initを行えばgo.modへ必要なモジュールを追加してくれたので楽ちんです。
詳細:Migrating to Go Modules
参考
Go Modules Reference まず公式ドキュメントを読もう!
Goで扱うやつら(go.mod / go.sum / Makefile)って何なの?
Go のモジュール管理【バージョン 1.17 改訂版】
go mod完全に理解した